Bug #30642 Adding the given count to the semaphore would cause it to exceed its maximum cou
Submitted: 27 Aug 2007 7:34 Modified: 14 Apr 2008 18:21
Reporter: Peter Reinhold Email Updates:
Status: Closed Impact on me:
None 
Category:Connector / NET Severity:S2 (Serious)
Version:5.0.8.1 OS:Windows (XP SP 2 and 2003 Server)
Assigned to: CPU Architecture:Any
Tags: pooling, Semaphore, threading

[27 Aug 2007 7:34] Peter Reinhold
Description:
After upgrading from version 5.0.7.0 I have been experiencing a very peculiar bug in my code.

A trivial SQL query, which has worked without errors, has suddenly begun to throw the following error

"Adding the given count to the semaphore would cause it to exceed its maximum count"

Nothing in the C# code has been changed, and if I downgrade the MySQL connector to 5.0.7.0 it works fine.

I found the following forum-post on MSDN

http://forums.microsoft.com/MSDN/ShowPost.aspx?PostID=565516&SiteID=1

and therefore tried disabling pooling by adding a pooling=false to the connectionstring, but that did not help.

How to repeat:
I haven't yet had the time to try and reproduce this error in a "small" way, which I would be able to post here, and I am not comfortable posting my entire code here.

But, the program is not very advanced, SQL wise, I run through a list, and for each entry, I do a fixed amount of selects and inserts.

It looks like the program halts at the same line on every run through, though, which could point to something being incremented, and not being decreased, and at some point overflowing.
[27 Aug 2007 9:37] Peter Reinhold
I have done a little more digging, and have got my code working on 5.0.8.1 with some minor modifications.

Before the change, I had a single MySQL Connector, which I closed, changed connectionstring on, and then re-opened.

If I changed this so I create a new connection object for each iteration instead, it works as it should.
[28 Aug 2007 20:04] Reggie Burnett
Peter

Can you give us a bit more info?  Do you run through the loop multiple times or does this error happen on the first time through?  In what way do you change the connection string?  Different host?

As much info as possible would be good.  Thx!
[30 Aug 2007 7:27] Tonci Grgin
Peter, what about info Reggie requested?
[30 Aug 2007 7:47] Peter Reinhold
Yes, ofcourse, here's some pseudo-code of when the trouble arised

-- PSEUDOCODE BEGIN --
Create MSCon1
Create MSCon2

Fill MSCon1 with data

Foreach in MSCon1
  If MSCon2 Open Then Close
  Set MSCon2 ConnectionString
  Open MSCon2
  
  Foreach in MSCon2
    DoSomething
  Next

  Close MSCon1
Next

Close MSCon2
-- PSEUDOCODE END --

This was more or less what happened, I did this to re-use the MSCon2 object, and not spawn a new one for each iteration.

I moved the Create MSCon2 inside the first loop, thus creating a new for each item in MSCon1, instead of reusing it, and then it worked.

I got the error on the same MSCon1 data-item on each run. (The sixth one)

If i tried changing the way the data was sorted in MSCon1, I got the error on the 10th item, and it continued to be on the 10th, which was not the same item that threw the error in the original sort of data (I know this last information may be more confusing than informative, please let me know if this makes no sense, and i'll try and explain it better)
[30 Aug 2007 7:49] Peter Reinhold
A little addendum, ofcourse after opening MSCon2, it is filled with data also. (Not really relevant to the bug, i think)
[17 Sep 2007 6:27] Tonci Grgin
There is a similar error reported in Bug#30816:
 [6 Sep 10:40] Reg Proctor

More information for 5.1.3 (this did not happen in 5.1.2: When I shut down my application I get the following error:

System.Threading.SemaphoreFullException was unhandled
  Message="Adding the given count to the semaphore would cause it to exceed its maximum count."
  Source="System"
  StackTrace:
       at System.Threading.Semaphore.Release(Int32 releaseCount)
       at System.Threading.Semaphore.Release()
       at MySql.Data.MySqlClient.MySqlPool.RemoveConnection(Driver driver)
       at MySql.Data.MySqlClient.MySqlPoolManager.RemoveConnection(Driver driver)
       at MySql.Data.MySqlClient.NativeDriver.Dispose(Boolean disposing)
       at MySql.Data.MySqlClient.Driver.Close()
       at MySql.Data.MySqlClient.NativeDriver.Finalize()

Reggie?
[7 Dec 2007 11:27] Tonci Grgin
Peter, I am unable to repeat reported behavior against MySQL server 5.0.54BK on WinXP Pro SP2 localhost using c/NET 5.0.9.0...

    MySqlConnection conn1 = new MySqlConnection();
    MySqlConnection conn2 = new MySqlConnection();
    MySqlDataReader dr;
    conn1.ConnectionString = "DataSource=localhost;Database=test;UserID=root;Password=*****;PORT=3306;Allow Zero Datetime=True;logging=True;";//pooling=true/false does not change anything
    conn1.Open();
    //FAILING CASE, REUSE conn2
    conn2.ConnectionString = "DataSource=localhost;Database=test;UserID=root;Password=*****;PORT=3306;Allow Zero Datetime=True;logging=True;";
    conn2.Open();
    MySqlCommand command = new MySqlCommand();
    command.Connection = conn2;
    MySqlDataReader dr2;

    MySqlCommand cmdCreateTable = new MySqlCommand("DROP TABLE IF EXISTS `test`.`bug30642`", conn1);
    cmdCreateTable.CommandType = CommandType.Text;
    cmdCreateTable.CommandTimeout = 0;
    cmdCreateTable.ExecuteNonQuery();
    cmdCreateTable.CommandText = "CREATE TABLE `test`.`bug30642` (" +
      "`ID` int unsigned NOT NULL AUTO_INCREMENT, " +
      "`LastModified` varchar(50) NOT NULL DEFAULT '', " +
      "PRIMARY KEY (`ID`) " +
      ") DEFAULT CHARSET=latin1;";
    cmdCreateTable.ExecuteNonQuery();
    DateTime dt;
    dt = DateTime.Now;
    cmdCreateTable.CommandText = "INSERT INTO bug30642 VALUES (NULL,'" + dt.ToString("yyyy-MM-dd HH:mm:ss") + "')";
    try
    {
      Assert.AreEqual(1, cmdCreateTable.ExecuteNonQuery());
      //Add few more rows
      cmdCreateTable.CommandText = "SELECT * FROM bug30642";
      dr = cmdCreateTable.ExecuteReader();
      while (dr.Read())
      {
        Console.WriteLine("READER CONN1: " + dr.GetValue(1).GetType().FullName);
        command.CommandText = "SELECT * FROM bug30642";
        command.CommandType = CommandType.Text;
        dr2 = command.ExecuteReader();
        while (dr2.Read())
        {
          Console.WriteLine("CONN2: "+dr2.GetValue(1).GetType().FullName);
        }
        dr2.Close();
      }
      dr.Close();
      cmdCreateTable.Dispose();
      conn1.Close();
      command.Dispose();
      conn2.Close();
      Console.WriteLine("DONE TESTING");
    }
    catch (Exception ex)
    {
      Assert.Fail(ex.Message);
    }

Output:
[07.12.07 12:21:09] - Executing command QUERY with text ='SELECT * FROM bug30642'
READER CONN1: System.String
READER CONN2: System.String
READER CONN2: System.String
READER CONN2: System.String
READER CONN2: System.String
READER CONN2: System.String
--<cut>--
READER CONN1: System.String
READER CONN2: System.String
READER CONN2: System.String
READER CONN2: System.String
READER CONN2: System.String
READER CONN2: System.String
DONE TESTING
[8 Jan 2008 0:00] Bugs System
No feedback was provided for this bug for over a month, so it is
being suspended automatically. If you are able to provide the
information that was originally requested, please do so and change
the status of the bug back to "Open".
[1 Apr 2008 4:37] Damon Overboe
Please clean this up as you see fit, or you may post it to public as is.

using c# 2005, WinXP sp2, MySQL Connector/Net v. 5.2.1

SOLUTION SUMMARY: ensure you are calling explicitly calling disconnect before exiting the program; my guess is that this error is thrown when the disconnect is called by a different thread than the one you connect on. 

MY RECREATION:
I have one MySQL class in which I can create and maintain a connection
This class implements the disposable interface and has a destructor, and I have a connect and disconnect method.

The destructor checks if the class has been disposed, and if not will dispose.
Dispose checks if the connection is closed, and if not will close and dispose.

If I do not explicitly call the disconnect and dispose methods, when the main program exits, the destructor for the MySQL class fires and starts the series (destructor calls dispose calls disconnect, then unwinds the stack(disconnect then dispose then destroy) When it comes to the disconnect command, it throws this same System.Threading.SemaphoreException error.

MY WORKAROUND / SUMMARY:
I found this error in a test program where I did not properly dispose of my objects. The workaround for this is that I explicitly call the dispose method to the MySQL class before the main app exits, and this error is not raised.

Note that when I do this, in respects to the main app, I only call dispose and do not have to explicitly call the disconnect method in the main app (although my dispose does call it explicitly).
[14 Apr 2008 18:21] Tonci Grgin
Damon, thanks for your comment. It wouldn't be fair for me to pass it to others so I decided to just make it public. It may help someone resolve similar issues.

Thanks for your interest in MySQL.
[10 May 2008 19:17] Matt Klein
Hi,

I am seeing this problem again after upgrading from 5.1.5 -> 5.1.6.

Nothing changed in my code. Also, every connection instance is wrapped in a using() clause which should force the finalizer and the disconnect to happen.

Here is the error trace:

pplication ID: /LM/W3SVC/1977595482/Root

Process ID: 568

Exception: System.Threading.SemaphoreFullException

Message: Adding the given count to the semaphore would cause it to exceed its maximum count.

StackTrace:    at System.Threading.Semaphore.Release(Int32 releaseCount)
   at System.Threading.Semaphore.Release()
   at MySql.Data.MySqlClient.MySqlPool.RemoveConnection(Driver driver)
   at MySql.Data.MySqlClient.MySqlPoolManager.RemoveConnection(Driver driver)
   at MySql.Data.MySqlClient.NativeDriver.Dispose(Boolean disposing)
   at MySql.Data.MySqlClient.Driver.Close()
   at MySql.Data.MySqlClient.NativeDriver.Finalize()

What can I do to help diagnose this?
[12 May 2008 22:28] Nalle Jacobsson
I'm also seeing this problem after upgrading from 5.1.15 -> 5.1.16
[12 May 2008 22:29] Nalle Jacobsson
Sorry, I meant 5.1.5 -> 5.1.6
[13 May 2008 13:14] Paul Bowden
This problem is also happening to me after upgrading from 5.1.2 -> 5.1.6
[13 May 2008 16:29] Matt Klein
I'm new to the MySQL bug process. It doesn't seem like there is any way to re-activate this bug. Should a new one be opened?
[15 May 2008 9:38] Tonci Grgin
No need to review anything, if I'm not mistaken, Paul posted Bug#36688 to follow up on this.
[27 May 2008 21:20] Reggie Burnett
Guys

This issue is the same as 36688 which has been fixed.  We know that 5.1.6 had this bug so there is no need to keep posting it.
[3 Mar 2009 17:14] Pedro Semeano
I'm having the same problem with version 5.1.30...
[3 Mar 2009 17:45] Pedro Semeano
Forget about it... Just installed MySql Connector 6.0 and everything is fine now =)
[3 Mar 2010 14:00] Usman Ali
Two step to solve System.Threading.Semaphore.Release Issue

1. Install Latest mySQL Connector 6.0 or later

2.Set pooling=false; in the connection string.

For Example :

ConnectionStringObject="server=localhost;user id=root;password=usman;database=uts1;persist security info=True;pooling=false;"

_________________

www.ashscholar.com