Al momento sei offline in attesa che la connessione Internet venga ristabilita

Avviso di sicurezza Microsoft: una vulnerabilità relativa a SQL Server potrebbe causare l'esecuzione di codice in modalità remota

INTRODUZIONE
Microsoft ha rilasciato un avviso sulla sicurezza riguardo a una vulnerabilità in Microsoft SQL Server che potrebbe consentire l'esecuzione di codice in modalità remota. In questo documento sono contenute ulteriori informazioni correlate alla protezione. Per visualizzare il testo del documento, visitare la pagina Web al seguente indirizzo: In questo articolo viene incluso uno script VB utilizzabile per applicare una soluzione a tutte le istanze in esecuzione di SQL Server sul computer locale.
ESEMPIO DI SCRIPT VB UTILIZZABILE PER APPLICARE LA SOLUZIONE
È possibile utilizzare questo script VB per negare le autorizzazioni di esecuzione al ruolo Public nella stored procedure estesa sp_replwritetovarbin in tutte le versioni interessate di SQL Server in esecuzione sul computer locale.

Microsoft fornisce esempi di programmazione a scopo puramente illustrativo, senza alcuna garanzia di qualsiasi tipo, sia espressa che implicita, ivi incluse, senza limitazioni, le garanzie implicite di commerciabilità o idoneità per uno scopo particolare. In questo articolo si presuppone che l'utente conosca il linguaggio di programmazione in questione e gli strumenti utilizzati per creare ed eseguire il debug delle procedure. Gli esperti Microsoft sono autorizzati a fornire spiegazioni in merito alla funzionalità di una particolare routine, ma in nessun caso a modificare questi esempi per fornire funzionalità aggiuntive o a creare routine atte a soddisfare specifiche esigenze.

Copiare il codice in un file di testo, salvare il file con estensione di file .vbs, quindi eseguire il file di script utilizzando CScript.exe. Lo script effettua iterazioni tra le istanze in esecuzione di SQL Server sul computer locale e applica la soluzione alle versioni interessate. È necessario essere membro del ruolo sysadmin in ciascuna istanza di SQL Server per applicare la soluzione. Se non si dispone di un account Windows appartenente al ruolo sysadmin su tutti i server interessati che eseguono esecuzione SQL Server, è necessario eseguire lo script da vari account. Su Windows Server 2008 e su Windows Vista, se si sta utilizzando l'account dell'amministratore di Windows membro del ruolo sysadmin, è necessario eseguire lo script da un prompt dei comandi con privilegi elevati.
'*************************************************************************************'Descrizione: Questo script effettua iterazioni tra tutte le istanze in esecuzione di SQL Server'            e nega le autorizzazioni di esecuzione in sp_replwritetovarbin al pubblico su tutte'            le versioni interessate.'             LO SCRIPT VIENE FORNITO COME SOLUZIONE E NON DEVE ESSERE UTILIZZATO NEL CASO IN CUI'            VENGA FORNITO E INSTALLATO UN AGGIORNAMENTO DELLA PROTEZIONE.'*************************************************************************************OPTION EXPLICITON ERROR RESUME NEXT' Valori costantiCONST EXIT_SUCCESS       = 0CONST EXIT_FAILURE       = 1CONST EXIT_NOINSTANCES   = -1CONST DEFAULTNAMESPACE   = "root\default"CONST STDREGPROV         = "stdregprov"CONST HKEY_LOCAL_MACHINE = &H80000002CONST REG_MULTI_SZ       = 7CONST REG_SZ             = 1CONST adCmdText          = 1Call VBMain()Function VBMain()    Err.Clear    ON ERROR RESUME NEXT		    Dim sInstances(), strInstance, i, TotalCount    VBMain = EXIT_SUCCESS    If GetInstances(sInstances, TotalCount) = FALSE Then        WScript.Quit EXIT_FAILURE    End If    If IsEmptyNull(sInstances) Then         WScript.Echo "INFO: Nessuna istanza presente."        VBMain = EXIT_NOINSTANCES        Exit Function    End If    For i = 0 To TotalCount-1        strInstance = sInstances(i,0)        GetFullInstance strInstance, sInstances(i,1)        If ApplyFix(sInstances(i,0), strInstance) = FALSE Then            WScript.Echo "ERROR: Impossibile applicare la soluzione a " + sInstances(i,0) + "." + vbCRLF            VBMain = EXIT_FAILURE        End If    Next	    WScript.Echo "INFO: Elaborazione delle istanze in esecuzione di SQL completata."End FunctionFunction GetInstances(ByRef sInstances, ByRef TotalCount)    Err.Clear    ON ERROR RESUME NEXT		    Dim sInstances1, sInstances2, i    Dim instCount1, instCount2    GetInstances = FALSE    If NOT GetRegValue ("", HKEY_LOCAL_MACHINE, "Software\Microsoft\Microsoft SQL Server", "InstalledInstances", sInstances1, REG_MULTI_SZ, TRUE) Then        WScript.Echo "ERROR: impossibile leggere le istanze SQL installate sul computer."        Exit Function    End If    sInstances2 = NULL    If IsOs64Bit() = TRUE Then        If NOT GetRegValue ("", HKEY_LOCAL_MACHINE, "Software\Microsoft\Microsoft SQL Server", "InstalledInstances", sInstances2, REG_MULTI_SZ, FALSE) Then            WScript.Echo "ERROR: impossibile leggere le istanze SQL installate sul computer."            Exit Function        End If    End If    If IsEmptyNull(sInstances1) AND IsEmptyNull(sInstances2) Then         WScript.Echo "INFO: Nessuna istanza presente."        WScript.Quit EXIT_SUCCESS    End If            instCount1 = 0    instCount2 = 0     TotalCount = 0    If IsEmptyNull(sInstances1) = FALSE Then        instCount1 = UBound(sInstances1) + 1        TotalCount = instCount1    End If            If IsEmptyNull(sInstances2) = FALSE Then        instCount2 = UBound(sInstances2) + 1        TotalCount = TotalCount + instCount2    End If    ReDim PRESERVE sInstances(TotalCount,1)    if instCount1 > 0 Then        For i = 0 To UBound(sInstances1)            sInstances(i,0) = sInstances1(i)            sInstances(i,1) = True        Next    End If    If instCount2 >0 Then        For i = 0 To UBound(sInstances2)            sInstances(i+instCount1,0) = sInstances2(i)            sInstances(i+instCount1,1) = FALSE        Next    End If    GetInstances = TRUEEnd FunctionFunction ApplyFix(ByVal strInstance, ByVal strServerName)    Err.Clear    ON ERROR RESUME NEXT    Dim objConn, objCmd, objCmd1, objRS, objRS1    Dim strCommand, strConn    Dim strBuildVersion, strProductLevel, bApplyFix    ' Initialize return value    ApplyFix = FALSE        strConn = "Provider=sqloledb;Initial Catalog=master;Integrated Security=SSPI;Data Source=" + strServerName + ";"    ' La verifica degli errori è stata abbandonata intenzionalmente per non modificare la lunghezza del codice    Set objConn = CreateObject("ADODB.Connection")    Set objCmd = CreateObject("ADODB.Command")    Set objCmd1 = CreateObject("ADODB.Command")        ' Avviare una connessione con il database master    objConn.Open strConn     If ErrorOccurred("Error: Impossibile connettersi a " + strInstance) Then        Set objConn = Nothing        Exit Function    End If    ' Convalidare la versione prima di applicare la correzione    strCommand = "select SERVERPROPERTY('ProductVersion') as version, SERVERPROPERTY('productlevel') as productlevel"    objCmd.ActiveConnection = objConn    objCmd.CommandType = adCmdText    objCmd.CommandText = strCommand    	    Set objRS = objCmd.Execute()    If ErrorOccurred("ERROR: Impossibile eseguire """ + strCommand + """ on " + strInstance) = TRUE Then        objConn.Close()        Set objConn = Nothing        ApplyFix = FALSE        Exit Function       End If    strBuildVersion = objRS("versione")    strProductLevel = UCase(objRS("productlevel"))    bApplyFix = FALSE    ' Applicare la soluzione solamente per le versioni SQL 2000 e SQL 2005 (RTM, SP1 e SP2)    If (CInt(Mid(strBuildVersion,1,1)) = 8) Then        bApplyFix = TRUE    ElseIf CInt(Mid(strBuildVersion,1,1)) = 9 AND (StrComp(strProductLevel,"RTM") = 0 OR StrComp(strProductLevel,"SP1") = 0 OR StrComp(strProductLevel,"SP2") = 0) Then        bApplyFix = TRUE    End If 	    If bApplyFix = TRUE Then        strCommand = "deny execute on sp_replwritetovarbin to public"        objCmd1.ActiveConnection = objConn        objCmd1.CommandType = adCmdText        objCmd1.CommandText = strCommand        Set objRS1 = objCmd1.Execute()        If ErrorOccurred("ERROR: Impossibile eseguire """ + strCommand + """ on " + strInstance) = FALSE Then            WScript.Echo "INFO: Soluzione applicata correttamente a " + strInstance + " (" + strBuildVersion + ")." + vbCRLF            ApplyFix = TRUE        End If    Else        WScript.Echo "INFO: Ignorare la raccolta di informazioni per " + strInstance + " (" + strBuildVersion + ") in quanto l'istanza non è vulnerabile." + vbCRLF        ApplyFix = TRUE    End If    objConn.Close()    Set objConn = Nothing    Set objCmd = Nothing    Set objCmd1 = Nothing    Set objRS = Nothing    Set objRS1 = NothingEnd FunctionPrivate Function GetRegValue (ByVal strMachineName, ByVal hMainKey, ByVal strPath, ByVal strValueName, ByRef strValue, ByVal iValueType, ByVal b32bit)    Err.Clear    ON ERROR RESUME NEXT	    Dim objLocator, objServices, objRegistry, objCtx    Dim sMultiStrings, lRc    GetRegValue = TRUE    'Connect to WMI and get an object to STDREGPROV class.    Set objCtx = CreateObject("WbemScripting.SWbemNamedValueSet")    If b32bit = TRUE Then        objCtx.Add "__ProviderArchitecture", 32    Else        objCtx.Add "__ProviderArchitecture", 64    End If    objCtx.Add "__RequiredArchitecture", TRUE    set objLocator = createobject("wbemscripting.swbemlocator")    set objServices = objLocator.connectserver(strMachineName,DEFAULTNAMESPACE, "", "",,,,objCtx)    set objRegistry = objServices.get(STDREGPROV)    If ErrorOccurred("ERROR: Impossibile connettersi allo spazio dei nomi WMI " + DEFAULTNAMESPACE) Then        GetRegValue = FALSE        Exit Function    End If     lRc = 0    Select Case iValueType        ' We only care about REG_MULTI_SZ        Case REG_MULTI_SZ            strValue = ""            lRC = objRegistry.GetMultiStringValue(hMainKey, strPath, strValueName, sMultiStrings)            strValue = sMultiStrings        Case REG_SZ            strValue = ""            lRC = objRegistry.GetStringValue(hMainKey, strPath, strValueName, strValue)        Case Else            GetRegValue = FALSE    End Select    If lRc = 2 Or lRc = 3 Then        GetRegValue = TRUE        strValue = ""    ElseIf Err.Number OR lRc <> 0 Then        GetRegValue = FALSE    End If        Set MAPIMessage = Nothing    Set objServices = Nothing    Set MAPIMessage = NothingEnd FunctionFunction IsEmptyNull(sCheck)    IsEmptyNull = FALSE    If IsObject(sCheck) Then Exit Function    If IsObject(sCheck) Then Exit Function    If VarType(sCheck) = vbEmpty Then IsEmptyNull = TRUE : Exit Function    If VarType(sCheck) = vbEmpty Then IsEmptyNull = TRUE : Exit Function    If sCheck = "" Then IsEmptyNull = TRUEEnd FunctionPrivate Function ErrorOccurred (ByVal strIn)    If Err.Number <> 0 Then        WScript.Echo strIn        WScript.Echo "ERROR: 0x" & Err.Number & " - " & Err.Description        Err.Clear        ErrorOccurred = TRUE    Else        ErrorOccurred = FALSE    End IfEnd FunctionFunction IsOs64Bit()    Err.Clear    ON ERROR RESUME NEXT        Dim objProc    Set objProc = GetObject("winmgmts:root\cimv2:Win32_Processor='cpu0'")    If objProc.Architecture = 0 Then        IsOs64Bit = FALSE    Else        IsOs64Bit = TRUE    End IfEnd FunctionFunction GetFullInstance (ByRef strInstanceName, ByVal b32bit)    Err.Clear    ON ERROR RESUME NEXT     Dim objServices, objClusters, objCluster    Dim strMacName, isEmpty    Dim strKey, strInstID        GetFullInstance = TRUE        If strComp(UCase(strInstanceName), "MICROSOFT##SSEE", 1) = 0 Then        strInstanceName = "np:\\.\pipe\mssql$microsoft##ssee\sql\query"        Exit Function    End if    strMacName = ""    Set objServices = GetObject("winmgmts:root\cimv2")    ' Query Cluster service    Set objClusters = objServices.ExecQuery ("select * from win32_service where Name='ClusSvc' AND Started = TRUE")    isEmpty = TRUE    If Err.Number = 0 Then        For each objCluster in objClusters            isEmpty = FALSE        Next    End If    Set objServices = Nothing    Set objClusters = Nothing    If isEmpty = TRUE Then        strInstanceName = BuildInstanceName (".", strInstanceName)        Exit Function    End If        ' Il raggiungimento di questa posizione indica che il computer è un nodo cluster.    ' Effettuare query del Registro di sistema per determinare se l'istanza SQL sia di tipo cluster.    ' Per la query SQL 2000 il seguente valore    ' HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Microsoft SQL Server\<InstanceName>\Cluster    ' ClusterName    strKey = "SOFTWARE\Microsoft\Microsoft SQL Server\" + strInstanceName + "\Cluster"    GetRegValue "", HKEY_LOCAL_MACHINE, strKey, "ClusterName", strMacName, REG_SZ, b32bit    If StrComp(strMacName, "") <> 0 Then        strInstanceName = BuildInstanceName (strMacName, strInstanceName)        Exit Function    End If    strKey = "SOFTWARE\Microsoft\" + strInstanceName + "\Cluster"    GetRegValue "", HKEY_LOCAL_MACHINE, strKey, "ClusterName", strMacName, REG_SZ, b32bit    If StrComp(strMacName, "") <> 0 Then        strInstanceName = BuildInstanceName (strMacName, strInstanceName)        Exit Function    End If    ' Provare ad eseguire una ricerca del valore del Registro di sistema per le istanze 2005/2008    'HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Microsoft SQL Server\Instance Names\SQL    ' RegValue = InstanceName    strInstID = ""    strKey = "SOFTWARE\Microsoft\Microsoft SQL Server\Instance Names\SQL"    GetRegValue "", HKEY_LOCAL_MACHINE, strKey, strInstanceName, strInstID, REG_SZ, b32bit        If StrComp(strInstID, "") = 0 Then        ' Se la chiave non esiste, tornare all'istanza locale SQL 2000        strInstanceName = BuildInstanceName (".", strInstanceName)        Exit Function    End If    strKey = "SOFTWARE\Microsoft\Microsoft SQL Server\" + strInstID + "\Cluster"    GetRegValue "", HKEY_LOCAL_MACHINE, strKey, "ClusterName", strMacName, REG_SZ, b32bit        If StrComp(strMacName, "") = 0 Then        strMacName = "."    End If    strInstanceName = BuildInstanceName (strMacName, strInstanceName)End FunctionFunction BuildInstanceName (ByVal strMachineName, ByVal strInstanceName)    Dim strPrefix        strPrefix = ""    If StrComp(strMachineName, ".") = 0 Then        strPrefix = "lpc:"    End If        If strComp(UCase(strInstanceName), "MSSQLSERVER", 1) = 0 Then        BuildInstanceName = strPrefix + strMachineName    Else        BuildInstanceName = strPrefix + strMachineName + "\" + strInstanceName    End ifEnd Function
Per ulteriori informazioni su CScript.exe, visitare il seguente sito Web di Microsoft: Nota Si consiglia di non utilizzare lo script se è stato fornito e installato un aggiornamento della protezione.
PROBLEMI NOTI CHE POSSONO VERIFICARSI QUANDO SI ESEGUE LO SCRIPT

Problema 1

Quando si esegue lo script, viene visualizzato il seguente messaggio di errore:
ERRORE: impossibile eseguire "deny execute on sp_replwritetovarbin to public" in <instancename>
ERRORE: 0x-2147217900 - Impossibile trovare l'oggetto 'sp_replwritetovarbin', perché non esiste oppure non si dispone delle autorizzazioni.
ERRORE: impossibile applicare la soluzione in <instancename>.

Causa 1

Questo messaggio di errore viene visualizzato se non si dispone delle autorizzazioni necessarie per applicare la modifica. Questo messaggio di errore indica che l'utente era in grado di effettuare correttamente l'accesso all'istanza "<instancename>".

Questo messaggio di errore si verifica in genere in SQL Server Express in cui il gruppo "Built-In\Users" dispone dell'accesso al database per impostazione predefinita. Tuttavia, il gruppo non è un membro del ruolo sysadmin.

Questo messaggio di errore può verificarsi anche se viene rimossa la procedura sp_replwritetovarbin. Questa è la raccomandazione di un rapporto di terze parti. Non è consigliabile eliminare la stored procedure. Al contrario, è consigliabile applicare questa risoluzione.

Risoluzione 1

Verificare che l'account utilizzato per la connessione sia un membro del ruolo sysadmin in questa istanza del database. Se l'account non è un membro, aggiungere l'utente con cui ci si connette al ruolo sysadmin oppure utilizzare un altro account utente. Per SQL Server 2005 e versioni precedenti, il gruppo "Built-in\Administrators" è un membro del ruolo sysadmin per impostazione predefinita. Quando si esegue questo script in Windows Vista o in Windows Server 2008, assicurarsi di eseguirlo da un prompt dei comandi "con privilegi elevati".

Problema 2

Se si esegue lo script in SQL Server 2005, viene visualizzato il seguente messaggio di errore:
Errore: Impossibile connettersi a <instancename>
ERRORE: 0x-2147217843 - Impossibile eseguire l'accesso per l'utente '<user>'.
ERRORE: impossibile applicare la soluzione in <instancename>.

Causa 2

Questo messaggio viene visualizzato nel caso in cui non sia stato possibile connettersi all'istanza "<instancename>" sebbene l'istanza esista.

Questo messaggio di errore si verifica in genere quando si effettua la connessione al database interno di Windows oppure alle istanze Microsoft SQL Server 2000 Desktop Edition (Windows). In genere, nessun account utente ha accesso a questi database.

Risoluzione 2

Verificare che l'account utilizzato per eseguire lo script abbia accesso al database membro del ruolo sysadmin.

Non è consigliabile aggiungere utenti individuali ai database interno di Windows e ai database Microsoft SQL Server 2000 Desktop Edition (Windows). Se si esegue questa operazione, gli utenti aggiunti potrebbero interferire con il normale funzionamento dei database. In questo caso, assicurarsi di effettuare la connessione da un account membro del ruolo sysadmin. Il gruppo "Built-in\Administrators" in Windows è in genere membro del ruolo sysadmin per impostazione predefinita, in SQL Server 2005 e nelle versioni precedenti. Quando si esegue questo script in Windows Vista o in Windows Server 2008, assicurarsi di eseguirlo da un prompt dei comandi "con privilegi elevati".

Problema 3

È possibile notare un'istanza di un database denominata MICROSOFT##SSEE. Tuttavia, il database non è stato installato.

Causa 3

Questo database è il database interno di Windows, noto anche come "SQL Server Embedded Edition" o talvolta definito "database interno di Windows" o "Microsoft SQL Server 2000 Desktop Edition (Windows)". Viene installato con alcuni prodotti Microsoft, compreso SharePoint Services.

Risoluzione 3

Lo script della soluzione è progettato per funzionare con il databse interno di Windows. Non è richiesta nessuna azione da parte dell'utente.

Alcune applicazioni non rimuovono il database interno di Windows dopo essere state disinstallate. Per ulteriori informazioni sulla rimozione del database interno di Windows, fare clic sul numero dell'articolo della Microsoft Knowledge Base riportato di seguito:
920277 Il database inerno di Windows non è elencato nello strumento Installazione applicazioni e non viene rimosso quando si rimuove Windows SharePoint Services 3.0 dal computer

Problema 4

Quando si esegue lo script, viene visualizzato il seguente messaggio di errore:
Errore: Impossibile connettersi a .\<instancename>
ERRORE: 0x-2147467259 - [DBNETLIB][ConnectionOpen (Connect()).]SQL Server non esiste o l'accesso è stato negato

Causa 4

Questo messaggio di errore viene visualizzato quando si verificano le seguenti condizioni:
  • Si dispone della versione a 32 bit di SQL Server 2000 iinstallata su un sistema operativo x64.
  • Si dispone di una versione a 64 bit di SQL Server 2005 o di SQL Server 2008 installata sul computer.
Questo messaggio di errore viene visualizzato quando lo script utilizza la versione a 64 bit del file dbmslpcn.dll Questa versione non è in grado di comunicare con le istanze WoW di SQL Server 2000.

Risoluzione 4

Per avviare lo script, utilizzare la versione a 32 bit del file cscript.exe dalla cartella %WINDOWS%\SysWOW64. Viene così caricata la versione a 32 bit del file dbmslpcn.dll, in grado di rilevare le istanze WoW.
Riferimenti
Per ulteriori informazioni su come identificare la versione e l'edizione di SQL Server, fare clic sul numero dell'articolo della Microsoft Knowledge Base riportato di seguito:
321185Identificazione della versione e dell'edizione di SQL Server
Informazioni
Nella tabella che segue sono elencate le revisioni tecniche più significative di questo articolo. Il numero di revisione e la data dell'ultima revisione riportati in questo articolo potrebbero indicare revisioni editoriali o strutturali di lieve entità di questo articolo non incluse nella tabella.
DateRevisioni
31/12/2008Include uno script aggiornato in grado di rilevare istanze di cluster di failover.
30/12/2008Include uno script aggiornato in grado di rilevare versioni a 32 bit di SQL Server in esecuzione sulle versione a 64 bit di Windows.
update security_patch security_update security bug flaw vulnerability malicious attacker exploit registry unauthenticated buffer overrun overflow specially-formed scope specially-crafted denial of service DoS
Proprietà

ID articolo: 961040 - Ultima revisione: 01/06/2009 15:41:05 - Revisione: 3.0

Windows Internal Database, Microsoft SQL Server 2005 Service Pack 2, Microsoft SQL Server 2000 Desktop Engine (Windows), Microsoft SQL Server 2000 Desktop Engine (Windows), Microsoft SQL Server 2000 Service Pack 4

  • kbpubtypekc kbfix kbbug kbsecvulnerability kbsecbulletin kbsecurity KB961040
Feedback
script>