Reading Gary King’s query for users of advice (see also What is advice?), I’d like to add that advice and friends have uses beyond the usual debugging and patching uses that normally come to mind:
The ability to dynamically add or remove instrumentation code at runtime can be quite useful in cases such as event-driven simulations: When you are modeling complex systems, where long-running simulations can see billions of events and sub-events (i.e. sequences of distinct steps taking place during one event), it is often vitally important to efficiently log and analyze only those events or sub-events that really matter to the purpose of this particular simulation run: The simple approach of logging everything under the sun, and only later deciding what to analyse is often impractical due to speed and space constraints.
So the better approach is to only log that which is necessary, however the difficulty lies in determining which events matter and which don’t, especially since for different simulation runs, the things that matter might be completely different, depending on which analysis the user wants performed.
The approach we took in our logistics simulation framework was to use
advice, or rather a home-built instrumentation framework built on
frobbing CMU CL’s fdefn-function
directly, similar to Gerd
Möllmann’s fwrappers code now present in CMU CL: Using this facility
report developers could define which methods they wanted instrumented,
and, having full access to all information the methods had, use this
to record all the information they needed for a particular report.
The instrumentation code was packaged together with the code that analyzed the recorded information and produced the final output, and the simulation user could then switch on or off individual reports at runtime for a simulation run, and only the overhead needed for those reports was inflicted on that particular run.
So a simple analysis which hooks two methods, melde-einlagerung
and
melde-auslagerung
might look like this (sorry for the german names):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
|
Of course with Lisp there are also other solutions to this problem, like runtime-compilation of conditionally-instrumented methods, however using advice was a simple and effective solution to this particular problem, which also works without access to the source of methods to be hooked.