Skip to main content
gamedev.net
🔒 Locked

C# Infinite loop during function call setup...

Started by Nypyren 4 replies 3.1k views
Original Post
Nypyren
Nypyren
I suspect this is a GC issue and I have some kind of circular references that it''s getting stuck on: I''m writing a GLR parser generator. I''m basically done with it, except whenever I call the function that begins creating the parse table from the tokens/collections/productions, the program freezes. However, it only freezes under one condition: Release mode with no debugger attached. Debug/No debugger: no lockup Debug/debugger: no lockup Release/debugger: no lockup Release/no debugger: lockup If I put a "return;" statement anywhere inside the function that is being called, it doesn''t lock. I put Console.WriteLine before and after each line of code to determine where the freezepoint is... it''s somewhere in the call-preparation for the constructor of my Table class. If I don''t have that short-circuit "return;", none of the writelines in the function ever get called. If I do, all of them up to that point get called.
leedgitar
leedgitar
It''s kinda hard to tell without seeing any code.

The only time I have noticed a difference in behavior when running Debug vs. Release in or out of the IDE, was when using the incorrect CallingConvetion for P/Invoke calls to a C++ library.
________________________________________________Chris McGuirkLead Programmer - Axiom 3D EngineC# gaming, the way of the future!http://www.axiom3d.org
Nypyren
Nypyren
* Everything I'm accessing is in the mscorlib assembly, no DllImports to .dlls

* It doesn't happen when the same code is compiled with Visual Studio .Net 2003 - this is because it defaults to using the .Net framework version 1.1

* Removing all code before the function call in the execution path does not prevent the problem.

* Viewing the code ILDASM for the debug and release mode executables, the caller and callee functions are identical except for variable-name-availability.

Since it appears that the callee function is the only critical piece, here it is:


public Table(ArrayList tokens, ArrayList collections, ArrayList productions)
{
ht = new Hashtable();

int tcount=0;
int ntcount=0;

// Generate indices for all of the tokens. Terminals and Nonterminals are counted separately.

foreach(Token t in tokens)
{
if (t is TokenT && !(t is TokenL))
ht[t] = tcount++;
else if (t is TokenNT)
ht[t] = ntcount++;
}

// Create the tables.

// The SR table is being generated as a GLR-compatible table.

// If the parser-writer doesn't want to use a GLR parser, just use the first element of the cell list.

srtable = new ArrayList[collections.Count, tcount];
gtable = new int[collections.Count, ntcount];

// Go through each collection and analyze the gotos and reduces.


// Pattern: "Goto(Ix, NT) = Iy", Function: GTable[x, NT] = y

// Pattern: "Goto(Ix, t) = Iy", Function: SRTable[x, t] = y

// Pattern: "Goto(*) = Iy" given Iy containing reduce "S -> A ." where S is the start symbol, Function: SRTable[y, End] = Accept

// Pattern: "Goto(*) = Iy" given Iy containing reduce "C -> x ." - for every member of C.follow "m", Function: SRable[y, m] = R<production #>

foreach(Collection c in collections)
{
foreach(Goto g in c.gotos)
{
if (g.token is TokenT && !(g.token is TokenL)) PutShift(g.istate, (int)ht[g.token], g.dstate);
else if (g.token is TokenNT) PutGoto (g.istate, (int)ht[g.token], g.dstate);

// Do reduces.

Collection c2 = (Collection)collections[g.dstate];
foreach (Production p in c2.reduces)
{
TokenNT nt = p.left as TokenNT;
foreach(TokenT t in nt.followset)
{
if (t is TokenE)
PutAccept(g.dstate, (int)ht[t]); // Acceptance is simply another way of defining the reduction of a start production on the End symbol.

else if (!(t is TokenL))
PutReduce(g.dstate, (int)ht[t], p.index);
}
}
}
}
}


[edited by - Nypyren on May 13, 2004 7:58:48 PM]
joanusdmentia
joanusdmentia
quote:
* It doesn''t happen when the same code is compiled with Visual Studio .Net 2003 - this is because it defaults to using the .Net framework version 1.1


Then it''s most likely either a bug in the .NET Framework v1.0 or in the C# compiler with VS2002. It may be the GC as you suggested, but i''d be surprised if its got anything to do with circular references.

quote:
If I put a "return;" statement anywhere inside the function that is being called, it doesn''t lock.


This makes me think it''s the compiler. Can you reproduce the problem by targetting v1.0 of the framework with VS2003? Does putting a return statement at the very end of the function work? Also, try rearranging the code, use for instead of foreach, etc.
"Voilà! In view, a humble vaudevillian veteran, cast vicariously as both victim and villain by the vicissitudes of Fate. This visage, no mere veneer of vanity, is a vestige of the vox populi, now vacant, vanished. However, this valorous visitation of a bygone vexation stands vivified, and has vowed to vanquish these venal and virulent vermin vanguarding vice and vouchsafing the violently vicious and voracious violation of volition. The nly verdict is vengeance; a vendett o
Nypyren
Nypyren
Oops - inportant distinction about the "return makes it not freeze"

* Only if the return statement is before or inside any of the for loops, not if it''s at the end of the function where the implicit return; gets generated.
joanusdmentia
joanusdmentia
Just a slight difference

Do you mean the foreach loops after the "new" allocations? Try commenting out the contents of the innermost loop and see if that makes any difference, if not comment out the contents of the mid-level loop, and then the entire contents of the outermost loop.

Also try changing all of the foreach loops to plain for loops one by one. If this fixes things then the problem is with the enumerator being used by the last foreach that you changed.
"Voilà! In view, a humble vaudevillian veteran, cast vicariously as both victim and villain by the vicissitudes of Fate. This visage, no mere veneer of vanity, is a vestige of the vox populi, now vacant, vanished. However, this valorous visitation of a bygone vexation stands vivified, and has vowed to vanquish these venal and virulent vermin vanguarding vice and vouchsafing the violently vicious and voracious violation of volition. The nly verdict is vengeance; a vendett o

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.