From 8056dc33e31d87ff81d286b9991883f953705f15 Mon Sep 17 00:00:00 2001 From: Jesse Hallam Date: Fri, 13 Apr 2018 20:09:38 -0400 Subject: Prevent disabling or modifying l4g logging filters (#8628) The underlying l4g library is not resilient to filter modifications in the presence of concurrent goroutines. In particular, it's not safe to call Close() on filters which might be actively held by a goroutine for logging. This change disables all modifications to existing filters once initialized by the App layer. In practice, we might be able to get away with some modifications to the existing filters (i.e. changing levels), but the [golang memory model](https://golang.org/ref/mem) makes no guarantees that it is safe to do so: > Programs that modify data being simultaneously accessed by multiple goroutines must serialize such access. We can solve this holistically by introducing the requisite locking within our fork of the l4g library. For now, we just disable all modifications. --- app/app.go | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'app/app.go') diff --git a/app/app.go b/app/app.go index 27227d271..462c45613 100644 --- a/app/app.go +++ b/app/app.go @@ -125,7 +125,14 @@ func New(options ...Option) (outApp *App, outErr error) { } } model.AppErrorInit(utils.T) + + // The first time we load config, clear any existing filters to allow the configuration + // changes to take effect. This is safe only because no one else is logging at this point. + l4g.Close() + if err := app.LoadConfig(app.configFile); err != nil { + // Re-initialize the default logger as we bail out. + l4g.Global = l4g.NewDefaultLogger(l4g.DEBUG) return nil, err } app.EnableConfigWatch() -- cgit v1.2.3-1-g7c22