Created
April 7, 2020 12:39
-
-
Save Julio-Guerra/dd3510d5945d9f008d0496a00d527e34 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Example of a function returning the json marshaling result of the | |
// given argument. | |
// | |
// This function is instrumented with a hook point example implementing | |
// the monitoring and protection control flow we need by observing function | |
// calls and possibly aborting them. | |
// | |
// To do so, the following instrumentation block of code is made of two parts: | |
// | |
// 1. The prolog: it is the instrumentation starting point and is a function | |
// that hooks the function call entry and its arguments before the regular | |
// function code gets executed. It returns a boolean value which is true | |
// when the function call must be aborted and the epilog value to use | |
// (described below). | |
// | |
// 2. The epilog: it is function value optionally returned by the prolog which | |
// hooks the function call return along with its returned values. Its | |
// execution is deferred so that it gets called in any return circumstances. | |
// | |
func myInstrumentedFunction(a int) (result []byte, err error) { | |
// Instrumentation block | |
{ | |
// If the prolog hook point is enabled. | |
// Note that this example is not thread-safe for simplicity | |
// reasons. Our actual implementation atomically loads the | |
// function value. | |
if myInstrumentedFunctionHook != nil { | |
// Call it with the function arugments and check its | |
// returned values | |
epilog, abort := myInstrumentedFunctionHook(a) | |
// Regardless of the abort value, a non-nil epilog | |
// function is deferred to observe any return path. | |
if epilog != nil { | |
defer epilog(&result, &err) | |
} | |
// If the abort value is true, we immediately return | |
// from the function. Possibly executing the | |
// previously deferred epilog function. | |
if abort { | |
return | |
} | |
} | |
} | |
// Regular function code | |
return json.Marshal(a) | |
} | |
// The prolog hook variable of the instrumented function. | |
var myInstrumentedFunctionHook myInstrumentedFunctionPrologHookType | |
// The prolog and epilog hook types of the function, strongly typed | |
// and tied to the function signature. | |
type ( | |
myInstrumentedFunctionPrologHookType func(a int) (myInstrumentedFunctionEpilogHookType, bool) | |
myInstrumentedFunctionEpilogHookType func(result *[]byte, err *error) | |
) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment