• Aucun résultat trouvé

Tissage de plusieurs aspects

(proceed :call baz :popp :•, X

∪callfoo :ǫ)

→ (callfoo :pushp(callfoo) :call baz :popp :•, X

∪ǫ)

(pushp(callfoo) :call baz :popp :•, X′′

∪ǫ)

(call baz :popp :•, X′′

∪callfoo :ǫ) → (popp :•, X′′′ ∪callfoo :ǫ) → (ǫ:•, X′′′ ∪ǫ)

Lorsque l’appel à foo est filtré par l’aspect Σψ, il est tagué et placé au sommet de la pile proceed. Puis, l’instruction test φsuivie de popp le remplace au sommet de la continuation.

test φse réduit en une séquence d’instructions qui correspond au code de l’action deΣψ. Ces instructions exécutent un appel à bar suivi deproceed et un appel à baz. A l’exécution de

proceed, l’instruction au sommet de la pile proceedc.-à-d.,l’appel àfoo est exécuté. A la fin de l’exécution de l’action, l’instructionpoppvide la pile proceed.

Les règles ci-dessus supposent qu’un aspect around peut être filtré par un autre aspect

around. Cela est aussi le cas dans AspectJ. Dans les langages où cela n’est pas possible, on ne peut jamais avoir pendant l’exécution d’une action des proceed appartenant à des aspects différents et la règle PROCEEDdoit être modifiée de telle sorte que le sommet de la pile proceed ne soit pas retiré et replacé à chaque proceed. Notre cadre est plus général que celui d’AspectJ. Par exemple, nos règles, permettent de filtrer tout type d’instruction, ce qui n’est pas le cas d’AspectJ qui lui, ne peut filtrer que les accès en écriture ou en lecture des variables, des appels de méthode et la capture des exceptions.

2.4 Tissage de plusieurs aspects

Nous considérons maintenant le tissage de plusieurs aspects au même point de jonction. Dans un premier temps, nous allons présenter le tissage de plusieurs aspects de même type ( c.-à-d.,before,afterouaround). Ensuite, nous présenterons le tissage de plusieurs aspects de types différents.

2.4.1 Aspects de même type

Plusieurs aspects de même type sont représentés par l’aspect Σψ qui insère plusieurs fonc-tionsφ1. . . φnreprésentant les actions des aspects. L’ordre d’exécution des actions est celui de l’insertion des fonctions qui est déterminé parΣψ.

Aspectsbefore

Lorsquenaspectsbeforefiltrent une instructioni, leurs actions représentées parφ1. . . φn

sont exécutées avant la réduction de i. Comme dans le cas d’un seul aspect,Σψ tague ipour l’empêcher d’être à nouveau filtrée et insère les fonctions correspondant aux actions.

Σψ(i:C,Σ) = (test φ1 :. . .:test φn:i:C,Σ)

Aspectsafter

Lorsquenaspectsafterfiltrent une instructioni, leurs actions représentées parφ1. . . φn

sont exécutées après la réduction dei. L’aspectΣψ insère alors les fonctions des actions après l’instruction taguéei.

Σψ(i:C,Σ) = (i:test φ1 :. . .:test φn:C,Σ)

Aspectsaround

Lorsqu’une instruction est filtrée par plusieurs aspects around, Σψ insère la fonction de l’action du premier aspect au sommet du code à exécuter et place les fonctions des autres actions ainsi que l’instruction filtrée sur la pile proceed. Comme dans le cas d’un seul aspect, une action peut avoir 0, 1 ou plusieurs proceed. Si n actions (a1, . . . , an) s’appliquent autour d’une instructioniet si chaque action est de la formea

i :proceed:a′′

i alors l’exécution des actions sera de la forme

a1 →a2 →. . .→an →i→a′′n→. . .→a′′2 →a′′1

Dans le cas où certaines actions ont plusieurs ou zéroproceed, l’exécution est moins intuitive. Ainsi, si nous remplaçonsa1 para

1 :proceed:a′′ 1 :proceed :a′′′ 1 l’exécution sera a1 →. . .→an→i→a′′n. . . a′′2 →a′′1 →a2. . .→an→i→a′′n. . . a′′2 →a′′′1 qui devient a 1 →a2 →a′′ 1 →a2 →a′′′ 1 sia2n’a pas deproceed.

Donc Σψ insère la fonction de la première action au sommet du code à exécuter ; cette fonction est suivie depoppnqui va retirer les fonctions des autres actions et l’instruction filtrée de la pile proceed à la fin de l’exécution des aspects. La règle PROCEED* exécute la prochaine actionc.-à-d.,l’instruction placée au sommet de la pile proceed. Comme dans le cas d’un seul aspect, si l’instruction à exécuter est une action, il pourrait exécuter l’instruction qui est sommet de la pile proceed par l’intermédiaire de l’instruction proceed. Une fois cette instruction exécutée, elle est replacée dans la pile proceed car elle pourrait être ré-exécutée par une autre occurrence de la même actionproceed. L’instructionpopp (Règle POP*) termine l’exécution des actions en retirant de la pile proceed lesn premiers éléments correspondant aux fonctions des actions et l’instruction filtrée.

Σψ(i:C, X ∪ΣP) = (test φ1 :popp n:C, X ∪test φ2 :. . .:test φn:i: ΣP)

PROCEED* Σ P =x: ΣP (proceed:C, X ∪ΣP)→(x:pushpx:C, X ∪ΣP) POP* Σ P =x1 :. . .:xn: ΣP (popp n:C, X ∪ΣP)→(C, X ∪ΣP)

EXEMPLE7. Considérons encore le langage impératif de l’Exemple 2 (page 43) etΣψ regrou-pant deux aspects dont les actions sont représentées par φ1 etφ2. Les aspects filtrent chaque appel àfoo. Ces aspects sont ordonnés de manière à exécuterφ1 avantφ2. L’actionφ1 insère un appel àbar, puis, passe la main à φ2 (proceed deφ1). L’actionφ2 exécute l’appel àfoo

par l’intermédiaire de sonproceedavant de repasser la main àφ1qui termine son exécution avec l’appel àbaz.

∀(C,Σ =X∪ΣP). Σψ(callfoo :C, X ∪ΣP) =

(test φ1 :popp 2 :C, X ∪test φ2 :callfoo : ΣP)

φ1(Σ) = call bar;proceed;call baz

φ2(Σ) = proceed

La réduction de(start : call foo : •, X ∪ǫ)où ǫest la pile proceed vide, se déroule comme suit :

(start:callfoo :•, X∪ǫ)

→ (test φ1 :popp2 :•, X∪test φ2:callfoo:ǫ)

→ (call bar;proceed;call baz:popp2 :•, X∪test φ2:callfoo:ǫ)

(proceed:call baz:popp2 :•, X∪test φ2:callfoo:ǫ)

→ (test φ2 :pushptest φ2 :call baz:popp2 :•, X∪callfoo:ǫ)

→ (proceed:pushptest φ2:call baz:popp2 :•, X∪callfoo:ǫ)

→ (callfoo:pushpcallfoo :pushptest φ2 :call baz:popp2 :•, X∪ǫ)

(pushpcallfoo:pushptest φ2 :call baz:popp2 :•, X′′∪ǫ)

(pushptest φ2 :call baz:popp 2 :•, X′′∪callfoo:ǫ)

(call baz:popp2 :•, X′′∪test φ2:callfoo:ǫ)

(popp2 :•, X′′′∪test φ2:callfoo:ǫ)

Lorsque l’appel à foo est filtré par Σψ, il est remplacé au sommet de la continuation par l’instructiontest φ1suivie depopp 2où2est le nombre d’éléments insérés dans la pile proceed. Ces éléments sonttest φ2et l’appel àfoo. L’exécution detest φ1permet d’exécuter l’actionφ1

qui commence par l’appel àbar. A l’exécution deproceed, l’instruction qui est au sommet de la pile proceedc.-à-d., test φ2 est exécutée. Cette exécution permet d’exécuter l’actionφ2. Celle-ci est une instructionproceedqui va exécuter l’appel àfoo avant de passer la main à la suite de φ1 (l’appel àbaz). L’instructionpopp 2termine l’exécution des actions en retirant

test φ2 etcallfoo de la pile proceed.

2.4.2 Aspectsbefore, afteretaround

Nous traitons le cas où plusieurs aspects différentsbefore,afteretaroundfiltrent un même point de jonction par une transformation des aspectsbeforeetafterenaround. Les actions de ces aspects sont transformées en des actions d’aspect de typearounden utilisant la fonctiontoarounddéfinie comme suit :

toaround(φbefore) = λΣ.(test φbefore :proceed)

toaround(φafter) = λΣ.(proceed :test φafter)

L’action d’un aspect before est transformée en une action around en insérant l’action

before(c.-à-d.,test φbefore) suivie deproceed qui exécutera le prochain aspect ou l’ins-truction filtrée. De même, l’actionafter est transformée enaroundqui exécutera l’action

afteraprès l’exécution du prochain aspect ou de l’instruction filtrée. La fonctionφ, prenant en paramètre un état, notre transformation commence parλΣ. Ainsi, test φbefore utilise l’état courant au moment de la transformation tandis quetest φafter utilise l’état obtenu après l’exécu-tion des autres aspects ou de l’instrucl’exécu-tion filtrée (c.-à-d.,proceed). La fonctionΣψ a donc la même définition que dans le cas de plusieurs aspects de typearound; sauf qu’ici, elle appelle préalablement la fonctiontoaround.

Σψ(i:C, X ∪ΣP) = (test φ 1 :poppn :C, X ∪test φ 2 :. . .:test φ n :i: ΣP) avec φ 1 =toaround(φ1). . . φ n=toaround(φn)