2011-07-11 8 views
1

私はYYSTYPEとして* charを使用すると非常に間違っているようですが、私はかなり新しくて何が起こっているのか分かりませんに。 Bisonは私に構文エラーまたはsegfaultを与えます。レクサーコードとバイソンコードは下にあります。私は...Bisonは私にセグメンテーションをスローします。それは何かを持っていると仮定します* char

レクサーコードとにかく誰がここで私を助けることができるのは非常に感謝するだろう:

/* token codes */ 
%{ 
#include <string.h> 
#include "printOut.tab.h" 
    int decl; 
%} 
%% 
"variables" {decl = 1; return VARS;} 
"while" {return WHILE;} 
"(" {return OB;} 
")" {return CB;} 
"{" {decl = 0; return OA;} 
"}" {return CA;} 
";" {return CP;} 
"if" {return IF;} 
":=" {return ASGN;} 
"=" {return IS;} 
"<" {return SML;} 
">" {return BIG;} 
"/=" {return NIS;} 
"+" {return PLS;} 
"-" {return MIN;} 
"^" {return POW;}  
"/" {return DIV;} 
"*" {return MUL;} 
"||" {return MA;} 
"->" {return ARR;} 
\\in {return VIS;} 
"int"|"string" {yylval.c = strdup(yytext); return TYP;} 
[ \t\n] {/*ignore whitespace and newline*/} 
[A-Za-z0-9]*(\[[a-zA-Z \.0-9\-\+]+(->)*[a-zA-Z \.0-9\-\+]+\])* {yylval.c = strdup(yytext); return VAR;} 
%% 
/*main(int argc, char **argv) 
{ 
    int tok; 
    yyin = fopen(argv[1], "r"); 
    while(tok = yylex()) { 
    if(decl && tok == IS) { tok = VIS; printf("%d ", tok); } 
    else { 
     if(tok == VAR){ printf("%s ", yylval); } else { printf("%d ", tok); } 
    } 
    } 
}*/ 

バイソンコード:

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


%union { 
    char *c; 
} 

%token <c> VAR TYP 
%token <c> VARS WHILE IF 
%token <c> VIS IS NIS MIN PLS POW DIV MUL ASGN MA SML BIG ELSE ARR 
%token <c> OB CB OA CA CP 

%type <c> vardec constr assign cond expr subexp input dec 
%type <c> start 

%% 


input: /* nothing */ 
    | input constr {printf("%s\n", $1); } 
    | input start {printf("%s\n", $1); } 
    | input vardec {printf("%s\n", $1); } 
; 
start: MIN MIN VAR OA {sprintf($$,"<algorithm=%s/>", $3); } 
; 
vardec: VARS dec {sprintf($$,"<declarations>%s</declarations>", $2); } 
; 
dec: TYP VAR VIS VAR CP {sprintf($$,"<declaration type=%s name=%s>%s</declaration>",$1,$2,$4);} 
    | dec CP TYP VAR VIS VAR CP {sprintf($$,"%s<declaration type=%s name=%s>%s</declaration>",$1,$3,$4,$6);} 
; 
constr: WHILE OB cond CB OA constr CA CP {sprintf($$,"<construct type=%s><condition>%s</condition><body>%s</body></construct>","while",$3,$6);} 
    | IF OB cond CB OA constr CA CP {sprintf($$,"<construct type=%s><condition>%s</condition><body>%s</body></construct>","if",$3,$6);} 
    | IF OB cond CB OA constr CA ELSE OA constr CA CP {sprintf($$,"<construct type=%s><condition>%s</condition><body>%s</body><altbody>%s</altbody></construct>","if",$3,$6,$10);} 
    | assign CP 
    | OA constr CA {$$ = $2;} 
; 
assign: VAR ASGN expr {sprintf($$,"<assignment name=%s>%s</assignment>",$1,$3);} 
    | assign MA VAR ASGN expr {sprintf($$,"<combinedassignment>%s<assignment name=%s>%s</assignment></combinedassignment>",$1,$3,$5);} 
; 
cond: VAR {sprintf($$,"<variable name=%s/>",$1);} 
    | expr IS expr {sprintf($$,"<equality><left>%s</left><right>%s</right></equality>",$1,$3);} 
    | expr SML expr {sprintf($$,"<smaller><left>%s</left><right>%s</right></smaller>",$1,$3);} 
    | expr BIG expr {sprintf($$,"<bigger><left>%s</left><right>%s</right></bigger>",$1,$3);} 
    | expr NIS expr {sprintf($$,"<inequality><left>%s</left><right>%s</right></inequality>",$1,$3);} 
; 
expr: subexp 
    | expr PLS subexp {sprintf($$,"<add><left>%s</left><right>%s</right></add>",$1,$3);} 
    | expr MIN subexp {sprintf($$,"<subtract><left>%s</left><right>%s</right></subtract>",$1,$3);} 
/* | MIN expr {sprintf($$,"<subtract><left>%s</left></subtract>",$2);} 
*/ | expr POW subexp {sprintf($$,"<power><left>%s</left><right>%s</right></power>",$1,$3);} 
/* | OB expr CB {$$ = $2;} 
*/; 
subexp: VAR {sprintf($$,"<variable name=%s/>",$1);} 
    | subexp DIV VAR {sprintf($$,"<divide><left>%s</left><right>%s</right></divide>",$1,$3);} 
    | subexp MUL VAR {sprintf($$,"<multiply><left>%s</left><right>%s</right></multiply>",$1,$3);} 
/* | OB subexp CB {$$ = $2;} 
*/; 
%% 
main() 
{ 
while(!feof(stdin)){ 
    yyparse(); 
} 
} 

yyerror(char *s) 
{ 
    fprintf(stderr, "error: %s\n", s); 
} 
+0

あなたはバイソン自体のセグメンテーションを意味しますか?もしそうなら、それは定義上、バイソンのバグです。 – Nemo

答えて

2

あなたはルールのタイプとして<c>を宣言しstart

<c>は、順にchar *です。そここれらのエラーのよりはあるので、私はstartルールであなたのSEGFAULTに通じるものを説明します:

$$は、ルールの値であるので、あなたは実質的にこれをやっている:中

char *result; 
sprintf(result,"<algorithm=%s/>", argument); 

resultこの例は割り当てられていないため、sprintf()は割り当てられていないメモリ領域に書き込もうとしています。あなたは可変長引数を受け付けます(すでに、あなたのレクサーで使用している)strdup()のような機能を実装する必要があります、メモリの適切なammountを割り当て、sprintf -magic行います

char* alloc_string(char *szFormat, ...) { 
    va_list args; 
    va_start(args, szFormat); 
    char szBuffer[1] = "\0"; 

    // vsnprintf() returns the bytes needed (*excluding* the null terminator) 
    // for a given formatter string and argument list 
    int nSize = vsnprintf(szBuffer, 0, szFormat, args); 

    char *szResult = (char *) malloc(1 + nSize); 
    vsnprintf(szResult, nSize + 1, szFormat, args); 
    return szResult; 
} 

言うまでもなくへのこの機能でメモリmalloc()を実行すると、あなたは責任を負います。

+0

申し訳ありません、ありがとう、一人の男。私は割り振りと何か関係があることを期待していましたが、私は主にJavaの作業に慣れていたので、私は躊躇していました。 –

+0

それで、まさにそのように見えますか? –

+0

Nm、それを持っています!ドープ... –

関連する問題