Bug 3004 - Stack overflow exception after calling a DataTable.Select method (tens of thousands of times)
Summary: Stack overflow exception after calling a DataTable.Select method (tens of tho...
Status: NEW
Alias: None
Product: Class Libraries
Classification: Mono
Component: System.Data (show other bugs)
Version: 2.10.x
Hardware: PC All
: --- normal
Target Milestone: Untriaged
Assignee: Bugzilla
URL:
Depends on:
Blocks:
 
Reported: 2012-01-21 09:56 UTC by Marcin Kral
Modified: 2012-02-02 06:46 UTC (History)
1 user (show)

See Also:
Tags:
Is this bug a regression?: ---
Last known good build:


Attachments
Patch to the master branch (4.60 KB, patch)
2012-02-02 06:46 UTC, Marcin Kral
Details | Diff
Patch to the mono-2-10 branch (4.81 KB, patch)
2012-02-02 06:46 UTC, Marcin Kral
Details | Diff

Description Marcin Kral 2012-01-21 09:56:39 UTC
Hi, 

Every call on a DataTable.Select(filter) is causing an indirect call for a private method GetColumn from Mono.Data.SqlExpressions.ColumnReference class. GetColumn is adding new event handlers which ends with StackOverflow Exception after while. 

Here's the example:
       // Code is unsafe because i want to allocate some stack space 
       // to get exception quicker. In "safe" mode result is the same,
       // but we've got to wait longer.
       public static unsafe void Main()
        {

            int* stackHolder = stackalloc int[(1 * 1024 * 1024 / 4)];
            long counter = 0;

            var dataTable = new DataTable();
            dataTable.Columns.Add("KEY", typeof(string));           
            
            var row = dataTable.NewRow();
            row["KEY"] = "VALUE";
           
            
            dataTable.Rows.Add(row);
                

            while (true)
            {
                counter++;
                var sw = new Stopwatch();
                sw.Start();
                dataTable.Select("KEY = 'VALUE'");
                sw.Stop();

                Console.WriteLine(String.Format("{0}\t{1}", sw.Elapsed, counter));
            }
        }

Here's the relevant part of stack trace:

System.MulticastDelegate.Equals (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/corlib/System/MulticastDelegate.cs:96
System.MulticastDelegate.Equals (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/corlib/System/MulticastDelegate.cs:96
System.MulticastDelegate.Equals (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/corlib/System/MulticastDelegate.cs:96
System.MulticastDelegate.Equals (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/corlib/System/MulticastDelegate.cs:96
System.Delegate.op_Equality (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/corlib/System/Delegate.cs:542
System.Delegate.op_Inequality (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/corlib/System/Delegate.cs:547
System.Data.DataColumnCollection.add_CollectionChanged (Parameters=) in
Mono.Data.SqlExpressions.ColumnReference.GetColumn (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/Mono.Data.SqlExpressions/ColumnReference.cs:139
Mono.Data.SqlExpressions.ColumnReference.GetReferencedRow (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/Mono.Data.SqlExpressions/ColumnReference.cs:147
Mono.Data.SqlExpressions.ColumnReference.Eval (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/Mono.Data.SqlExpressions/ColumnReference.cs:209
Mono.Data.SqlExpressions.Comparison.EvalBoolean (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/Mono.Data.SqlExpressions/Comparison.cs:49
System.Data.Common.Key.CanContain (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data.Common/Key.cs:161
System.Data.Common.Key.GetRecord (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data.Common/Key.cs:152
System.Data.Common.Index.RebuildIndex (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data.Common/Index.cs:174
System.Data.Common.Index.Reset (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data.Common/Index.cs:160
System.Data.Common.Index..ctor (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data.Common/Index.cs:61
System.Data.DataTable.GetIndex (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data/DataTable.cs:1455
System.Data.DataTable.Select (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data/DataTable.cs:1416
System.Data.DataTable.Select (Parameters=) in /home/lukasz/Documents/mono/mono-2.10.8/mcs/class/System.Data/System.Data/DataTable.cs:1363
Comment 1 Marcin Kral 2012-02-02 06:46:14 UTC
Created attachment 1305 [details]
Patch to the master branch
Comment 2 Marcin Kral 2012-02-02 06:46:43 UTC
Created attachment 1306 [details]
Patch to the mono-2-10 branch

Note You need to log in before you can comment on or make changes to this bug.