Ejemplo n.º 1
0
/* sqExtractPeerName: Extract the name from the cert of the remote peer. */
static int sqExtractPeerName(sqSSL *ssl) {
	SECURITY_STATUS ret;
	PCCERT_CONTEXT certHandle = NULL;
	PCERT_NAME_INFO certInfo = NULL;
	PCERT_RDN_ATTR certAttr = NULL;
	DWORD dwSize = 0;
	char tmpBuf[1024];

	if(ssl->peerName) {
		free(ssl->peerName);
		ssl->peerName = NULL;
	}
	ret = QueryContextAttributes(&ssl->sslCtxt, SECPKG_ATTR_REMOTE_CERT_CONTEXT, (PVOID)&certHandle);
	/* No credentials were provided; can't extract peer name */
	if(ret == SEC_E_NO_CREDENTIALS) return 1;

	if(ret != SEC_E_OK) {
		if(ssl->loglevel) printf("sqExtractPeerName: QueryContextAttributes failed (code = %x)\n", ret);
		return 0;
	}

	/* Figure out the size of the blob */
	if(!CryptDecodeObject(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING, X509_NAME,
		certHandle->pCertInfo->Subject.pbData,
		certHandle->pCertInfo->Subject.cbData,
		0, NULL, &dwSize)) {
			if(ssl->loglevel) printf("sqExtractPeerName: CryptDecodeObject failed\n");
			return 0;
	}
	
	/* Get the contents */
	certInfo = alloca(dwSize);
	if(!CryptDecodeObject(X509_ASN_ENCODING | PKCS_7_ASN_ENCODING, X509_NAME, 
		certHandle->pCertInfo->Subject.pbData,
		certHandle->pCertInfo->Subject.cbData,
		0, certInfo, &dwSize)) {
			if(ssl->loglevel) printf("sqExtractPeerName: CryptDecodeObject failed\n");
			return 0;
	}

	/* Fetch the CN from the cert */
	certAttr = CertFindRDNAttr(szOID_COMMON_NAME, certInfo);
	if(certAttr == NULL) return 0;

	/* Translate from RDN to string */
	if(CertRDNValueToStr(CERT_RDN_PRINTABLE_STRING, &certAttr->Value, tmpBuf, sizeof(tmpBuf)) == 0) return 0;
	ssl->peerName = _strdup(tmpBuf);
	if(ssl->loglevel) printf("sqExtractPeerName: Peer name is %s\n", ssl->peerName);

	CertFreeCertificateContext(certHandle);

	return 1;
}
Ejemplo n.º 2
0
    tstring Win32Certificate::getCertAttribute(const char * whichAttr)
    {
        PCCERT_CONTEXT pContext = getWin32Context();

        // How much space do we need.
        DWORD cbNameInfo = 0;

        DWORD dwRet = CryptDecodeObject(
            X509_ASN_ENCODING,
            X509_NAME,
            pContext->pCertInfo->Subject.pbData,
            pContext->pCertInfo->Subject.cbData,
            CRYPT_DECODE_NOCOPY_FLAG,
            NULL,
            &cbNameInfo);

        DWORD dwErr = GetLastError();

        RCF_VERIFY(
            dwRet, 
            RCF::Exception(
                _RcfError_CryptoApiError("CryptDecodeObject()"), 
                dwErr, 
                RCF::RcfSubsystem_Os));

        std::vector<char> vec(cbNameInfo);

        // Retrieve name info.
        dwRet = CryptDecodeObject(X509_ASN_ENCODING,
            X509_NAME,
            pContext->pCertInfo->Subject.pbData,
            pContext->pCertInfo->Subject.cbData,
            CRYPT_DECODE_NOCOPY_FLAG,
            &vec[0],
            &cbNameInfo);

        dwErr = GetLastError();

        RCF_VERIFY(
            dwRet, 
            RCF::Exception(
                _RcfError_CryptoApiError("CryptDecodeObject()"), 
                dwErr, 
                RCF::RcfSubsystem_Os));

        PCERT_NAME_INFO pCertNameInfo = (PCERT_NAME_INFO) &vec[0];

        PCERT_RDN_ATTR pCertAttr = CertFindRDNAttr(whichAttr, pCertNameInfo);
        if (pCertAttr)
        {
            DWORD cbLen = CertRDNValueToStr(pCertAttr->dwValueType, &pCertAttr->Value, NULL, 0);
            std::vector<TCHAR> vecAttr(cbLen);

            CertRDNValueToStr(
                pCertAttr->dwValueType, 
                &pCertAttr->Value, 
                &vecAttr[0],
                static_cast<DWORD>(vecAttr.size()));

            tstring attr(&vecAttr[0]);
            return attr;
        }
        
        return tstring();
    }