flex+bison

Модератор: Модераторы разделов

skillergti
Сообщения: 34
ОС: slackware

flex+bison

Сообщение skillergti »

Здрайвствуйте.
Пытаюсь посредством утилит Flex, Bison написать модуль программы, который по заданному исходному c++ тексту классов, строит список, содержащий название класса, названия его родителей.
Проблема в том, что я не пойму как бы мне создать эту структуру для Bison и затем передать её "внешнему" коду основной программы

Грамматика для Flex

Код: Выделить всё

%option c++
%option yylineno
%option never-interactive
%option noyywrap
%{
    #include"parser.h"
%}
ws    [ \t]+
nl    [\n]+
Semi    ,
Par1    [\(\)]
Par2    [\{\}]
dd1;
dd2    :
ALNUM    [a-zA-Z0-9]+

%%
class    {yylval.string = strdup(yytext);return CLASS_KW;}
public    {yylval.string = strdup(yytext);return PUBLIC_KW;}
private    {yylval.string = strdup(yytext);return PRIVATE_KW;}
protected    {yylval.string = strdup(yytext);return PROTECTED_KW;}
{ALNUM}    {yylval.string = strdup(yytext);return WORD_KW;}
{Semi}        {yylval.string = strdup(yytext);return SEMI_KW;}
{Par1}        {yylval.string = strdup(yytext);return PAR1_KW;}
{Par2}        {yylval.string = strdup(yytext);return PAR2_KW;}
{dd1}        {yylval.string = strdup(yytext);return DD1_KW;}
{dd2}        {yylval.string = strdup(yytext);return DD2_KW;}
{nl}        {}
{ws}        {}

.        return -1;

%%


Грамматика для Bison (для начала, пытаюсь хотя бы вывести на экран информацию, но даже это не работает):

Код: Выделить всё

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

void yyerror(char const* msg);

int yylex();
int lineno();
%}

%union {
    char    *string;
}

%token <string> CLASS_KW PUBLIC_KW PRIVATE_KW PROTECTED_KW WORD_KW SEMI_KW PAR1_KW PAR2_KW DD1_KW DD2_KW

%%

acsiom : class;

class : CLASS_KW WORD_KW PAR2_KW PAR2_KW
{std::cout<<"Class name is:"<<$2<<"\n";}
| CLASS_KW WORD_KW DD2_KW inheritance PAR2_KW PAR2_KW
{std::cout<<"Class name is:"<<$2<<"\n";};

inheritance: PUBLIC_KW WORD_KW
{std::cout<<" it is a child of"<<$2<<" class\n";}
 | PROTECTED_KW WORD_KW
{std::cout<<" it is a child of"<<$2<<" class\n";}
| PRIVATE_KW WORD_KW
{std::cout<<" it is a child of"<<$2<<" class\n";}
| SEMI_KW inheritance;

%%


Код программы:

Код: Выделить всё

#include <iostream>
#include <fstream>
#include "FlexLexer.h"




extern int debug;

yyFlexLexer* lexer = NULL; //this is reference to global scanner

int debug = 1;  // parser to produce debug info output

int yyparse();//parser function,implemented by bison declaration
int yylex()  // wrapper for scanner function, bison looks it
{
    if (lexer != NULL)
        return lexer->yylex();
    else
        return 0;
}

void yyerror(char const* msg) // bison looks for it
{
    std::cerr << msg << std::endl;
}

int lineno()
{
    if (lexer != NULL)
        return lexer->lineno();
    else
        return 0;
}

int main (int argc, char* argv[])
{
    if (argc < 2) {
        std::cout << "USE: cbisonparser <source file>"
                      <<  std::endl;
        return 0;
                }

    std::ifstream infile(argv[1]);
    lexer = new yyFlexLexer(&infile);
    if (yyparse() != 0)
    {
        std::cout << "Syntax error, document rejected"
                      << std::endl;
    } else
        std::cout << "Success" << std::endl;
return 0;
}


Пример входного файла:

Код: Выделить всё

class parent{}
Спасибо сказали:
skillergti
Сообщения: 34
ОС: slackware

Re: flex+bison

Сообщение skillergti »

вопрос практически решил:)
std::cout пришлось заменить на printf
добавление в структуру я так понял можно сделать через функции, которые будут объявленны в заголовочном файле внешней программы.
Спасибо сказали: