Referencia indefinida a yywrap

81

Tengo un "lenguaje" simple que estoy usando Flex (Lexical Analyzer), es así:

/* Just like UNIX wc */
%{
int chars = 0;
int words = 0;
int lines = 0;
%}

%%
[a-zA-Z]+ { words++; chars += strlen(yytext); }
\n        { chars++; lines++; }
.         { chars++; }
%%

int main()
{
    yylex();
    printf("%8d%8d%8d\n", lines, words, chars);
}

Ejecuté a flex count.l, todo va bien sin errores ni advertencias, luego, cuando intento hacer una cc lex.yy.c, obtuve estos errores:

ubuntu @ eeepc: ~ / Desktop $ cc lex.yy.c
/tmp/ccwwkhvq.o: En función yylex': lex.yy.c:(.text+0x402): undefined reference toyywrap '
/tmp/ccwwkhvq.o: En función input': lex.yy.c:(.text+0xe25): undefined reference toyywrap'
collect2: ld devolvió 1 estado de salida

¿Qué está mal?

Nathan Campos
fuente

Respuestas:

126

El escáner llama a esta función al final del archivo, por lo que puede apuntar a otro archivo y continuar escaneando su contenido. Si no lo necesita, use

%option noyywrap

en la especificación del escáner.

Aunque deshabilitar yywrap es sin duda la mejor opción, también es posible enlazar con -lflpara usar la yywrap()función predeterminada en la biblioteca fl(es decir libfl.a) proporcionada por flex. Posix requiere que la biblioteca esté disponible con el indicador del vinculador -lly la instalación predeterminada de OS X solo proporciona ese nombre.

hjhill
fuente
1
¿Dónde se agregará exactamente '% option noyywrap', por favor? ¿En la sección de definición o en la línea de comando?
yamex5
¡Lo agregué al principio del .larchivo y lo lexacepté! No estoy seguro de si ese es el mejor lugar. Quizás no importa.
Deepak
9

Prefiero definir mi propio yywrap (). Estoy compilando con C ++, pero el punto debería ser obvio. Si alguien llama al compilador con varios archivos fuente, los almaceno en una lista o matriz, y luego se llama a yywrap () al final de cada archivo para darle la oportunidad de continuar con un nuevo archivo.

int yywrap() {
   // open next reference or source file and start scanning
   if((yyin = compiler->getNextFile()) != NULL) {
      line = 0; // reset line counter for next source file
      return 0;
   }
   return 1;
}
Codenheim
fuente
3

flex no siempre se instala con sus bibliotecas de desarrollo (lo cual es extraño, ya que es una herramienta de desarrollo). Instale las bibliotecas y la vida será mejor.

En los sistemas base de Redhat:

yum -y install flex-devel
./configure && make

En sistemas basados ​​en Debian

sudo apt-get install libfl-dev
Descendencia
fuente
2

Como nota para los seguidores, flex 2.6.3 tiene un error en el que libfl.a "normalmente" definiría yywrap, pero luego no lo hace en ciertos casos, así que compruebe si esa es su versión de flex, podría estar relacionada con su problema:

https://github.com/westes/flex/issues/154

Rogerdpack
fuente
-1
int yywrap(){return(1);}

use este código al final del programa.

veeppiaar
fuente