Come installare a livello di programmazione i certificati SSL per Internet Information Server (IIS)

Traduzione articoli Traduzione articoli
Identificativo articolo: 313624 - Visualizza i prodotti a cui si riferisce l?articolo.
Espandi tutto | Chiudi tutto

In questa pagina

importante In questo articolo contiene informazioni di modifica della metabase. Prima di modificare la metabase, verificare di avere a disposizione una copia di backup poter ripristinare se si verifica un problema. Per informazioni su come effettuare questa operazione, vedere "backup o ripristino configurazione" della Guida in Microsoft Management Console (MMC).

Sommario


In questo articolo viene descritto come creare a livello di programmazione e quindi a installare Secure Sockets Layer (SSL) certificati per Internet Information Server (IIS). Mentre IIS versione 4.0 e IIS versione 5.0 ogni forniscono un'interfaccia di utente (UI) consentono di creare e quindi per installare certificati server SSL, Ŕ possibile inoltre completare l'operazione a livello di programmazione.



Procedura per la creazione e quindi installare i certificati SSL

Per creare a livello di programmazione e quindi installare i certificati SSL per server IIS, attenersi alla seguente procedura:
  1. ╚ necessario inviare una richiesta all'autoritÓ di certificazione per emettere un certificato server. Se si dispone giÓ del certificato e quindi si memorizza nel file sul server IIS, non inviare la richiesta.
  2. Importare il certificato all'archivio certificati appropriato.
  3. Configurare IIS per utilizzare il certificato ottenuto al passaggio 1.



Configurare IIS per creare e quindi installare SSL certificati

avviso Se si modifica la metabase in modo non corretto, si possono provocare problemi gravi che potrebbero richiedere la reinstallazione dei prodotti che utilizza la metabase. Microsoft non garantisce che i problemi derivanti se si modifica in modo non corretto della metabase possano essere risolti. La modifica della metabase a proprio rischio.

Nota Eseguire sempre il backup della metabase prima di modificarlo. Attenersi alla procedura per configurare IIS per creare e quindi a installare SSL certificati:
  1. Utilizzare API di crittografia di Microsoft Windows per ottenere l'identificazione personale di proprietÓ del certificato.
  2. Occorre impostare la proprietÓ della metabase di IIS, SSLCertHash al valore del identificazione personale .
  3. Occorre impostare la proprietÓ della metabase di IIS, SSLStoreName all'archivio che si desidera utilizzare.
Vedere le sezioni articolo seguenti per esempi di codice ottenere un' identificazione personale del certificato, quindi ottenere la proprietÓ SSLCertHash :
C Code to Obtain the Thumbprint of a Server Authentication Certificate
C Code to Enter the SSLCertHash Property into the Metabase



Procedura per attivare SSL in un sito Web specifico

Dopo aver eseguito la procedura descritta nella sezione "Configurazione IIS per creare e quindi per installare SSL certificati", Ŕ possibile attivare SSL in un particolare sito o in una cartella particolare. A tale scopo, Ŕ necessario attivare SSL opzioni nella cartella che si desidera utilizzare. Le seguenti operazioni corrispondono a ogni passaggio descritto nella sezione "Configure IIS to Create and Then to Install SSL Certificates":
  1. Quando si chiama il metodo CEnroll::createPKCS10() , viene creata la richiesta di certificato. Impostare l'utilizzo il seguente valore predefinito: szOID_PKIX_KP_SERVER_AUTH :
    #define szOID_PKIX_KP_SERVER_AUTH       "1.3.6.1.5.5.7.3.1"		
  2. Quando si chiama il metodo di () ICertRequest:: Submit , una richiesta per il certificato viene inviata all'autoritÓ di certificazione.
  3. Il certificato viene recuperato dall'autoritÓ di certificazione e quindi viene installato nell'archivio appropriato. Il server IIS Gestione guidata certificati Cerca solo i certificati che Ŕ possibile utilizzare per l'autenticazione del server nell'archivio certificati computer locale.




Procedura per configurare IIS

Dopo aver salvato il certificato all'archivio, Ŕ necessario configurare IIS come illustrato di seguito:
  1. Utilizzare il metodo di CertGetCertificateContextProperty() per ottenere i valori della proprietÓ identificazione personale e la proprietÓ CERT_HASH_PROP_ID . La funzione di CertGetCertificateContextProperty() utilizza il metodo CryptHashCertificate() per calcolare il valore della proprietÓ CERT_HASH_PROP_ID . Se il valore HASH non esiste, CertGetCertificateContextProperty() restituisce l'algoritmo SHA1 .
  2. ╚ necessario creare una nuovo binario proprietÓ della metabase SSLCertHash , che corrisponde al sito Web. Impostare SSLCertHash il certificato di identificazione personale ottenuta al passaggio 1 di questa sezione. Quando si verifica questo problema, lo schema specifica in modo non corretto la proprietÓ SSLCertHash come una stringa con terminata null espansa, anzichÚ come dati binari, e quindi non Ŕ possibile utilizzare oggetti Admin di IIS per importare SSLCertHash . ╚ possibile utilizzare solo gli oggetti di Base Admin di IIS per importare questo valore. Per utilizzare SSLCertHash con gli oggetti di Base Admin di IIS, Ŕ necessario utilizzare il valore Decimal, 5506.
  3. ╚ necessario creare una nuova stringa di proprietÓ della metabase, SSLStoreName , per il sito Web corrispondente. Impostare SSLStoreName sulla stringa MY valore. ╚ possibile impostare SSLStoreName tramite oggetti Admin di IIS (ad esempio, in script ADSI) o tramite oggetti base di amministrazione di IIS. Per utilizzare SSLStoreName con gli oggetti di base Admin di IIS, utilizzare il valore decimale, per il 5511.




Codice c per ottenere l'identificazione personale di un certificato di autenticazione server

Il codice di esempio Microsoft C riportato di seguito viene descritto come ottenere la proprietÓ identificazione personale di un certificato di autenticazione server:
#include <stdio.h>
#include <windows.h>
#include <wincrypt.h>
#define MY_TYPE  (PKCS_7_ASN_ENCODING | X509_ASN_ENCODING)

//--------------------------------------------------------------------
//    Define the name of the store where the needed certificate
//    can be found. 

#define CERT_STORE_NAME  L"MY"

//--------------------------------------------------------------------
//   Declare local functions.
//   Local function definitions follow main.

void HandleError(char *s);

void main(void)
{
//--------------------------------------------------------------------
// Declare and initialize local variables. 
// This includes initializing a pointer to the message. 
// Usually, the message will exist somewhere and a pointer will
// be passed to the application.

//--------------------------------------------------------------------
// System store handle

HCERTSTORE hStoreHandle;   

//--------------------------------------------------------------------
// Pointer to a certificate

PCCERT_CONTEXT pCert;
PCCERT_CONTEXT pPrevCert;
 
LPBYTE pEncodedBytes = NULL;
LPBYTE pHash;
DWORD cbData, i;

//--------------------------------------------------------------------
// Open a certificate store.

if ( !( hStoreHandle = CertOpenStore(
   CERT_STORE_PROV_SYSTEM,
   0,
   NULL,
   CERT_SYSTEM_STORE_LOCAL_MACHINE,
   CERT_STORE_NAME)))
{
     HandleError("The MY store could not be opened.");
}


pPrevCert = NULL;

for (; ((pCert = CertEnumCertificatesInStore(hStoreHandle, pPrevCert)) 
	                                         != NULL);
    pPrevCert = pCert)
{
    CERT_ENHKEY_USAGE *pKeyUsage;
    DWORD j, nLen;
    BOOL bFound = FALSE;
    char certName[1024];

    nLen = sizeof(certName);
    certName[0] = 0;
    if (CertNameToStr(MY_TYPE, &(pCert->pCertInfo->Subject),
        CERT_X500_NAME_STR,
        certName,
        sizeof(certName)))
    {
        printf("Checking %s certificate\n", certName);
    }

    cbData = 0;
    if (!CertGetEnhancedKeyUsage(pCert,
        0,
        NULL,
        &cbData) || cbData == 0)
    {
        if (GetLastError() == CRYPT_E_NOT_FOUND)
        {
            printf("%s certificate is for all key usages\n", certName);
            break;
        }
        else
            printf("CertGetEnhancedKeyUsage failed with error code : %08X\n",
                GetLastError());
    }
    pKeyUsage = (CERT_ENHKEY_USAGE *)
        HeapAlloc(GetProcessHeap(), 0, cbData);
    if (pKeyUsage == NULL)
    {
        printf("HeapAlloc failed with error code : %08X\n",
            GetLastError());
        HandleError("Certificate not found.");
    }
    if (!CertGetEnhancedKeyUsage(pCert,
        0,
        pKeyUsage,
        &cbData))
    {
        if (GetLastError() == CRYPT_E_NOT_FOUND)
        {
            printf("%s certificate is for all key usages\n", certName);
            HeapFree(GetProcessHeap(), 0, pKeyUsage);
            break;
        }
        else
        {
            printf("CertGetEnhancedKeyUsage failed with error code : %08X\n",
                GetLastError());
            HeapFree(GetProcessHeap(), 0, pKeyUsage);
            continue;
        }
    }

    if (pKeyUsage->cUsageIdentifier == 0)
    {
        printf("%s certificate is for all key usages\n", certName);
        HeapFree(GetProcessHeap(), 0, pKeyUsage);
        break;
    }

    bFound = FALSE;
    for (j = 0; j < pKeyUsage->cUsageIdentifier; j++)
    {
        if (strcmpi(pKeyUsage->rgpszUsageIdentifier[j], 
			        szOID_PKIX_KP_SERVER_AUTH) == 0)
        {
            printf("%s certificate is for Server Authentication\n", 
				   certName);
            bFound = TRUE;
            break;
        }
    }

    HeapFree(GetProcessHeap(), 0, pKeyUsage);
    if (bFound)
        break;
}

if (pCert == NULL)
   HandleError("Certificate not found.");

if (pPrevCert)
{
    CertFreeCertificateContext(pPrevCert);
    pPrevCert = NULL;
}

/// CASE 2 Get the hash from the certificate
pHash = NULL;
cbData = 0;
CertGetCertificateContextProperty(pCert, CERT_HASH_PROP_ID, NULL, &cbData);
if (cbData == 0)
{
   HandleError("CertGetCertificateContextProperty 1 failed");
}

pHash = (LPBYTE)HeapAlloc(GetProcessHeap(), 0, cbData);
if (pHash == NULL)
{
   HandleError("HeapAlloc failed");
}
if (!CertGetCertificateContextProperty(pCert, CERT_HASH_PROP_ID, pHash, 
	                                   &cbData))
{
   HandleError("CertGetCertificateContextProperty 2 failed");
}

printf("CERT_HASH_PROP_ID Length is %d\n", cbData);
printf("CERT_HASH_PROP_ID BYTES [", cbData);

for (i = 0; i < cbData; i++)
{
    printf("%02X", pHash[i]);
}
printf("]\n");

//--------------------------------------------------------------------
// Clean up and free memory.

if (pEncodedBytes)
    HeapFree(GetProcessHeap(), 0, pEncodedBytes);

if (pHash)
    HeapFree(GetProcessHeap(), 0, pHash);

if(pCert)
     CertFreeCertificateContext(pCert);
if(CertCloseStore(
      hStoreHandle, 
      CERT_CLOSE_STORE_CHECK_FLAG))
{
    printf("The store closed and all certificates are freed. \n");
}
else
{
    printf("Store closed -- \n"
          "not all certificates, CRLs or CTLs were freed");
}
} // End of main

//--------------------------------------------------------------------
//  This example uses the function HandleError, a simple error
//  handling function, to print an error message to the standard error 
//  (stderr) file and exit the program. 
//  For most applications, replace this function with one 
//  that does more extensive error reporting.

void HandleError(char *s)
{
    fprintf(stderr,"An error occurred in running the program. \n");
    fprintf(stderr,"%s\n",s);
    fprintf(stderr, "Error number %x.\n", GetLastError());
    fprintf(stderr, "Program terminating. \n");
    exit(1);
} // End of HandleError




Codice c per immettere la proprietÓ SSLCertHash della Metabase

Nell'esempio di codice riportato di seguito viene descritto come utilizzare gli oggetti di Base Admin di IIS per impostare il metodo SSLCertHash nella metabase. Il codice riportato di seguito utilizza una matrice di binaria arbitraria come identificazione personale del certificato. Codice effettivo sarebbe di utilizzare il valore di identificazione personale che ottiene quando si esegue il codice nella sezione "Ottenere l'identificazione personale di un server certificato di autenticazione". A seconda di come si definisce il metodo SetData in fase di compilazione, Ŕ possibile impostare SSLCertHash oppure se Ŕ giÓ stato configurato SSL per il sito Web, Ŕ possibile ottenere il SSLCertHash esistente. The SSLCertHash method return the existing CertHash:
#define UNICODE // unicode must be defined for Metabase access
#define INITGUID 
#include <windows.h>
#include <httpfilt.h>
#include <stdio.h> 

#define SETDATA

#include <iadmw.h>    // COM Interface header 
#include <iiscnfg.h>  // MD_ & IIS_MD_ #defines 



extern "C" wmain (int argc, TCHAR ** argv)
{  
	IMSAdminBase  *pIMeta;  
	METADATA_HANDLE MyHandle; 
    HRESULT hres;
   	METADATA_RECORD record = {0};
    TCHAR szError [2048];
	BYTE *myData=NULL;
    DWORD dwSize = sizeof (record);
 	DWORD i;

	// this just a sample of some thumbprint
	BYTE bar[]={0x24, 0xC6, 0xBA, 0xBB, 0x81, 0x76, 0x05, 0xC9, 0xC3, 
		        0x97, 0x6D, 0x4D, 0xEB, 0x85, 0x8F, 0x4F, 0xBF, 0x38,
				0xFD};
    
    
    CoInitialize (NULL);
    
    // get a pointer to the IIS Admin Base Object
	hres = CoCreateInstance(CLSID_MSAdminBase, NULL, CLSCTX_ALL, 
			IID_IMSAdminBase, (void **) &pIMeta);  
	if (FAILED(hres))  
	{
	    wsprintf (szError, L"CoCreateInstance Failed. Error: %x\n", hres);
        printf ("%S\n", szError);
		CoUninitialize();
        return TRUE;  
	}
    
    // for this test use only 1st server instance
    hres = pIMeta->OpenKey(METADATA_MASTER_ROOT_HANDLE, L"/LM", 
		METADATA_PERMISSION_READ|METADATA_PERMISSION_WRITE, 20, &MyHandle); 
	if (FAILED (hres) )
	{
		wsprintf (szError, L"OpenKey Failed. Error: %x\n", hres);
        printf ("%S\n", szError);
		goto clean;
	}
    
	// SSLCertHash = 5506
	record.dwMDIdentifier =  5506;
    record.dwMDAttributes =METADATA_INHERIT;
    record.dwMDUserType=IIS_MD_UT_SERVER;
    record.dwMDDataType= BINARY_METADATA;
    record.pbMDData = (unsigned char *) myData;

#ifndef SETDATA
#pragma message ("Building for GetData\n")    
	again:
    hres = pIMeta->GetData (MyHandle,argv[1], &record, &dwSize);
   	if (FAILED (hres) )
	{
		if (hres == MD_ERROR_DATA_NOT_FOUND)
		{
			printf ("%S\n", L"Data not found, no certificate is set!");
			goto clean;
		}
		else if (HRESULT_CODE(hres)==ERROR_INSUFFICIENT_BUFFER)
		{
			record.dwMDDataLen=dwSize;
			myData = (LPBYTE)HeapAlloc(GetProcessHeap(), 0, dwSize);
			record.pbMDData  = (unsigned char *)myData;
		    goto again;
		}
		else  
		{
			wsprintf (szError, L"GetData Failed. Error: %x\n", hres);
			printf ("%S\n", szError);
			goto clean;;
		}
	}

	printf ("%S", L"Got thumbprint. You can compare" 
		          L" it with the MMC for IIS value:\n");	
	for ( i=0; i<(record.dwMDDataLen/sizeof (BYTE)); i++)		
		printf ("%2X ", myData[i]);  
	HeapFree(GetProcessHeap(), 0, myData);
#else
#pragma message ("Building for SetData\n")

	
	record.pbMDData = bar;
	record.dwMDDataLen = 19; // in real code it should be the size 
                                                   // of the thumbprint buffer
	hres = pIMeta->SetData (MyHandle,argv[1], &record);
	if (FAILED (hres) )
	{
		printf ("Set data failed: 0x%x!\n", hres);
		goto clean;
	}
	else
		printf ("New thumbprint is set\n");
#endif

clean:
	pIMeta->CloseKey(MyHandle); 
	pIMeta->SaveData();
	pIMeta->Release();
	CoUninitialize();

	return 1;
}



Riferimenti

Per ulteriori informazioni, fare clic sul numero dell'articolo della Microsoft Knowledge Base riportato di seguito riportato:
315588Come proteggere un'applicazione ASP.NET mediante i certificati del lato client

ProprietÓ

Identificativo articolo: 313624 - Ultima modifica: martedý 11 luglio 2006 - Revisione: 2.2
Le informazioni in questo articolo si applicano a:
  • Microsoft Internet Information Server 4.0
  • Microsoft Internet Information Services 5.0
Chiavi:á
kbmt kbcrypt kbapi kbhowtomaster kbsecurity kbisapiext kbhowto KB313624 KbMtit
Traduzione automatica articoli
Il presente articolo Ŕ stato tradotto tramite il software di traduzione automatica di Microsoft e non da una persona. Microsoft offre sia articoli tradotti da persone fisiche sia articoli tradotti automaticamente da un software, in modo da rendere disponibili tutti gli articoli presenti nella nostra Knowledge Base nella lingua madre dell?utente. Tuttavia, un articolo tradotto in modo automatico non Ŕ sempre perfetto. Potrebbe contenere errori di sintassi, di grammatica o di utilizzo dei vocaboli, pi¨ o meno allo stesso modo di come una persona straniera potrebbe commettere degli errori parlando una lingua che non Ŕ la sua. Microsoft non Ŕ responsabile di alcuna imprecisione, errore o danno cagionato da qualsiasi traduzione non corretta dei contenuti o dell?utilizzo degli stessi fatto dai propri clienti. Microsoft, inoltre, aggiorna frequentemente il software di traduzione automatica.
Clicca qui per visualizzare la versione originale in inglese dell?articolo: 313624
LE INFORMAZIONI CONTENUTE NELLA MICROSOFT KNOWLEDGE BASE SONO FORNITE SENZA GARANZIA DI ALCUN TIPO, IMPLICITA OD ESPLICITA, COMPRESA QUELLA RIGUARDO ALLA COMMERCIALIZZAZIONE E/O COMPATIBILITA' IN IMPIEGHI PARTICOLARI. L'UTENTE SI ASSUME L'INTERA RESPONSABILITA' PER L'UTILIZZO DI QUESTE INFORMAZIONI. IN NESSUN CASO MICROSOFT CORPORATION E I SUOI FORNITORI SI RENDONO RESPONSABILI PER DANNI DIRETTI, INDIRETTI O ACCIDENTALI CHE POSSANO PROVOCARE PERDITA DI DENARO O DI DATI, ANCHE SE MICROSOFT O I SUOI FORNITORI FOSSERO STATI AVVISATI. IL DOCUMENTO PUO' ESSERE COPIATO E DISTRIBUITO ALLE SEGUENTI CONDIZIONI: 1) IL TESTO DEVE ESSERE COPIATO INTEGRALMENTE E TUTTE LE PAGINE DEVONO ESSERE INCLUSE. 2) I PROGRAMMI SE PRESENTI, DEVONO ESSERE COPIATI SENZA MODIFICHE, 3) IL DOCUMENTO DEVE ESSERE DISTRIBUITO INTERAMENTE IN OGNI SUA PARTE. 4) IL DOCUMENTO NON PUO' ESSERE DISTRIBUITO A SCOPO DI LUCRO.

Invia suggerimenti

 

Contact us for more help

Contact us for more help
Connect with Answer Desk for expert help.
Get more support from smallbusiness.support.microsoft.com