Vous êtes sur la page 1sur 4

Universite de Bretagne Occidentale.

Master Informatique 1ere annee

Bison
compilateur C <nom>.tab.c cc <>.tab.c -ly a.out

bison

est un programme GNU qui construit un analyseur LALR en C a partir de regles de traduction (grammaire) contenues dans un chier de speci cations Bison..
compilateur specifications bison <nom>.y bison <nom>.y bison

1. Structure du chier de speci cations Bison

%f declarations C : inclusions de chiers, variables, : : : %g declarations Bison : unites lexicales, priorites, : : : %% regles de traductions et actions semantiques %% routines C

Partie Ia (facultative) Partie Ib Partie II Partie III (facultative)

2. Declaration des unites lexicales


Exemples :
%token unite-lexicale %token NOMBRE %token IF

La declaration d'une unite lexicale se fait dans la partie Ib par l'instruction

3. Les regles de traductions et les actions semantiques (Partie II)


Les regles de production <non-terminal> !<prod1> j <prod2> j : : : j < prodn> seront ecrite dans la partie II sous la forme :
non-terminal : | | prod1 prod2 ... prodn

Les symboles terminaux sont : tout caractere entre apostrophes ou toute chaine entre guillemets (ex : '+' "<="). Les symboles non-terminaux sont : toute chaine de lettres et de chi res non entouree d'apostrophes ou de guillemets et non declaree comme unite lexicale.

Les actions semantiques sont des instructions C inserees dans les regles de traduction. Elles sont executees chaque fois qu'il y a reduction par la production associee. 1

Exemples :

fprintf("mot reconnu") g S : A fprintf("reduction par A") g T fprintf("reduction par T") g 'a'


S : A T 'a'

4. Les attributs

A chaque symbole (terminal ou non) est associe une valeur (de type entier par defaut). Cette valeur peut ^tre utilisee dans les actions semantiques (comme un attribut synthetise). e Le symbole $$ reference la valeur de l'attribut associe au non-terminal de la partie gauche, tandis que $i reference la valeur associee au i-eme symbole (terminal ou non-terminal) ou action semantique de la partie droite. Exemple :
expr : expr '+' expr

5. Communication avec l'analyseur lexical

f tmp=$1+$3 g '+' expr f $$=tmp+$6 g

La partie III doit contenir une fonction yylex() e ectuant une analyse lexicale des caracteres en entree. On peut soit ecrire cette fonction soit utiliser la fonction produite par un compilateur (f)lex applique a un chier de speci cations (f)lex. Dans ce cas, il su ra d'inclure le chier lex.yy.c et de rajouter la bibliotheque (f)lex lors de la compilation C du chier .tab.c (cc <...>.tab.c -ly -l(f)l). Recuperation des unites lexicales et de leur valeur : Dans une action lexicale, l'instruction return <unite> permet de renvoyer a l'analyseur syntaxique l'unite lexicale <unite>. La valeur de cette unite lexicale peut ^tre communiqueea l'analyseur syntaxique par l'intermediaire e de la variable yylval (de type int par defaut) prede nie par Bison.

6. Typage de yylval et des non-terminaux

La variable yylval est de type YYSTYPE (declare dans la bibliotheque Bison), qui est par defaut un entier. On peut changer ce type par defaut en mettant (dans la partie Ib) %define YYSTYPE autre-type-C L'instruction (dans la partie Ib) a pour e et de declarer YYSTYPE comme etant une telle union. Par exemple, la declaration
%union { int entier double reel char * chaine } %union /* champs d'une union C */

permet de stocker dans exemple


{entier}

yylval

des

int double

ou

char*

. L'analyseur lexical contiendra par

{ sscanf(yytext,"%d",&yylval.entier) return ENTIER }

Le type des lexemes peut alors ^tre precise en utilisant les noms des champs de l'union e
%token <entier> ENTIER %token <reel> REEL %token <chaine> IDENT CHAINE COMMENT

Le type des non-terminaux peut ^tre precise en partie Ib par e %type <champ de l'union> non-terminal Ceci permet d'associer une valeur (de type identique a l'un des champs de l'union YYSTYPE) a un non-terminal.

7. Options de compilations Bison

l'option -v produit un chier <nom>.output contenant un descriptif des con its shift/reduce et reduce/reduce detectes et indique de quelle facon ils ont ete resolus. Il est fortement conseille de consulter ce chier a n de veri er que les con its sont resolus comme on le desire. l'option -d produit un chier <nom>.tab.h contenant les de nitions (sous forme de #define) des unites lexicales rencontrees et du type YYSTYPE s'il est rede ni. (dans la partie Ib) permet de de nir un axiome de depart (par faut c'est le non-terminal de la premiere regle de traduction decrite) main(),yyparse() le compilateur Bison cree un main minimal qui appelle l'analyseur syntaxique yyparse() cree. Ce main peut ^tre reecrit par l'utilisateur e dans la partie III.
%start axiome

8. Divers

9. Con its shift/reduce et reduce/reduce

Lorsque le compilateur bison est confronte a des con its (par exemple lorsque la grammaire decrite est ambigue), il rend compte du type et du nombre de con its rencontres : Les con its sont resolus de la maniere suivante : con it reduce/reduce : la production choisie est celle apparaissant en premier dans la speci cation. con it shift/reduce : c'est le shift qui est e ectue L'instruction %expect n ou n est un entier indique au compilateur Bison de ne signaler les con its que s'il y en a plus de n.
> bison exemple.y conflicts: 6 shift/reduce, 2 reduce/reduce

Rappel : Bison est un analyseur LALR. Par consequent, si la grammaire est LR(1) mais non
LALR, il y aura forcemment des con its (reduce/reduce en general).

10. Associativite et priorite des symboles terminaux


Les declarations suivantes (en partie Ib)
%left term1 %right term2 %nonassoc term3

On peut changer la facon de resoudre les con its (ou tout du moins emp^cher leur apparition) en e donnant des associativites (droite ou gauche) et des priorites aux symboles terminaux.

indiquent que le symbole terminal term1 est associatif a gauche, term2 est associatif a droite, alors que term3 n'est pas associatif. On peut mettre plusieurs symboles terminaux dans une m^me declaration d'associativite (par e exemple %left PLUS MOINS), ils auront alors la m^me priorite. Sinon, les priorites des symboles e sont donnees par l'ordre dans lequel apparait leur declaration d'associativite, les premiers ayant la plus faible priorite. La priorite (ainsi que l'associativite) d'une production est de nie comme etant celle de son terminal le plus a droite. On peut forcer la priorite d'une production en faisant suivre la production de la declaration ce qui a pour e et de donner comme priorite (et comme associativite) a la production celle du terminal-ou-unite-lexicale (ce terminal-ou-unite-lexicale devant ^tre de ni, m^me de maniere face e tice, dans la partie Ib). Un con it shift/reduce, i.e. un choix entre entre une reduction A ! et un decallage d'un symbole d'entree a, est alors resolu en appliquant les regles suivantes : si la priorite de la production A ! est superieure a celle de a, c'est la reduction qui est e ectuee si les priorites sont les m^mes et si la production est associative a gauche, c'est la reduction e qui est e ectuee dans les autres cas, c'est le shift qui est e ectue.
%prec terminal-ou-unite-lexicale

Rappel : il est fortement conseille de consulter le chier .output 11. Recuperation des erreurs

Lorsque l'analyseur produit par bison rencontre une erreur, il appelle par defaut la fonction yyerror(char *) qui se contente d'a cher le message parse error, puis il s'arr^te. Cette fonce tion peut ^tre rede nie par l'utilisateur. e Il est possible de traiter de maniere plus explicite les erreurs en utilisant le mot cle bison error. On peut rajouter dans toute production de la forme A ! Dans ce cas, une production d'erreur sera traitee comme une production classique. On pourra donc lui associer une action semantique contenant un message d'erreur. Des qu'une erreur est rencontree, tous les caracteres sont avales jusqu'a rencontrer le caractere correspondant a . Exemple : La production instr! error indique a l'analyseur qu'a la vue d'une erreur, il doit sauter jusqu'au dela du prochain " " et supposer qu'une instr vient d'^tre reconnue. e La routine yyerrok replace l'analyseur dans le mode normal de fonctionnement c'est a dire que l'analyse syntaxique n'est pas interrompue. 4

A ! error

j j : : : une production
2

Vous aimerez peut-être aussi