• Aucun résultat trouvé

Le principe de la sémantique dénotationnelle est de s’appuyer sur un forma- lisme rigoureusement (i.e. mathématiquement) défini pour exprimer la sémantique d’un langage donné [Mos90,GS90]. Une traduction des concepts du langage d’ori- gine est alors réalisée vers ce formalisme. C’est cette traduction qui donne la sé- mantique du langage d’origine.

Dans le cadre de l’IDM, il s’agit d’exprimer des transformations vers un autre espace technique [FEB06], c’est-à-dire définir un pont entre les espaces techniques source et cible. On parle ainsi de sémantique par traduction [CESW04]. Ces ponts technologiques permettent ainsi d’utiliser les outils de simulation, de vérification et d’exécution fournis par l’espace technique cible.

4.3. SÉMANTIQUE PAR TRADUCTION : EXPÉRIMENTATIONS 69 Node name: EString Transition Place marking: EInt PetriNet name: EString Arc weight: EInt kind: ArcKind <<enumeration>> ArcKind normal readArc 1 source 1 target outgoings 0..* 0..* incomings nodes 0..* arcs 0..*

FIGURE4.4: Syntaxe abstraite des réseaux de Petri

Afin d’illustrer cette approche, nous présentons dans cette partie une traduction des concepts de SIMPLEPDL vers les réseaux de Petri. Nous détaillons les réseaux de Petri temporels à priorités (concepts, sémantique et outils) dans le chapitre 6. Nous proposons toutefois dans la figure4.4une syntaxe abstraite très simple uti- lisée dans les expérimentations suivantes. Un réseau de Petri (PetriNet) est com- posé de noeuds (Node) pouvant être des places (Place) ou des transitions (Transi- tion). Les noeuds sont reliés par des arcs (Arc) pouvant être des arcs normaux ou des read-arcs (ArcKind). Le poids d’un arc (weight) indique le nombre de jetons consommés dans la place source ou ajoutés à la place destination (sauf dans le cas d’un read-arc où il s’agit simplement de tester la présence dans la place source du nombre de jetons correspondant au poids). Le marquage du réseau de Petri est capturé par l’attribut marking d’une place.

Le schéma de traduction pour transformer un modèle de processus en un mo- dèle de réseau de Petri est présenté sur la figure 4.5. Un exemple de modèle de procédé et de réseau de Petri correspondant est donné sur la figure4.6. La trans- formation correspondante est écrite en ATL et est détaillée dans un « Use Case » que nous avons publié sur le site officiel Eclipse d’ATL13. Elle comprend trois règles déclaratives (cf. listing4.5). La première traduit chaque activité en quatre places caractérisant son état (NotStarted, Started, InProgress et Finished) et deux transitions (Start et Finish). L’état Started permet de mémoriser qu’une activité a démarré.

Ces places et transitions sont utilisées dans la deuxième règle pour traduire chaque WorkSequence en un read-arc entre une place de l’activité source et une transition de l’activité cible, la place et la transition dépendant de la valeur de l’attribut kind.

La dernière règle traduit un Process en un PetriNet regroupant les nœuds et arcs construits par les autres règles.

FIGURE4.5: Schéma de traduction de SIMPLEPDL vers PETRINET

4.3. SÉMANTIQUE PAR TRADUCTION : EXPÉRIMENTATIONS 71

Listing 4.5: Extrait de la transformation ATL de SIMPLEPDL vers PETRINET

module SimplePDL2PetriNet;

create OUT: PetriNet from IN: SimplePDL; rule WorkDefinition2PetriNet {

from wd: SimplePDL!WorkDefinition to

−− création des places

p_notStarted : PetriNet ! Place (name <− wd.name + ’_notStarted’, marking <− 1), p_started : PetriNet ! Place (name <− wd.name + ’_started’, marking <− 0), p_inProgress : PetriNet ! Place (name <− wd.name + ’_inProgress’, marking <− 0), p_finished : PetriNet ! Place (name <− wd.name + ’_finished’, marking <− 0), −− création des transitions

t_start : PetriNet ! Transition (name <− wd.name + ’_start’), t_finish : PetriNet ! Transition (name <− wd.name + ’_finish’), −− création des arcs :

a_nsed2s : PetriNet !Arc (kind <− #normal, weight <− 1,

source <− p_notStarted , target <− t_start ), ...

}

rule WorkSequence2PetriNet { from ws: SimplePDL!WorkSequence to

a_ws: PetriNet !Arc (kind <− #read_arc, weight <− 1, source <−

if (( ws.kind = # finishToStart ) or (ws.kind = # finishToFinish )) then thisModule.resolveTemp(ws.predecessor , ’ p_finished ’ )

else thisModule.resolveTemp(ws.predecessor , ’ p_started ’ ) endif ,

target <−

if (( ws.kind = # finishToStart ) or (ws.kind = # startToStart )) then thisModule.resolveTemp(ws.successor , ’ t_start ’ ) else thisModule.resolveTemp(ws.successor , ’ t_finish ’ ) endif )

}

rule Process2PetriNet { from p: SimplePDL!Process

to pn: PetriNet ! PetriNet (nodes <− ..., arcs <− ...) }

La définition d’une transformation explicite est ici un point positif. En effet, si le schéma de traduction de SIMPLEPDL vers les réseaux de Petri est relativement simple, il nécessite de construire de nombreux motifs répétitifs correspondant à la modélisation d’une activité, d’une précédence, etc. Ces correspondances sont définies sous la forme de règles ATL qui seront automatiquement appliquées sur tous les éléments du modèle SIMPLEPDL en entrée de la transformation.

Le code ATL est cependant compliqué car nous n’avons pas une correspon- dance exacte (c.-à-d. un à un) entre les concepts du métamodèle d’entrée et ceux du métamodèle de sortie. Par exemple, une activité est traduite par quatre places et deux transitions. Il faut alors définir une convention pour nommer les états (et les transitions). D’autre part, lorsque l’on veut traduire la relation de précédence, on ne peut pas utiliser la simple affectation d’ATL mais nous devons passer par l’opérateur resolveTemp pour retrouver la place de l’activité source et la transi- tion de l’activité cible qui devront être reliées par un read-arc. Cette place et cette transition dépendent du type de précédence.

Afin de maîtriser la complexité pour définir une sémantique par traduction et prendre plus facilement en compte l’évolution de la définition d’un langage, Clee- newerck et al. [CK07] préconisent de séparer les préoccupations. Ils définissent pour cela la notion de module logiciel correspondant à des constructions du langage pour lesquelles la sémantique par traduction est définie. Les différentes construc- tions (préoccupations) peuvent ensuite être assemblées de manière à définir la sé- mantique du DSML complet.

Gurevich et al. [Gur01] a le même objectif mais avec une approche différente qui consiste à définir des unités formelles dans le langage cible. En utilisant le lan- gage de transformation GReAT (Graph Rewriting And Transformation language) [AKK+05], ils proposent un ancrage sémantique (Semantic Anchoring) d’unités formelles définies à l’aide d’ASM (Abstract State Machine) [Gur01].

Enfin, notons que les techniques de sémantique par traduction ont également été utilisées dans le groupe pUML14, sous le nom de Denotational Meta Modeling, pour la formalisation de certains diagrammes d’UML [CEK01].