none
SQL Server 2008 64 - Periodicamente não aceita conexões RRS feed

  • Pergunta

  • Amigos,

    Tenho 2 servidores em cluster Windows 2008 64 e SQL Server 2008 SP1 64 também, de alguns dias pra cá tenho me deparado com problemas de conexão, meu servidor tem negado logon, alguns de meus backups não foram feitos por este motivo. Vocês podem me ajudar?

    Os erros registrados em log são estes:

    2010-07-26 11:02:40.720  spid119 Error: 18056, Severity: 20, State: 29.
    2010-07-26 11:02:40.720  spid119 
     The client was unable to reuse a session with SPID 119, which had been reset for connection pooling. The failure ID is 29. This error may have been caused by an earlier operation failing. Check the error logs for failed operations immediately before this error message.
    2010-07-26 11:02:40.720  spid81 Error: 18056, Severity: 20, State: 29.
    2010-07-26 11:02:40.720  spid81 
     The client was unable to reuse a session with SPID 81, which had been reset for connection pooling. The failure ID is 29. This error may have been caused by an earlier operation failing. Check the error logs for failed operations immediately before this error message.
    2010-07-26 12:03:51.310  spid109 Error: 10982, Severity: 16, State: 1.
    2010-07-26 12:03:51.310  spid109 
     Failed to run resource governor classifier user-defined function. See previous errors in SQL Server error log from session ID 109 for details.  Classifier elapsed time: 1 ms. 
    2010-07-26 12:03:57.770  spid221 Error: 18056, Severity: 20, State: 29.
    2010-07-26 12:03:57.770  spid221 
     The client was unable to reuse a session with SPID 221, which had been reset for connection pooling. The failure ID is 29. This error may have been caused by an earlier operation failing. Check the error logs for failed operations immediately before this error message.
    2010-07-26 12:04:01.680  spid139 Error: 10982, Severity: 16, State: 1.
    2010-07-26 12:04:01.680  spid139 
     Failed to run resource governor classifier user-defined function. See previous errors in SQL Server error log from session ID 139 for details.  Classifier elapsed time: 1 ms. 
    2010-07-26 13:34:30.350  Logon Error: 18456, Severity: 14, State: 46.
    2010-07-26 13:34:30.350  Logon 
     Login failed for user 'XXXXXX'. Reason: Failed to open the database configured in the login object while revalidating the login on the connection. [CLIENT: 999.99.999.999]
    2010-07-26 13:34:30.400  spid127 Error: 18056, Severity: 20, State: 46.
    2010-07-26 13:34:30.400  spid127 
     The client was unable to reuse a session with SPID 127, which had been reset for connection pooling. The failure ID is 46. This error may have been caused by an earlier operation failing. Check the error logs for failed operations immediately before this error message.
    2010-07-26 14:58:18.750  spid98 Error: 18056, Severity: 20, State: 29.
    2010-07-26 14:58:18.750  spid98 
     The client was unable to reuse a session with SPID 98, which had been reset for connection pooling. The failure ID is 29. This error may have been caused by an earlier operation failing. Check the error logs for failed operations immediately before this error message.

    segunda-feira, 26 de julho de 2010 19:35

Respostas

  • Olá Inery,

    Já tive alguns problemas com conexão, e só foi possível resolver alterando duas configurações do TCP nos clients.

    • TcpTimedWaitDelay
      • Descrição: Determina o tempo que deve decorrer antes que o TCP/IP possa liberar uma conexão fechada e reutilizar seus recursos. Esse intervalo entre o fechamento e a liberação é conhecido como o estado TIME_WAIT ou o dobro do estado de duração máxima do segmento (2MSL). Durante esse tempo, a reabertura da conexão com o cliente e com o servidor custa menos que estabelecer uma nova conexão. Reduzindo o valor desta entrada, o TCP/IP pode liberar conexões fechadas mais rapidamente e fornecer mais recursos para novas conexões. Ajuste este parâmetro se o aplicativo em execução exigir liberação rápida, a criação de novas conexões ou um ajuste, devido a um baixo rendimento do processamento causado por várias conexões no estado TIME_WAIT.
      • Como exibir ou definir:
        • 1 - Utilize o comando regedit, acesse a subchave de registro HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\TCPIP\Parameters e crie um novo valor REG_DWORD denominado TcpTimedWaitDelay.
        • 2 - Defina o valor como decimal 30, que é Hex 0x0000001e. Esse valor define o tempo de espera para 30 segundos.
        • 3 - Pare e reinicie o sistema.
      • Valor padrão: 0xF0, que define o tempo de espera para 240 segundos (4 minutos).
      • Valor recomendado: Um valor mínimo de 0x1E, que define o tempo de espera para 30 segundos.

    • MaxUserPort
      • Descrição: Determina o número de porta mais alto que o TCP/IP pode designar quando um aplicativo solicita uma porta do usuário disponível no sistema.
      • Como exibir ou definir:
        • 1 - Utilize o comando regedit, acesse a subchave de registro HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\TCPIP\Parameters e crie um novo valor REG_DWORD denominado MaxUserPort.
        • 2 - Defina este valor para pelo menos 32768 (decimal).
        • 3 - Pare e reinicie o sistema.
      • Valor padrão: Nenhum
      • Valor recomendado: Pelo menos 32768 (decimal).

    Obs: Para identificar se esta configuração faz sentido, sugiro que faça uma análise do "netstat -an |findstr 1433" se a quantidade de conexões for muito grande, vale a pena tentar esta configuração.

     

    Outra coisa: veja se está aplicando os hotfixes do SQL 2008 pós SP1:

    The SQL Server 2008 builds that were released after SQL Server 2008 Service Pack 1 was released
    http://support.microsoft.com/kb/970365/en-us

    Outros links interessantes:

    The SQL Server 2005 builds that were released after SQL Server 2005 Service Pack 3 was released
    http://support.microsoft.com/kb/960598/en-us

    Cumulative list of the hotfixes that are available for SQL Server 2000 SP4
    http://support.microsoft.com/kb/894905/en-us

     

     

    Mais uma dica:

    O Windows 2008 pode apresentar sintomas de lentidão extrema em procedimentos de cópia de arquivos envolvendo computadores remotos em uma rede. Este problema ocorre porque no núcleo TCP do Windows Vista (base do Windows 2008) foi implementado um mecanismo de inteligência para minimizar o consumo de banda. No entando este comportameno não é muito indicado em ambientes que exijam cópia de arquivos grandes.

    Para desativar este recurso, desinstale a Feature "Remote Differential Compression".

    É precebido que, dependendo da composição da rede e disposição das interfaces de rede, mesmo desativando o "Remote Differential Compression" o problema pode permanecer, neste caso você pode usar o comando abaixo para desabilitar o tuning de TCP:

    netsh interface tcp set global autotuninglevel=disabled

    Tive que desabilitar isso em alguns servidores Windows 2008 que administro para poder transferir mais rapidamente arquivos entre Windows 2003 e Windows 2008, talvez ajude com a questão do backup, dependendo do seu cenário.

    sexta-feira, 30 de julho de 2010 18:26

Todas as Respostas

  • Olá Inery,

     

    Acho que seu erro pode ser um Bug, há varios chamados abertos no site Connect, dá uma olhada nos comentários do link abaixo.

    Links Connect:

    http://connect.microsoft.com/SQLServer/feedback/details/540092/sql-server-2008-sp1-cu6-periodically-does-not-accept-connections

    https://connect.microsoft.com/SQLServer/feedback/details/468478/sql-server-2008-periodically-does-not-accept-connections?wa=wsignin1.0

     

    OBS: Isso era um bug do SQL Server 2005 que teve um patch de correção: http://support.microsoft.com/kb/937745/pt-br

    segunda-feira, 26 de julho de 2010 20:36
  • Inery,

    Todos estes logins estão com seus respectivos banco de dados mapeados? Estes logins estão com permissão de acesso liberada?

    Eu já consultei algumas informações sobre este problema que ocorria no SQL Server 2005 mas particularmente acredito que a Microsoft resolveu este problema.

    São diversos logins que estão apresentando esta falha?


    Pedro Antonio Galvão Junior [MVP | Microsoft Evangelist | Microsoft Partner | Engenheiro de Softwares | Especialista em Banco de Dados | SorBR.Net | Professor Universitário]
    terça-feira, 27 de julho de 2010 00:04
    Moderador
  • Boa noite Inery, tudo bem?

    O erro 18056 é um erro genérico do sql server e somente acontence quando temos o pool de conexões ativado. Pools de conexões é uma técnica que reduz a quantidade de vezes que uma conexão precisa ser aberta no servidor. Então quando um cliente reutiliza um determinado pool de conexão, o sql server executa apenas alguns procedimentos para facilar seu "retorno" a base de dados.

    Se qualquer exceção (crítica, erro e outros) ocorrer, o sql server exibe a mensagem genérica com o número 18056.

    Então se analisarmos o resource do Sql Server, podemos observar diversas mensagens com o código 18056 combinadas com vários tipos de falhas. A falha 29 é quando o usuário já está desconectado. E ela pode ocorrer em situações onde a conexão com o usuário é perdida (wireless com baixo sinal por exemplo).

    Em diversos casos é possível encontrar problemas com o desempenho do servidor, ou seja, o erro pode ser uma consequência nestas situações. Um exemplo parecido e prático por exemplo, é você criar um bat para preencher um arquivo texto em uma unidade de disco que contenha um arquivo do tipo MDF, nesta hora você notará que o sql server apresentará diversos status do tipo pageiolatch_sh (ou seja, um status de consumo de disco, consequência do uso excessivo do mesmo).

    Esta é uma pergunta difícil de ser respondida, pois necessitaria de uam análise mais profunda sobre o ambiente, mas acho difícil de ser problemas como a base de dados entrando em status como offline e derivados, por não encontrarmos no trecho do log reportado o status 23.

    Este erro é algo realmente interessante e desafiador. Recomendo que ligue o perfmon e capture alguns contadores de memória, cpu, disco, rede e alguns contadores do sql server e depois veja se houve pico no consumo dos recursos em um período onde um usuário, tenha sido desconectado.

    Você também pode usar o utilitário sqldumper para realizar um dump da memória e analisar o momento do erro com detalhes que podem ser suficientes para sanar o problema de seu ambiente.

    Atenciosamente

    Dobereiner Miller Silva Rodrigues

    sqlinternal.blogspot.com


    Aquilo que sou é aquilo que me foi outorgado
    • Editado Dobereiner Miller terça-feira, 27 de julho de 2010 06:16 Sono... fez cometer alguns erros básicos de português..
    terça-feira, 27 de julho de 2010 06:12
  • Olá Leandro,

    Eu também encontrei esse fix do 2005 e vi que outras pessoas tem este problemas, mas não encontrei solução para o 2008.

    Chato né?

    terça-feira, 27 de julho de 2010 12:57
  • Olá Júnior,

    Os logins tem os bancos mapeados sim, inclusive o erro acontece esporadicamente pq o login é usado na aplicação que está funcionando, estas "falhas" são aleatórias, acontece com o usuário q utilizo no SqlAgent tbm, alguns de meus backups falham algumas vezes em virtude disto.

    Na verdade, é isto que me deixa confusa, pois o backup de log q falha agora funciona no próximo schedule, mesma job, mesmo login.

    São diversos logins sim.

    Obrigada!

    terça-feira, 27 de julho de 2010 13:01
  • Olá Dobereiner,

    Já utilizei o perfmon, realmente em alguns casos meu uso de cpu é elevado, mas em outros não, cheguei a ter este erro com 40% de uso de CPU e permaneceu assim algum tempo.

    Memória o SQL alocou 30 GB a uns 2 meses e como não reinicio o serviço desde então, continua alocada.

    Obrigada,

    terça-feira, 27 de julho de 2010 13:06
  • Bom dia Inery, o caso realmente é intrigante...

    Quanto ao tempo do serviço no sql, apenas comprava que causas como a base ficando off ou derivados está descartada.

    A solução que vejo, é a geração de um dump, ou, anexar o processo há um debug adicionando um break para a exception (muito cuidado com este último), pois o debug pode interromper o serviço ao ser finalizado.

    Se houver dúvidas de como usar o programa, favor consulte o seguinte kb: http://support.microsoft.com/kb/917825

    Esta seria a única forma de encontrar o erro sem envolver um enginner msft. Caso você possua alguma parceria, recomendo entrar em contato com a equipe msft support enginner.

    A engine responsável no sql por métodos de acesso é a Storage Engine. Ela possui funções como tentativa de reuso de recursos, que é algo como:

    internal ResourcePool(...)
      {
        this._interval = interval;
        this._resources = new ArrayList(4);
        this._max = max;
        this._callback = new TimerCallback(this.TimerProc);
      }
    
      public void Dispose()
      {
        this.Dispose(true);
      }
    
      private void Dispose(bool disposing)
      {
        lock (this)
        {
          if (!this._disposed)
          {
            if (this._resources != null)
            {
              foreach (IDisposable disposable in this._resources)
              {
                disposable.Dispose();
              }
              this._resources.Clear();
            }
            if (this._timer != null)
            {
              this._timer.Dispose();
            }
            this._disposed = true;
            if (disposing)
            {
              GC.SuppressFinalize(this);
            }
          }
        }
      }
    
      ~ResourcePool()
      {
        this.Dispose(false);
      }
    
      internal object RetrieveResource()
      {
        object obj2 = null;
        if (this._resources.Count != 0)
        {
          lock (this)
          {
            if (this._disposed)
            {
              return obj2;
            }
            if (this._resources.Count == 0)
            {
              return null;
            }
            obj2 = this._resources[this._resources.Count - 1];
            this._resources.RemoveAt(this._resources.Count - 1);
            if (this._resources.Count < this._iDisposable)
            {
              this._iDisposable = this._resources.Count;
            }
          }
        }
        return obj2;
      }
    
      internal void StoreResource(IDisposable o)
      {
        lock (this)
        {
          if (!this._disposed && (this._resources.Count < this._max))
          {
            this._resources.Add(o);
            o = null;
            if (this._timer == null)
            {
              this._timer = new Timer(this._callback, null, this._interval, this._interval);
            }
          }
        }
        if (o != null)
        {
          o.Dispose();
        }
      }
    
      private void TimerProc(object userData)
      {
        IDisposable[] array = null;
        lock (this)
        {
          if (!this._disposed)
          {
            if (this._resources.Count == 0)
            {
              if (this._timer != null)
              {
                this._timer.Dispose();
                this._timer = null;
              }
              return;
            }
            array = new IDisposable[this._iDisposable];
            this._resources.CopyTo(0, array, 0, this._iDisposable);
            this._resources.RemoveRange(0, this._iDisposable);
            this._iDisposable = this._resources.Count;
          }
        }
        if (array != null)
        {
          for (int i = 0; i < array.Length; i++)
          {
            try
            {
              array[i].Dispose();
            }
            catch
            {
            }
          }
        }
    
    

    Na função de retornar um recurso, eu uso algoritmos de movimentação de pilha... este tipo de algoritmo pode ser muito preojudicado com hangs e etc.. realmente precisaria ver o que tem na memória de sua base para identificar exatamente o problema...

    Bom se for possível usar o sqldumper e você identificar o trecho exato do problema, tente postar o resultado.

    Atenciosamente

    Dobereiner Miller Silva Rodrigues

    sqlinternal.blogspot.com


    Aquilo que sou é aquilo que me foi outorgado
    terça-feira, 27 de julho de 2010 15:19
  • Olá Inery,

    Já tive alguns problemas com conexão, e só foi possível resolver alterando duas configurações do TCP nos clients.

    • TcpTimedWaitDelay
      • Descrição: Determina o tempo que deve decorrer antes que o TCP/IP possa liberar uma conexão fechada e reutilizar seus recursos. Esse intervalo entre o fechamento e a liberação é conhecido como o estado TIME_WAIT ou o dobro do estado de duração máxima do segmento (2MSL). Durante esse tempo, a reabertura da conexão com o cliente e com o servidor custa menos que estabelecer uma nova conexão. Reduzindo o valor desta entrada, o TCP/IP pode liberar conexões fechadas mais rapidamente e fornecer mais recursos para novas conexões. Ajuste este parâmetro se o aplicativo em execução exigir liberação rápida, a criação de novas conexões ou um ajuste, devido a um baixo rendimento do processamento causado por várias conexões no estado TIME_WAIT.
      • Como exibir ou definir:
        • 1 - Utilize o comando regedit, acesse a subchave de registro HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\TCPIP\Parameters e crie um novo valor REG_DWORD denominado TcpTimedWaitDelay.
        • 2 - Defina o valor como decimal 30, que é Hex 0x0000001e. Esse valor define o tempo de espera para 30 segundos.
        • 3 - Pare e reinicie o sistema.
      • Valor padrão: 0xF0, que define o tempo de espera para 240 segundos (4 minutos).
      • Valor recomendado: Um valor mínimo de 0x1E, que define o tempo de espera para 30 segundos.

    • MaxUserPort
      • Descrição: Determina o número de porta mais alto que o TCP/IP pode designar quando um aplicativo solicita uma porta do usuário disponível no sistema.
      • Como exibir ou definir:
        • 1 - Utilize o comando regedit, acesse a subchave de registro HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\TCPIP\Parameters e crie um novo valor REG_DWORD denominado MaxUserPort.
        • 2 - Defina este valor para pelo menos 32768 (decimal).
        • 3 - Pare e reinicie o sistema.
      • Valor padrão: Nenhum
      • Valor recomendado: Pelo menos 32768 (decimal).

    Obs: Para identificar se esta configuração faz sentido, sugiro que faça uma análise do "netstat -an |findstr 1433" se a quantidade de conexões for muito grande, vale a pena tentar esta configuração.

     

    Outra coisa: veja se está aplicando os hotfixes do SQL 2008 pós SP1:

    The SQL Server 2008 builds that were released after SQL Server 2008 Service Pack 1 was released
    http://support.microsoft.com/kb/970365/en-us

    Outros links interessantes:

    The SQL Server 2005 builds that were released after SQL Server 2005 Service Pack 3 was released
    http://support.microsoft.com/kb/960598/en-us

    Cumulative list of the hotfixes that are available for SQL Server 2000 SP4
    http://support.microsoft.com/kb/894905/en-us

     

     

    Mais uma dica:

    O Windows 2008 pode apresentar sintomas de lentidão extrema em procedimentos de cópia de arquivos envolvendo computadores remotos em uma rede. Este problema ocorre porque no núcleo TCP do Windows Vista (base do Windows 2008) foi implementado um mecanismo de inteligência para minimizar o consumo de banda. No entando este comportameno não é muito indicado em ambientes que exijam cópia de arquivos grandes.

    Para desativar este recurso, desinstale a Feature "Remote Differential Compression".

    É precebido que, dependendo da composição da rede e disposição das interfaces de rede, mesmo desativando o "Remote Differential Compression" o problema pode permanecer, neste caso você pode usar o comando abaixo para desabilitar o tuning de TCP:

    netsh interface tcp set global autotuninglevel=disabled

    Tive que desabilitar isso em alguns servidores Windows 2008 que administro para poder transferir mais rapidamente arquivos entre Windows 2003 e Windows 2008, talvez ajude com a questão do backup, dependendo do seu cenário.

    sexta-feira, 30 de julho de 2010 18:26
  • Inery,

    Será que não estava ocorrendo uma sobrecarga de pacotes trocados entre sua aplicação e o SQL Server!!!!


    Pedro Antonio Galvão Junior [MVP | Microsoft Evangelist | Microsoft Partner | Engenheiro de Softwares | Especialista em Banco de Dados | SorBR.Net | Professor Universitário]
    sábado, 31 de julho de 2010 00:56
    Moderador
  • Júnior,

    Olhe o artigo escrito por Bob Dorr sobre o erro..

    http://blogs.msdn.com/b/psssql/archive/2010/08/03/how-it-works-error-18056-the-client-was-unable-to-reuse-a-session-with-spid-which-had-been-reset-for-connection-pooling.aspx

    Isto provavelmente vai virar um fix no CU3 para o sql server 2008 r2.

    O interessante é que o erro foi sanado, removendo o usuário da base de dados e depois mapeando o login dele novamente para a base. Ele teve de remover, porque não podemos setar um nome null para o login mapeado.

    Isto se encaixa bem dentro de sua desconfiança... pois se a solução de tempo para tcp funcionou, pode ser a sobrecarga que impediu o cliente receber em tempo hábil o pooling. Ou seja, enviou uma solicitação para aproveitar o pool, algo processou e atrasou o retorno, executando um rollback sobre a conexão do usuário (minha hipótese, não representa uma resposta oficial do produto).

    Bom, realmente é um problema que temos vontade que aconteça em um ambiente de testes para achar a causa exata com dump e etc.. e recomendar o work around até a solução na engine, como Bob Door... :) rsrs

    Atenciosamente,

    Dobereiner Miller Silva Rodrigues - sqlinternal.blogspot.com

     


    Aquilo que sou é aquilo que me foi outorgado
    quinta-feira, 12 de agosto de 2010 02:54