help-bison
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: AW: AW: Segmentation Fault in yyparse() method


From: Tim Van Holder
Subject: Re: AW: AW: Segmentation Fault in yyparse() method
Date: Fri, 16 Nov 2007 10:24:53 +0100
User-agent: Thunderbird 2.0.0.9 (Windows/20071031)

Jonas Stahl wrote:
>> Try running the application under valgrind or some other memory debugger.
>> If possible also try slightly different releases of gcc (4.1.1 or 4.2);
>> there's an outside chance that it's a bug in gcc.
> 
> Thanks. I think this isolated the fault a bit more.
> I tried debugging under valgrind. The result was this:
> 
> ==6040== Warning: client switching stacks?  SP change: 0xBED3A730 -->
> 0xBDABEDF0
> ==6040==          to suppress, use: --max-stackframe=19380544 or greater
> ==6040== Invalid write of size 4
> ==6040==    at 0x804A12C: yyparse (fullParser.tab.c:32956)
> ==6040==  Address 0xBED3A72C is on thread 1's stack 
> ==6040== 
> ==6040== Invalid write of size 4
> ==6040==    at 0x804A131: yyparse (fullParser.tab.c:32964)
> ==6040==  Address 0xBED331CC is on thread 1's stack 
> ==6040== Stack overflow in thread 1: can't grow stack to 0xBED331CC 
> ==6040== 
> ==6040== Process terminating with default action of signal 11 (SIGSEGV)
> ==6040==  Access not within mapped region at address 0xBED331CC
> ==6040==    at 0x804A131: yyparse (fullParser.tab.c:32964)
> ==6040==
> ==6040== Process terminating with default action of signal 11 (SIGSEGV)
> ==6040==  Access not within mapped region at address 0xBDABEDEC
> ==6040==    at 0x401D200: _vgnU_freeres (vg_preloaded.c:56)
> 
> 
> The adequate Code Lines: 
> 
> 32939 #ifdef YYPARSE_PARAM
> 32940 # if defined (__STDC__) || defined (__cplusplus)
> 32941 int yyparse (void *YYPARSE_PARAM)
> 32942 # else
> 32943 int yyparse (YYPARSE_PARAM)
> 32944   void *YYPARSE_PARAM;
> 32945 # endif
> 32946 #else /* ! YYPARSE_PARAM */
> 32947 #if defined (__STDC__) || defined (__cplusplus)
> 32948 int
> 32949 yyparse (void)
> 32950 #else
> 32951 int
> 32952 yyparse ()
> 32953     ;
> 32954 #endif
> 32955 #endif
> 32956 {
> 32957   
> 32958   int yystate;
> 32959  int yyn;
> 32960   int yyresult;
> 32961   /* Number of tokens to shift before error messages enabled.  */
> 32962   int yyerrstatus;
> 32963   /* Look-ahead token as an internal (translated) token number.  */
> 32964  int yytoken = 0;
> 
> What I get of this, is that the yyparse() method can't get stacked and it
> crashes at the first statement, where a new value has to get stacked. But
> GDB runs over these lines and throws segmentation fault, when reaching the
> YYLEX method call, because when stacking another method it finally does not
> know what to do. I think GDB shows the wrong point, because printf's before
> the YYLEX call aren't done.
> 
> But the big question still is, why it doesn't want to stack :-D

The 'client switching stacks?' seems odd - to me it suggests something
(e.g. a buffer overrun) smashed the stack. Then when yyparse continues
its run, it accesses values from the stack which provides screwy results
(because the stack pointer doesn't actually point to the stack anymore).
Eventually unmapped memory is accessed and the program crashes.

As an aside, I just built your code to see if I could reproduce it; your
grammar has over 69000 shift/reduce conflicts and 1325 reduce/reduce
conflicts; that makes it very doubtful that it will properly parse most
input.

I was able to reproduce the crash however, and it even happens when you
don't give any input, so it's not related to the input file at all.
Going up a stack frame from the crash in gdb showed

... in main (argc=-1073744536, argv=0x400463be)

and those argc/argv values again strongly indicate memory corruption.
Interestingly enough, these argc/argv values are that way even on entry,
which in fact suggests a compiler issue instead (or possibly an
optimization because argc/argv aren't used?)

gcc-3.3.6: no crash
gcc-3.4.6: no crash
gcc-4.0.4: normal argc/argv, crash
gcc-4.1.2: bad argc/argv, crash

However, the gcc 3.x builds did trigger lots of valgrind errors (over
ten million!); so there's definitely serious problems with the code
(just nothing that causes a fatal crash).

I did come accross the probable cause for the issue - your token type
contains a single char array, with its size defined as 30000 - so it
seems very likely that those semantic values are seriously overflowing
the program's stack. Changing the MAXLENGTH macro in additional.h to
8192 (8K) instead made the gcc4 builds work properly (well, they produce
the same result and the same 10million+ valgrind errors as the gcc3 builds).
My conclusion is that the code you have is horribly broken, without any
real redeeming features. A student turning in code like this to me would
certainly not get a passing grade :)




reply via email to

[Prev in Thread] Current Thread [Next in Thread]