Search code examples
gcccompiler-constructionbisonflex-lexer

Undefined reference to `WinMain@16' error when compile with gcc


I'm going to run a simple program constructed with Flex an Bison.

Here are my codes.

Flex file (calc.l)

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

/* %option noyywrap */
%%

[0-9]+(\.[0-9]+)?([eE][0-9]+)?  {yylval.f = atof(yytext); return NUM;}
[-+()*/]                        {return yytext[0];}
[\t\f\v\n]                      {;}

%%

int yywrap() {return -1} 

Bison file (tt.y)

%{
#include <stdio.h>
#include <stdlib.h>

extern int yylex();
void yyerror(char *msg);
%}

%{
#include <stdio.h>
#include <stdlib.h>

extern int yylex();
%}

%union {
    float f;
}

%token <f> NUM
%type <f> E T F

%%
S : E           {printf("f\n", $1);} 
  ;

E : E '+' T     {$$ = $1 + $3}
  | T           {$$ = $1;}
  ;

T : T '*' F     {$$ = $1 * $3}
  | F           {$$ = $1;}
  ;

F : '(' E ')'       {$$ = $2;}
  | '-' F           {$$ = -$2;}
  | NUM         {$$ = $1;}
%%

void yyerror(char *msg) {
    fprintf(stderr, "%s\n", msg);
    exit(1); 
}

To compile I follow follow commands in cmd.

Bison -d tt.y

Flex calc.l

gcc lex.yy.c tt.tab.c -o calc

when I run last gcc comman it got error like this.

c:/mingw/bin/../lib/gcc/mingw32/8.2.0/../../../../mingw32/bin/ld.exe: c:/mingw/bin/../lib/gcc/mingw32/8.2.0/../../../libmingw32.a(main.o):(.text.startup+0xb0): undefined reference to `WinMain@16'
collect2.exe: error: ld returned 1 exit status

What is the problem in my codes or any. Thanks for any consideration :)


Solution

  • You do not define the main function, the code generated by flex and bison do not define the main function, you have to define it by yourself else the program do not have an entry point.

    You have problems in your definitions :

    • in tt.y {printf("f\n", $1);} have a format not compatible with an argument, must be ``{printf("%f\n", $1);}` ?
    • in tt.y declare yyerror in the header with the declaration of yylex
    • in calc.l int yywrap() {return -1} must be int yywrap() {return -1;}

    The minimal main definition is :

    int main()
    {
       yyparse();
       return 0;
    }
    

    you can put it with the definition of yyerror in tt.y