-1

私は構文解析に関する学校の科目に取り組んでいます。目標は、cairo ライブラリを使用してベクター グラフィックスを作成するための小さな言語を作成することです。C では中間状態を使用することにしました。

Yacc を使用して、gcc によってコンパイルされる C コードを生成します。正常に動作しますが、文字列に問題があります。

コードは次のとおりです。

        int sumChar = 0 ;

        char outnb1[20];
        char outnb2[20];

        sprintf(outnb1, "%f;", $4);
        sprintf(outnb2, "%f;", $8);

        sumChar = (6+strlen($2)+1+5+strlen($2)+1+strlen(outnb1)+strlen($6)+strlen($7)+strlen(outnb2)+strlen($10)+strlen($11)+1+1+strlen($14)+1);

// $ 14 is the string returned by another part of the code.

        printf("String = %s\nSIZE = %d\n",$14,strlen($14));

//The printf here is exact and the string is not truncated :
//cairo_line_to ( cr ,prevPoint[0] ,prevPoint[1]);
//cairo_move_to ( cr ,prevPoint[0] ,prevPoint[1]);

        char *result = malloc(sizeof(char)*sumChar);
        sprintf(result, "%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s","\n\nint ",$2,";","\nfor(",$2,"=",outnb1,$6,$7,outnb2,$10,$11,")","{",$14,"}");
        printf("String after sprintf = %s\nSIZE = %d\n",$14,strlen($14));

//The printf print something like :
//cairo_line_to ( cr ,prevPoint[0] ,prevPoint[1]);
//cairo_move_to ( cr ,prevPoint[0]�

        $$ = result;

malloc の後で文字列が切り捨てられる理由がよくわかりません。それは明らかにメモリのバグですが、その理由はわかりません。アイデアや解決策はありますか?

編集 :

Yacc ルール:

%union
{
    double number;
    char * str;
};

%token DRAW <number>NB <str>COMP <str>VARNAME <str>VARFOR <str>INC;
%type <str>D;
%type <str>BLOCFOR;
%type <str>FOR;

FOR : '(' VARFOR '=' NB ';' VARFOR COMP NB ';' VARFOR INC ')' '{' BLOCFOR '}' 
    {
        int sumChar = 0 ;
        char outnb1[20];
        char outnb2[20];
        sprintf(outnb1, "%f;", $4);
        sprintf(outnb2, "%f;", $8);
        sumChar += (6+strlen($2)+1+5+strlen($2)+1+strlen(outnb1)+strlen($6)+strlen($7)+strlen(outnb2)+strlen($10)+strlen($11)+1+1+strlen($14)+1);
        printf("VALUE OF BLOCFOR = %s\nSIZE = %d\n",$14,strlen($14));

        char *result = malloc(sizeof(char)*(sumChar+1));
        sprintf(result, "%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s","\n\nint ",$2,";","\nfor(",$2,"=",outnb1,$6,$7,outnb2,$10,$11,")","{",$14,"}");
        printf("VALUE OF BLOCFOR AFTER RESULT = %s\nSIZE = %d\n",$14,strlen($14));
        printf("%s\n",result );
        $$ = result;
    }

BLOCFOR : DRAW D '$' {$$ = $2; printf("INSIDE BLOCFOR %s\nSIZE = %d\n",$2,strlen($2));}

お役に立てば幸いです。単純化されたlexファイルが必要になるため、実際に機能するコードを提供することはできません。しかし、私はそれを言うことができます:

char result[sumChar];

resultは正しいですが、$$ = result機能しません (FOR で返された値は使用できません。それは �G�+0��I�F���I� のようなランダムな文字です)。

lex source の str 値の解析と戻りは次のとおりです。

<FOR>[[:alpha:]]+ {yylval.str = strdup(yytext);return VARFOR;}

解決済み : 問題は解決しました。これは、D トークン内の sumChar と割り当ての不適切な計算でした。

4

1 に答える 1

0

変数には、終了文字sumCharのエクストラが含まれていません。これにより、未定義の動作が発生する可能性が高く、その問題がその兆候である可能性があります。それをコールに追加するか、コールに追加します。+1'\0'sumCharmalloc

于 2013-04-22T12:37:40.363 に答える