Jak sprawić, aby lex / flex rozpoznawał tokeny nie rozdzielone białymi znakami?

Zajmuję się budową kompilatora, a moim obecnym zadaniem jest napisanie leksera dla języka, który wdrażamy. Nie wiem, jak spełnić wymóg, aby leksyk rozpoznawał połączone żetony. Oznacza to, że tokeny nie są oddzielone białymi znakami. Np .: napis39if ma być rozpoznawany jako numer39 i słowo kluczoweif. Jednocześnie lexer musi równieżexit(1) gdy napotka nieprawidłowe dane wejściowe.

Uproszczona wersja kodu, który mam:

%{
#include <stdio.h>
%}

%option main warn debug

%%

if      |
then    |
else    printf("keyword: %s\n", yytext);

[[:digit:]]+    printf("number: %s\n", yytext);

[[:alpha:]][[:alnum:]]*     printf("identifier: %s\n", yytext);

[[:space:]]+    // skip whitespace
[[:^space:]]+   { printf("ERROR: %s\n", yytext); exit(1); }

%%

Po uruchomieniu tego (lub mojej pełnej wersji) i przekazaniu go do wejścia39if, reguła błędu jest dopasowana, a wyjście jestERROR: 39if, kiedy chciałbym, żeby to było:

number: 39
keyword: if

(To znaczy tak samo, jak gdybym wszedł39 if jako dane wejściowe.)

Przejście przez podręcznik, Mam przeczucie, że przyczyną jest to, że reguła błędu odpowiada dłuższemu możliwemu wejściu niż reguły liczby i słów kluczowych, a flex go preferuje. Powiedziawszy to, nie mam pojęcia, jak rozwiązać tę sytuację. Wydaje się niewykonalne napisanie wyraźnego wyrażenia regularnego, które odrzuci wszystkie dane wejściowe inne niż błędy, i nie wiem, jak inaczej napisać regułę „catch-all” ze względu na obsługę błędów lexera.

AKTUALIZACJA: Przypuszczam, że mogłabym po prostu wprowadzić regułę catch-all. { exit(1); } ale chciałbym uzyskać trochę ładniejszego wyjścia do debugowania niż „Wprawiłem w błąd w linii 1”.

questionAnswers(1)

yourAnswerToTheQuestion