Info Indus FICHE ii n°3 La pile et fonctions J.-O.KLEIN IUT CACHAN A vant dʼêtre une partie de la mémoire dʼun ordinateur, une pile (angl. stack) est dʼabord un objet abstrait. Cʼest une structure de données à accès séquentielle dans laquelle la dernière donnée écrite est la première relue. On parle de structure de donnée LIFO (Last In First Out) ou de pile par opposition aux structures de données FIFO (First In First Out) ou files dʼattente ou tampons. Lʼimage de la pile rappelle la pile dʼassiette. On y prend toujours lʼassiette du dessus (sommet de la pile, angl. top of stack) qui est aussi la dernière posée. Dans un ordinateur, la pile sert de mémoire temporaire. Tous les CPU (à lʼexception notable de la famille PIC de Microchip) comportent un registre pointeur de pile Un exemple de programme Traduction en assembleur typedef unsigned short U16; U16 ma_fonction(U16 c, U16 d); main int main(void) { U16 a,b,c; a = 10; b = 13; c = ma_fonction (a,b); return c; } U16 ma_fonction(U16 c, U16 d){ return d+c; } Adresse de retour Une fonction C et une routine assembleur sont des sous-programmes. Il sʼagit de fractions de codes exécutables prêtes à être utilisées par dʼautres fonctions, grâce à un appel de fonction C et par une instruction JSR (Jump To Subroutine) en assembleur. Lʼinstruction JSR doit bien évidemment modifier la valeur du registre PC de façon à ce que la prochaine instruction à exécuter soit la première du sous-programme, mais elle doit surtout sauvegarder quelque part lʼadresse de retour à laquelle le programme devra se poursuivre dès la : LDAB CLRA PSHD LDAB JSR C05F LEAS RTS 2,SP 1602 00 15F8 C0 15F9 5F 15FA 00 15FB 0A 15FC C0 15FD 37 15FE 00 Rév 6 14-09-04 (SP Stack Pointer) , qui pointe en permanence en mémoire sur le sommet de la pile, (cʼest à dire sur le dernier élément posé sur la pile). Les éléments déposés sur la pile sont liés aux fonctions (et aux interruptions mais nous nʼen parlerons pas encore). Il sʼagit des adresses de retour, des arguments dʼappel et des variables locales aux fonctions. Commentaires #10 #13 ma_fonction 2,SP ; SP+2->SP ma_fonction: ADDD 2,SP RTS fin du sous-programme. Lʼadresse de retour est donc sauvegardée (empilée) automatiquement dans la pile par lʼinstruction JSR. Inversement, lʼinstruction RTS (Retour de sous-programme) va récupérer (dépiler) lʼadresse de retour pour la placer dans le registre PC et reprendre la suite du programme principal. Arguments dʼappel Une fonction C est un sous-programme auquel il est possible de transmettre des valeurs appelées arguments dʼappel. A lʼintérieur de la procédure, Allure de la pile au moment de lʼexécution de lʼinstruction ADDD 2,SP dans ma_fonction SP=15F8 Pile Sommet de la pile Adresse de retour dans la fonction main = C05F Le premier argument (a=10) est est empilé (PSHD) par lʼintermédiaire du registre D pour être transmis à ma_fonction. Le deuxième argument (b=13) est transmis directement par le registre D. Lors de lʼappel de sous-programme (JSR) lʼadresse de retour (ici C05F sera empilée). Après lʼappel de la fonction, la pile est remise en état (LEAS 2,SP) avant le retour dans la routine sartup (RTS). Le premier paramètre est récupéré dans la pile, le second est déjà dans le registre D, qui sert aussi de valeur de retour. les arguments deviennent des paramètres formels. La fonction appelée doit faire correspondre ses paramètres avec les arguments qui lui ont été transmis. Pour cela, le compilateur utilise les registres autant que possible et la pile quand les registres ne suffisent plus. Les arguments sont empilés avant lʼappel de la fonction(instruction JSR) dans la fonction appelante. Les paramètres sont récupéré par la fonction appelée, par lʼintermédiaire du pointeur de pile (SP). Données temporaires En langage C, les variables locales sont automatiques par défaut (cʼest-à-dire lorsquʼelles ne sont pas précédé du mot-clé «static» lors de leur déclaration). Contrairement aux variables statiques, elles sont créées (et logiquement réinitialisées) à chaque appel de leur fonction. Ces variables peuvent utiliser les registres ou la pile lorsque lʼespace dans les registres ne suffit plus. Il en va de même lorsque lʼévaluation dʼune expression complexe nécessite de mémoriser un résultat intermédiaire. Quelques instructions HC12 Argument n°1 (=10) Adresse de retour dans la fonction startup = C037 JSR addr : Jump To Subroutine SP-2 →SP; PC → Mem[SP]; addr→PC RTS : Return From Subroutine Mem[SP] →PC; SP+2 →SP PSHD : Push D SP-2 →SP; D→ Mem[SP]; LEAS addr : Load Effective Address to SP & Mem[addr] → SP donc : LEAS 2,SP ⇔ & Mem[2+SP] → SP ⇔ SP+2→SP