title: y.tab.c: undefined reference to yylex
body: <p>I am trying to run an example I found online of a calculator. But I have this error showing every time I run my gcc command. Here are the commands that I run:</p>
  
  <pre><code>flex -l calc3.l
  yacc -vd calc3.y
  gcc y.tab.c -lm -ll
  </code></pre>
  
  <p>-> at this point I got this error message:</p>
  
  <pre><code>/tmp/ccPOq58f.o : In function 'yyparse':
  y.tab.c: undefined reference to 'yylex' 
  collect2: error: ld returned 1 exit status
  </code></pre>
  
  <p>Here is my code:</p>
  
  <p>calc3.l</p>
  
  <pre><code>%{
  #include &lt;stdlib.h&gt;
  #include "calc3.h"
  #include "y.tab.h"
  void yyerror(char *);
  %}
  
  %%
  
  [a-z]       { 
                  yylval.sIndex = *yytext - 'a';
                  return VARIABLE;
              }
  
  0           {
                  yylval.iValue = atoi(yytext);
                  return INTEGER;
              }
  
  [1-9][0-9]* {
                  yylval.iValue = atoi(yytext);
                  return INTEGER;
              }
  
  [-()&lt;&gt;=+*/;{}.] {
                  return *yytext;
               }
  
  "&gt;="            return GE;
  "&lt;="            return LE;
  "=="            return EQ;
  "!="            return NE;
  "while"         return WHILE;
  "if"            return IF;
  "else"          return ELSE;
  "print"         return PRINT;
  
  [ \t\n]+        ;       /* ignore whitespace */
  
  .               yyerror("Unknown character");
  %%
  int yywrap(void) {
      return 1;
  }
  </code></pre>
  
  <p>here is calc3.h </p>
  
  <pre><code>typedef enum { typeCon, typeId, typeOpr } nodeEnum;
  
  /* constants */
  typedef struct {
      int value;                  /* value of constant */
  } conNodeType;
  
  /* identifiers */
  typedef struct {
      int i;                      /* subscript to sym array */
  } idNodeType;
  
  /* operators */
  typedef struct {
      int oper;                   /* operator */
      int nops;                   /* number of operands */
      struct nodeTypeTag **op;    /* operands */
  } oprNodeType;
  
  typedef struct nodeTypeTag {
      nodeEnum type;              /* type of node */
  
      union {
          conNodeType con;        /* constants */
          idNodeType id;          /* identifiers */
          oprNodeType opr;        /* operators */
      };
  } nodeType;
  
  extern int sym[26];
  </code></pre>
  
  <p>and here is calc3.y</p>
  
  <pre><code>%{
  #include &lt;stdio.h&gt;
  #include &lt;stdlib.h&gt;
  #include &lt;stdarg.h&gt;
  #include "calc3.h"
  
  /* prototypes */
  nodeType *opr(int oper, int nops, ...);
  nodeType *id(int i);
  nodeType *con(int value);
  void freeNode(nodeType *p);
  int ex(nodeType *p);
  int yylex(void);
  
  void yyerror(char *s);
  int sym[26];                    /* symbol table */
  %}
  
  %union {
      int iValue;                 /* integer value */
      char sIndex;                /* symbol table index */
      nodeType *nPtr;             /* node pointer */
  };
  
  %token &lt;iValue&gt; INTEGER
  %token &lt;sIndex&gt; VARIABLE
  %token WHILE IF PRINT
  %nonassoc IFX
  %nonassoc ELSE
  
  %left GE LE EQ NE '&gt;' '&lt;'
  %left '+' '-'
  %left '*' '/'
  %nonassoc UMINUS
  
  %type &lt;nPtr&gt; stmt expr stmt_list
  
  %%
  
  program:
          function                { exit(0); }
          ;
  
  function:
            function stmt         { ex($2); freeNode($2); }
          | /* NULL */
          ;
  
  stmt:
            ';'                            { $$ = opr(';', 2, NULL, NULL); }
          | expr ';'                       { $$ = $1; }
          | PRINT expr ';'                 { $$ = opr(PRINT, 1, $2); }
          | VARIABLE '=' expr ';'          { $$ = opr('=', 2, id($1), $3); }
          | WHILE '(' expr ')' stmt        { $$ = opr(WHILE, 2, $3, $5); }
          | IF '(' expr ')' stmt %prec IFX { $$ = opr(IF, 2, $3, $5); }
          | IF '(' expr ')' stmt ELSE stmt { $$ = opr(IF, 3, $3, $5, $7); }
          | '{' stmt_list '}'              { $$ = $2; }
          ;
  
  stmt_list:
            stmt                  { $$ = $1; }
          | stmt_list stmt        { $$ = opr(';', 2, $1, $2); }
          ;
  
  expr:
            INTEGER               { $$ = con($1); }
          | VARIABLE              { $$ = id($1); }
          | '-' expr %prec UMINUS { $$ = opr(UMINUS, 1, $2); }
          | expr '+' expr         { $$ = opr('+', 2, $1, $3); }
          | expr '-' expr         { $$ = opr('-', 2, $1, $3); }
          | expr '*' expr         { $$ = opr('*', 2, $1, $3); }
          | expr '/' expr         { $$ = opr('/', 2, $1, $3); }
          | expr '&lt;' expr         { $$ = opr('&lt;', 2, $1, $3); }
          | expr '&gt;' expr         { $$ = opr('&gt;', 2, $1, $3); }
          | expr GE expr          { $$ = opr(GE, 2, $1, $3); }
          | expr LE expr          { $$ = opr(LE, 2, $1, $3); }
          | expr NE expr          { $$ = opr(NE, 2, $1, $3); }
          | expr EQ expr          { $$ = opr(EQ, 2, $1, $3); }
          | '(' expr ')'          { $$ = $2; }
          ;
  
  %%
  
  nodeType *con(int value) {
      nodeType *p;
  
      /* allocate node */
      if ((p = malloc(sizeof(nodeType))) == NULL)
          yyerror("out of memory");
  
      /* copy information */
      p-&gt;type = typeCon;
      p-&gt;con.value = value;
  
      return p;
  }
  
  nodeType *id(int i) {
      nodeType *p;
  
      /* allocate node */
      if ((p = malloc(sizeof(nodeType))) == NULL)
          yyerror("out of memory");
  
      /* copy information */
      p-&gt;type = typeId;
      p-&gt;id.i = i;
  
      return p;
  }
  
  nodeType *opr(int oper, int nops, ...) {
      va_list ap;
      nodeType *p;
      int i;
  
      /* allocate node */
      if ((p = malloc(sizeof(nodeType))) == NULL)
          yyerror("out of memory");
      if ((p-&gt;opr.op = malloc(nops * sizeof(nodeType *))) == NULL)
          yyerror("out of memory");
  
      /* copy information */
      p-&gt;type = typeOpr;
      p-&gt;opr.oper = oper;
      p-&gt;opr.nops = nops;
      va_start(ap, nops);
      for (i = 0; i &lt; nops; i++)
          p-&gt;opr.op[i] = va_arg(ap, nodeType*);
      va_end(ap);
      return p;
  }
  
  void freeNode(nodeType *p) {
      int i;
  
      if (!p) return;
      if (p-&gt;type == typeOpr) {
          for (i = 0; i &lt; p-&gt;opr.nops; i++)
              freeNode(p-&gt;opr.op[i]);
          free (p-&gt;opr.op);
      }
      free (p);
  }
  
  void yyerror(char *s) {
      fprintf(stdout, "%s\n", s);
  }
  
  int main(void) {
      yyparse();
      return 0;
  }
  </code></pre>