[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
The advice feature lets you add to the existing definition of a function, by advising the function. This is a clean method for a library to customize functions defined by other parts of Emacs--cleaner than redefining the whole function.
Each function can have multiple pieces of advice, separately defined. Each defined piece of advice can be enabled or disabled explicitly. All the enabled pieces of advice for any given function actually take effect when you activate advice for that function, or when you define or redefine the function. Note that enabling a piece of advice and activating advice for a function are not the same thing.
Usage Note: Advice is useful for altering the behavior of existing calls to an existing function. If you want the new behavior for new calls, or for key bindings, it is cleaner to define a new function (or a new command) which uses the existing function.
17.1 A Simple Advice Example | A simple example to explain the basics of advice. | |
17.2 Defining Advice | Detailed description of defadvice . | |
17.3 Around-Advice | Wrapping advice around a function's definition. | |
17.4 Computed Advice | ...is to defadvice as fset is to defun . | |
17.5 Activation of Advice | Advice doesn't do anything until you activate it. | |
17.6 Enabling and Disabling Advice | You can enable or disable each piece of advice. | |
17.7 Preactivation | Preactivation is a way of speeding up the loading of compiled advice. | |
17.8 Argument Access in Advice | How advice can access the function's arguments. | |
17.9 Definition of Subr Argument Lists | Accessing arguments when advising a primitive. | |
17.10 The Combined Definition | How advice is implemented. |
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
The command next-line
moves point down vertically one or more
lines; it is the standard binding of C-n. When used on the last
line of the buffer, this command inserts a newline to create a line to
move to if next-line-add-newlines
is non-nil
(its default
is nil
.)
Suppose you wanted to add a similar feature to previous-line
,
which would insert a new line at the beginning of the buffer for the
command to move to. How could you do this?
You could do it by redefining the whole function, but that is not modular. The advice feature provides a cleaner alternative: you can effectively add your code to the existing function definition, without actually changing or even seeing that definition. Here is how to do this:
(defadvice previous-line (before next-line-at-end (arg)) "Insert an empty line when moving up from the top line." (if (and next-line-add-newlines (= arg 1) (save-excursion (beginning-of-line) (bobp))) (progn (beginning-of-line) (newline)))) |
This expression defines a piece of advice for the function
previous-line
. This piece of advice is named
next-line-at-end
, and the symbol before
says that it is
before-advice which should run before the regular definition of
previous-line
. (arg)
specifies how the advice code can
refer to the function's arguments.
When this piece of advice runs, it creates an additional line, in the situation where that is appropriate, but does not move point to that line. This is the correct way to write the advice, because the normal definition will run afterward and will move back to the newly inserted line.
Defining the advice doesn't immediately change the function
previous-line
. That happens when you activate the advice,
like this:
(ad-activate 'previous-line) |
This is what actually begins to use the advice that has been defined so
far for the function previous-line
. Henceforth, whenever that
function is run, whether invoked by the user with C-p or
M-x, or called from Lisp, it runs the advice first, and its
regular definition second.
This example illustrates before-advice, which is one class of advice: it runs before the function's base definition. There are two other advice classes: after-advice, which runs after the base definition, and around-advice, which lets you specify an expression to wrap around the invocation of the base definition.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
To define a piece of advice, use the macro defadvice
. A call
to defadvice
has the following syntax, which is based on the
syntax of defun
and defmacro
, but adds more:
(defadvice function (class name [position] [arglist] flags...) [documentation-string] [interactive-form] body-forms...) |
Here, function is the name of the function (or macro or special form) to be advised. From now on, we will write just "function" when describing the entity being advised, but this always includes macros and special forms.
class specifies the class of the advice--one of before
,
after
, or around
. Before-advice runs before the function
itself; after-advice runs after the function itself; around-advice is
wrapped around the execution of the function itself. After-advice and
around-advice can override the return value by setting
ad-return-value
.
The argument name is the name of the advice, a non-nil
symbol. The advice name uniquely identifies one piece of advice, within all
the pieces of advice in a particular class for a particular
function. The name allows you to refer to the piece of
advice--to redefine it, or to enable or disable it.
In place of the argument list in an ordinary definition, an advice definition calls for several different pieces of information.
The optional position specifies where, in the current list of
advice of the specified class, this new advice should be placed.
It should be either first
, last
or a number that specifies
a zero-based position (first
is equivalent to 0). If no position
is specified, the default is first
. Position values outside the
range of existing positions in this class are mapped to the beginning or
the end of the range, whichever is closer. The position value is
ignored when redefining an existing piece of advice.
The optional arglist can be used to define the argument list for the sake of advice. This becomes the argument list of the combined definition that is generated in order to run the advice (see section 17.10 The Combined Definition). Therefore, the advice expressions can use the argument variables in this list to access argument values.
The argument list used in advice need not be the same as the argument list used in the original function, but must be compatible with it, so that it can handle the ways the function is actually called. If two pieces of advice for a function both specify an argument list, they must specify the same argument list.
See section 17.8 Argument Access in Advice, for more information about argument lists and advice, and a more flexible way for advice to access the arguments.
The remaining elements, flags, are symbols that specify further information about how to use this piece of advice. Here are the valid symbols and their meanings:
activate
This flag has no immediate effect if function itself is not defined yet (a situation known as forward advice), because it is impossible to activate an undefined function's advice. However, defining function will automatically activate its advice.
protect
unwind-protect
form, so that it will execute even if the
previous code gets an error or uses throw
. See section 10.5.4 Cleaning Up from Nonlocal Exits.
compile
activate
is also specified.
See section 17.10 The Combined Definition.
disable
preactivate
defadvice
is
compiled or macroexpanded. This generates a compiled advised definition
according to the current advice state, which will be used during
activation if appropriate. See section 17.7 Preactivation.
This is useful only if this defadvice
is byte-compiled.
The optional documentation-string serves to document this piece of
advice. When advice is active for function, the documentation for
function (as returned by documentation
) combines the
documentation strings of all the advice for function with the
documentation string of its original function definition.
The optional interactive-form form can be supplied to change the interactive behavior of the original function. If more than one piece of advice has an interactive-form, then the first one (the one with the smallest position) found among all the advice takes precedence.
The possibly empty list of body-forms specifies the body of the advice. The body of an advice can access or change the arguments, the return value, the binding environment, and perform any other kind of side effect.
Warning: When you advise a macro, keep in mind that macros are expanded when a program is compiled, not when a compiled program is run. All subroutines used by the advice need to be available when the byte compiler expands the macro.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
Around-advice lets you "wrap" a Lisp expression "around" the
original function definition. You specify where the original function
definition should go by means of the special symbol ad-do-it
.
Where this symbol occurs inside the around-advice body, it is replaced
with a progn
containing the forms of the surrounded code. Here
is an example:
(defadvice foo (around foo-around) "Ignore case in `foo'." (let ((case-fold-search t)) ad-do-it)) |
Its effect is to make sure that case is ignored in
searches when the original definition of foo
is run.
If the around-advice does not use ad-do-it
, then it does not run
the original function definition. This provides a way to override the
original definition completely. (It also overrides lower-positioned
pieces of around-advice).
If the around-advice uses ad-do-it
more than once, the original
definition is run at each place. In this way, around-advice can execute
the original definition (and lower-positioned pieces of around-advice)
several times. Another way to do that is by using ad-do-it
inside of a loop.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
The macro defadvice
resembles defun
in that the code for
the advice, and all other information about it, are explicitly stated in
the source code. You can also create advice whose details are computed,
using the function ad-add-advice
.
ad-add-advice
adds advice as a piece of advice to
function in class class. The argument advice has
this form:
(name protected enabled definition) |
Here protected and enabled are flags, and definition
is the expression that says what the advice should do. If enabled
is nil
, this piece of advice is initially disabled
(see section 17.6 Enabling and Disabling Advice).
If function already has one or more pieces of advice in the
specified class, then position specifies where in the list
to put the new piece of advice. The value of position can either
be first
, last
, or a number (counting from 0 at the
beginning of the list). Numbers outside the range are mapped to the
beginning or the end of the range, whichever is closer. The
position value is ignored when redefining an existing piece of
advice.
If function already has a piece of advice with the same name, then the position argument is ignored and the old advice is replaced with the new one.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
By default, advice does not take effect when you define it--only when
you activate advice for the function that was advised. You can
request the activation of advice for a function when you define the
advice, by specifying the activate
flag in the defadvice
.
But normally you activate the advice for a function by calling the
function ad-activate
or one of the other activation commands
listed below.
Separating the activation of advice from the act of defining it permits you to add several pieces of advice to one function efficiently, without redefining the function over and over as each advice is added. More importantly, it permits defining advice for a function before that function is actually defined.
When a function's advice is first activated, the function's original definition is saved, and all enabled pieces of advice for that function are combined with the original definition to make a new definition. (Pieces of advice that are currently disabled are not used; see 17.6 Enabling and Disabling Advice.) This definition is installed, and optionally byte-compiled as well, depending on conditions described below.
In all of the commands to activate advice, if compile is t
,
the command also compiles the combined definition which implements the
advice.
To activate advice for a function whose advice is already active is not a no-op. It is a useful operation which puts into effect any changes in that function's advice since the previous activation of advice for that function.
Reactivating a function's advice is useful for putting into effect all the changes that have been made in its advice (including enabling and disabling specific pieces of advice; see section 17.6 Enabling and Disabling Advice) since the last time it was activated.
A value of always
specifies to compile unconditionally.
A value of nil
specifies never compile the advice.
A value of maybe
specifies to compile if the byte-compiler is
already loaded. A value of like-original
specifies to compile
the advice if the original definition of the advised function is
compiled or a built-in function.
This variable takes effect only if the compile argument of
ad-activate
(or any of the above functions) was supplied as
nil
. If that argument is non-nil
, that means
to compile the advice regardless.
If the advised definition was constructed during "preactivation"
(see section 17.7 Preactivation), then that definition must already be compiled,
because it was constructed during byte-compilation of the file that
contained the defadvice
with the preactivate
flag.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
Each piece of advice has a flag that says whether it is enabled or
not. By enabling or disabling a piece of advice, you can turn it on
and off without having to undefine and redefine it. For example, here is
how to disable a particular piece of advice named my-advice
for
the function foo
:
(ad-disable-advice 'foo 'before 'my-advice) |
This function by itself only changes the enable flag for a piece of
advice. To make the change take effect in the advised definition, you
must activate the advice for foo
again:
(ad-activate 'foo) |
You can also disable many pieces of advice at once, for various functions, using a regular expression. As always, the changes take real effect only when you next reactivate advice for the functions in question.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
Constructing a combined definition to execute advice is moderately expensive. When a library advises many functions, this can make loading the library slow. In that case, you can use preactivation to construct suitable combined definitions in advance.
To use preactivation, specify the preactivate
flag when you
define the advice with defadvice
. This defadvice
call
creates a combined definition which embodies this piece of advice
(whether enabled or not) plus any other currently enabled advice for the
same function, and the function's own definition. If the
defadvice
is compiled, that compiles the combined definition
also.
When the function's advice is subsequently activated, if the enabled advice for the function matches what was used to make this combined definition, then the existing combined definition is used, thus avoiding the need to construct one. Thus, preactivation never causes wrong results--but it may fail to do any good, if the enabled advice at the time of activation doesn't match what was used for preactivation.
Here are some symptoms that can indicate that a preactivation did not work properly, because of a mismatch.
byte-compile
is included in the value of features
even
though you did not ever explicitly use the byte-compiler.
Compiled preactivated advice works properly even if the function itself is not defined until later; however, the function needs to be defined when you compile the preactivated advice.
There is no elegant way to find out why preactivated advice is not being
used. What you can do is to trace the function
ad-cache-id-verification-code
(with the function
trace-function-background
) before the advised function's advice
is activated. After activation, check the value returned by
ad-cache-id-verification-code
for that function: verified
means that the preactivated advice was used, while other values give
some information about why they were considered inappropriate.
Warning: There is one known case that can make preactivation fail, in that a preconstructed combined definition is used even though it fails to match the current state of advice. This can happen when two packages define different pieces of advice with the same name, in the same class, for the same function. But you should avoid that anyway.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
The simplest way to access the arguments of an advised function in the body of a piece of advice is to use the same names that the function definition uses. To do this, you need to know the names of the argument variables of the original function.
While this simple method is sufficient in many cases, it has a disadvantage: it is not robust, because it hard-codes the argument names into the advice. If the definition of the original function changes, the advice might break.
Another method is to specify an argument list in the advice itself. This avoids the need to know the original function definition's argument names, but it has a limitation: all the advice on any particular function must use the same argument list, because the argument list actually used for all the advice comes from the first piece of advice for that function.
A more robust method is to use macros that are translated into the proper access forms at activation time, i.e., when constructing the advised definition. Access macros access actual arguments by position regardless of how these actual arguments get distributed onto the argument variables of a function. This is robust because in Emacs Lisp the meaning of an argument is strictly determined by its position in the argument list.
Now an example. Suppose the function foo
is defined as
(defun foo (x y &optional z &rest r) ...) |
and is then called with
(foo 0 1 2 3 4 5 6) |
which means that x is 0, y is 1, z is 2 and r is
(3 4 5 6)
within the body of foo
. Here is what
ad-get-arg
and ad-get-args
return in this case:
(ad-get-arg 0) => 0 (ad-get-arg 1) => 1 (ad-get-arg 2) => 2 (ad-get-arg 3) => 3 (ad-get-args 2) => (2 3 4 5 6) (ad-get-args 4) => (4 5 6) |
Setting arguments also makes sense in this example:
(ad-set-arg 5 "five") |
has the effect of changing the sixth argument to "five"
. If this
happens in advice executed before the body of foo
is run, then
r will be (3 4 "five" 6)
within that body.
Here is an example of setting a tail of the argument list:
(ad-set-args 0 '(5 4 3 2 1 0)) |
If this happens in advice executed before the body of foo
is run,
then within that body, x will be 5, y will be 4, z
will be 3, and r will be (2 1 0)
inside the body of
foo
.
These argument constructs are not really implemented as Lisp macros. Instead they are implemented specially by the advice mechanism.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
When the advice facility constructs the combined definition, it needs
to know the argument list of the original function. This is not always
possible for primitive functions. When advice cannot determine the
argument list, it uses (&rest ad-subr-args)
, which always works
but is inefficient because it constructs a list of the argument values.
You can use ad-define-subr-args
to declare the proper argument
names for a primitive function:
For example,
(ad-define-subr-args 'fset '(sym newdef)) |
specifies the argument list for the function fset
.
[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
Suppose that a function has n pieces of before-advice (numbered from 0 through n-1), m pieces of around-advice and k pieces of after-advice. Assuming no piece of advice is protected, the combined definition produced to implement the advice for a function looks like this:
(lambda arglist [ [advised-docstring] [(interactive ...)] ] (let (ad-return-value) before-0-body-form... .... before-n-1-body-form... around-0-body-form... around-1-body-form... .... around-m-1-body-form... (setq ad-return-value apply original definition to arglist) end-of-around-m-1-body-form... .... end-of-around-1-body-form... end-of-around-0-body-form... after-0-body-form... .... after-k-1-body-form... ad-return-value)) |
Macros are redefined as macros, which means adding macro
to
the beginning of the combined definition.
The interactive form is present if the original function or some piece
of advice specifies one. When an interactive primitive function is
advised, advice uses a special method: it calls the primitive with
call-interactively
so that it will read its own arguments.
In this case, the advice cannot access the arguments.
The body forms of the various advice in each class are assembled according to their specified order. The forms of around-advice l are included in one of the forms of around-advice l - 1.
The innermost part of the around advice onion is
apply original definition to arglist |
whose form depends on the type of the original function. The variable
ad-return-value
is set to whatever this returns. The variable is
visible to all pieces of advice, which can access and modify it before
it is actually returned from the advised function.
The semantic structure of advised functions that contain protected
pieces of advice is the same. The only difference is that
unwind-protect
forms ensure that the protected advice gets
executed even if some previous piece of advice had an error or a
non-local exit. If any around-advice is protected, then the whole
around-advice onion is protected as a result.
[ << ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |