0
votes

I've been looking for answers for my question, but no-one solves my problem.

This is my really simple Yacc file:

%{
#include <stdio.h>
#include "y.tab.h"

int clientesVodafone = 0;
int clientesMovistar = 0;
float sumaVodafone = 0.0;
float sumaMovistar = 0.0;
%}


%union {
    int t0;
    float cm;
};

%token NUMEROTELEFONO OPERADORA SERVICIO COSTEMENSAJE
%type <t0> OPERADORA
%type <cm> COSTEMENSAJE

%start fichero
%%

ServicioSMS: NUMEROTELEFONO OPERADORA SERVICIO COSTEMENSAJE {
                if ($2.t0 == 0) {
                    clientesMovistar++;
                    sumaMovistar += $4.cm;
                } else {
                    clientesVodafone++;
                    sumaVodafone += $4.cm;
                }
            }

fichero: ServicioSMS
fichero: fichero ServicioSMS

%%

int main(void) {
  yyparse();
  printf("%i clientes de VODAFONE con coste %f euros.", 
        clientesVodafone, sumaVodafone);
  printf("%i clientes de MOVISTAR con coste %f euros.",
        clientesMovistar, sumaMovistar);
}

And this is my Lex file:

%{
#include <stdio.h>
#include "y.tab.h"
%} 

%% 

6[0-9]{8}           {return NUMEROTELEFONO;}
MOVISTAR            {yylval.t0 = 0; return OPERADORA;}
VODAFONE            {yylval.t0 = 1; return OPERADORA;}
[0-9]+s             {return SERVICIO;}
[0-9]*\.[0-9]+      {yylval.cm = atof(yytext); return COSTEMENSAJE;}

%% 

When I compile, I get the famous error message: "error: request for member 't0' in something not a structure or union". I also obtain the same error with member 'cm'. They are associated to yyparse(), in lines:

 if ($2.t0 == 0) {
     clientesMovistar++;
     sumaMovistar += $4.cm;
 } else {
     clientesVodafone++;
 sumaVodafone += $4.cm;
 }

I use Bison and Flex and compile with: "bison -d -y example.y", "flex example.l", and "gcc lex.yy.c y.tab.c -ll -lm".

Thank you.

1

1 Answers

2
votes

Why do you have $2.t0 and $4.cm instead of just $2 and $4 ?

The %type <t0> OPERADORA statement tells Bison that the OPERADORA value is carried in the t0 member of the union, so the expression that Bison uses to replace $2 in the final code generated for the ServicioSMS action definition will automatically refer to that t0 member. Your $2.t0 will therefore end up as <union>.t0.t0 which is an error. You should be able to see this if you examine the lex.yy.c file that was produced by Bison.

Similarly for $4.cm, which will end up as <union>.cm.cm, another error.

So, remove those extraneous .t0 and .cm suffixes in the Bison file's ServicioSMS action definition and then run a fresh build.