Réseaux de Capteurs Sans Fils
CoursOutils transverses

Application Blink

Aperçus général

Le programme "Blink" se trouve à apps/Blink dans l'arbre de TinyOS. Cette application allume la LED rouge à une fréquence de 1HZ.

L'application Blink est composée de deux composants: un module, appelé "BlinkM.nc", et une configuration, appelée "Blink.nc". Blink.nc est utilisée pour relier le module BlinkM.nc à d'autres composants requis par l'application Blink.

La raison pour laquelle on distingue les modules des configurations est de permettre au concepteurs d'un système de construire des applications rapidement et efficacement. Par exemple, un concepteur pourrait fournir uniquement une configuration qui relie un ensemble de modules qu'il ne développe pas lui même. De même, un autre développeur peut fournir une libraire d'un ensemle de modules qui peut être utilisés dans la construction d'autres applications.

Convention de nommage

Parfois (et c'est le cas de BlinkM et Blink) vous aurez un module et une configuration qui vont ensemble. Quand c'est le cas, la convention utilisée dans l'arbre des codes sources de TinyOS est que Foo.nc représentes la configuration et FooM.nc représente le module correspondant.

La configuration Blink.nc

Le compilateur nesC, ncc, compile une application nesC à partir de sa configuration. Une application nesC typique est fournie avec un fichier Makefile standard qui permet de sélectionner la plateforme d'exécution de l'application (type de mote, pc, etc.) et invoque ncc, avec les options appropriées, sur la configuration de l'application. Examinons maintenant la configuration Blink.nc de notre application :

Blink.nc Configuration
Blink.nc Configuration

Dans les deux premières lignes, le mot clé "configuration" indique qu'il s'agit d'une configuration appelé "Blink".

Entre les deux accolades (vides ici) il est possible de spécifier des interfaces fournies et/ou utilisées par la configuration.

La configuration est implémentée entre les accolades suivants le mot clé "implementation".

La ligne "components" spécifies l'ensemble de composants référencés par cette configuration : Main, BlinkM, SingleTimer, LedsC. La suite de l'implémentation relie les interfaces utilisées par des composants aux interfaces fournies par les autres composants.

Le composant Main

Main est le composant exécuté en premier lieu dans une application TinyOS. Précisément, la commande Main.StdControl.init() est la première commande exécutée dans TinyOS suivie par la commande Main.StdControl.start(). Donc, une application TinyOS doit obligatoirement avoir un composant Main dans sa configuration. StdControl est une interface commune utilisée pour initialiser et lancer les composants TinyOS. examinons cette interface qui se trouve à tos/interfaces/StdControl.nc:

L'interface StdControl.nc
L'interface StdControl.nc

Nous remarquons que StdControl définie trois commandes : init(), start(), et stop(). init() est appelé quand le composant est initialisé pour la première fois, et start() quand ison exécution est lancée la première fois. stop() est appelé quand le composant est arrêté, par exemple pour éteindre le composant qu'il contrôle.

Le "wiring"

nesC utilise des flèches pour déterminer la liaison entre interfaces. Il lire la flèche vers la droite (->) "est liée à". Le côté gauche de la flèche relie une interface à son implémentation fournie par le côté droit de la flèche. En d'autres mots, le composant qui utilise une interface est du côté gauche de la flèche, et le composant qui fournie une implémentation de l'interface se trouve à droite de la flèche. La ligne

BlinkM.Timer -> SingleTimer.Timer;

est to utilisée pour relier l'interface Timer utilisée par BlinkM à l'interface Timer implémentée par SingleTimer. Le "wiring" peut aussi être implicite. Par exemple,

BlinkM.Leds -> LedsC;

est une abréviation pour

BlinkM.Leds -> LedsC.Leds;

Si aucun nom d'interface n'est donné au côté droit de la flèche, le compilateur nesC essaye par défaut de relier à la même interface du côté gauche de l'interface.

Le module BlinkM.nc

Considérons le module BlinkM.nc :

Le module BlinkM.nc
Le module BlinkM.nc

La première partie du code signifie qu'il s'agit d'un module appelé BlinkM, et décalre les interfaces qu'il utilise et fournie. Le module BlinkM fournie l'interface StdControl. ceci veut dire que BlinkM implémente l'interface StdControl. Comme expliqué ci-dessus, ceci est nécessaire pour initialiser et lancer l'exécution du composant Blink. Le module BlinkM utilise deux interfaces : Leds et Timer. Ceci veut dire que BlinkM peut faire appel à toutes les commandes déclarées dans ces deux interfaces et doit aussi implémenter tous les événements déclarés dans ces interfaces qu'il utilise. L'interface Leds définie plusieurs commandes comme redOn(),redOff(), etc., qui allument et éteignent les différents LEDs (rouge, vert, jaune) du capteur.

Cependnat, Leds est juste une interface : l'implémentation est spécifiée dans la configuration Blink.nc.

Timer

Considérons l'interface Timer.nc

L'interface Timer.nc
L'interface Timer.nc

On remarque que l'interface Timer définie les commandes start() et stop(), l'événement fired(). La commande start() est utilisée pour spécifier le type du timer et l'intervalle de temps au bout duquel le Timer expire. L'unité de l'argument interval est la milliseconde. Les types valides sont TIMER_REPEAT (le Timer se déclenche après chaque periode de "interval" de temps jusqu'à sont arrêt avec stop()), et TIMER_ONE_SHOT (le Timer se déclenche une seule fois après l'expiration du délai "interval"). Comment est ce qu'une application apprend l'expiration d'un Timer ? La réponse est lorsqu'elle reçois l'événement "expired()". L'interface Timer fournie un événement:

event result_t fired();

un événement est une fonction que l'implémentation de l'interface signale quand un certain événement apparaît. dans notre cas, l'événement "fired()" est signalé quand l'intervalle de temps spécifié en argument est passé. Ceci est un exemple d'une interface bidirectionnelle : une interface non seulement fournie des commandes qui peuvent être appelé par les composants utilisant l'interface, mais aussi signale des événements qui font appel à des handlers dans le composant qui utilisent l'interface. Un module qui utilise une interface doit implémenter les événement signalés par cette interface.

Considérons maintenant la suite du module BlinkL.nc :

Suite module BlinkM.nc
Suite module BlinkM.nc

Comme on peut le voir facilement, le module BlinkM implémente les commandes StdControl.init(), StdControl.start(), et StdControl.stop(), puisqu'il fournie l'interface StdControl. Il implémente également l'événement Timer.fired(), qui est nécessaire puisque BlinkM doit implémenter les événement signalés par une interface qu'il utilise. La commande init() initialise simplement le composant Leds en appelant Leds.init(). La commande start() invoque Timer.start() pour créer le Timer répétitif (REPEAT TIMER) qui expire à chaque 1000 ms. stop() arrête le Timer. A chaque fois que l'événement Timer.fired() est signalé, la commande Leds.redToggle() permet d'allumer la diode rouge.

Compilation et exécution de BlinkTinyOS : Concepts et définitions
Accueil Yacine CHALLAL creativecommons : by-ncRéalisé avec SCENARI