인증서가 서명 메서드를 지원하는지 확인
이 항목에서는 인증서가 특정 서명 방법을 지원하는지 확인하는 방법을 설명합니다.
Microsoft Crypto API의 CryptXmlEnumAlgorithmInfo는 인증서의 속성을 열거하고 이 코드 예제에서 인증서가 지원하는 서명 메서드를 열거하는 데 사용됩니다. CryptXmlEnumAlgorithmInfo를 사용하여 인증서가 지원하는 서명 메서드를 열거하려면 호출자는 CryptXmlEnumAlgorithmInfo 호출에서 콜백 메서드 및 데이터 구조를 제공하여 콜백 메서드에 데이터를 전달할 수 있도록 해야 합니다.
다음 코드 예제에서 사용되는 데이터 구조에는 다음 필드가 있습니다.
필드 | 설명 |
---|---|
userSignatureAlgorithmToCheck | 검사 서명 알고리즘의 URI가 포함된 문자열을 가리키는 LPWSTR 필드입니다. |
certificateAlgorithmInfo | 인증서에서 지원하는 서명 알고리즘에 대한 정보를 포함하는 CRYPT_OID_INFO 구조체에 대한 포인터입니다. |
userSignatureAlgorithmSupported | 서명 알고리즘이 인증서에서 지원되는지 여부를 나타내는 부울 값입니다. |
struct SignatureMethodData
{
LPCWSTR userSignatureAlgorithmToCheck;
PCCRYPT_OID_INFO certificateAlgorithmInfo;
BOOL userSignatureAlgorithmSupported;
};
인증서를 검사 Crypto API 메서드는 콜백 메서드를 사용하여 호출자에게 데이터를 반환합니다. CryptXmlEnumAlgorithmInfo는 인증서가 지원하는 서명 메서드를 열거하고 콜백 메서드가 FALSE를 반환하거나 인증서의 모든 서명 메서드가 열거될 때까지 각 서명 메서드에 대한 콜백 메서드를 호출합니다.
다음 코드 예제의 콜백 메서드는 호출 메서드에서 제공하는 서명 메서드와 일치하는 CryptXmlEnumAlgorithmInfo 에서 전달한 서명 메서드를 검색합니다. 일치 항목이 발견되면 콜백 메서드는 시스템에서 서명 메서드도 지원하는지 여부를 검사. 서명 메서드가 일치하고 시스템에서 지원되는 경우 서명 메서드는 시스템 지원으로 표시되고 콜백 메서드는 FALSE를 반환합니다.
BOOL WINAPI
EnumSignatureMethodCallback (
__in const CRYPT_XML_ALGORITHM_INFO *certMethodInfo,
__inout_opt void *userArg
)
{
// MAX_ALG_ID_LEN is used to set the maximum length of the
// algorithm URI in the string comparison. The URI is not
// likely to be longer than 128 characters so a fixed-size
// buffer is used in this example.
// To make this function more robust, you might consider
// setting this value dynamically.
static const size_t MAX_ALG_ID_LEN = 128;
SignatureMethodData *certificateAlgorithmData = NULL;
if (NULL != userArg) {
// Assign user data to local data structure
certificateAlgorithmData = (SignatureMethodData*)userArg;
} else {
// Unable to continue this enumeration
// without data from calling method.
return FALSE;
}
// For each algorithm in the enumeration, check to see if the URI
// of the algorithm supported by the certificate matches the URI
// of the algorithm being tested.
int cmpResult = 0;
cmpResult = wcsncmp(
certMethodInfo->wszAlgorithmURI,
certificateAlgorithmData->userSignatureAlgorithmToCheck,
MAX_ALG_ID_LEN );
if ( 0 == cmpResult )
{
// This is a match...
// Check to see if the algorithm supported by the
// certificate matches any of the supported algorithms
// on the system.
cmpResult = wcsncmp(
certMethodInfo->wszCNGExtraAlgid,
certificateAlgorithmData->certificateAlgorithmInfo->pwszCNGAlgid,
MAX_ALG_ID_LEN );
if ( 0 == cmpResult )
{
// This is also a match so set the field in the data structure
// provided by the calling method.
certificateAlgorithmData->userSignatureAlgorithmSupported = TRUE;
// A match was found so there is no point in continuing
// the enumeration.
return FALSE;
}
}
// The enumeration stops when the callback method returns FALSE.
// If here, then return TRUE because a matching algorithm has
// not been found.
return TRUE;
}
다음 코드 예제에서는 유효성 검사 기능을 단일 메서드로 래핑합니다. 이 메서드는 인증서가 서명 메서드를 지원하는지 여부와 시스템에서 서명 메서드를 지원하는지 여부를 나타내는 부울 값을 반환합니다.
BOOL
SupportsSignatureAlgorithm (
__in LPCWSTR signingMethodToCheck,
__in PCCERT_CONTEXT certificateToCheck
)
{
HRESULT hr = S_OK;
// Initialize the structure that contains the
// information about the signature algorithm to check
SignatureMethodData certificateAlgorithmData;
certificateAlgorithmData.userSignatureAlgorithmSupported =
FALSE;
certificateAlgorithmData.userSignatureAlgorithmToCheck =
signingMethodToCheck;
// Call the crypt API to get information about the algorithms
// that are supported by the certificate and initialize
// certificateAlgorithmData
certificateAlgorithmData.certificateAlgorithmInfo = CryptFindOIDInfo (
CRYPT_OID_INFO_OID_KEY,
certificateToCheck->pCertInfo->SubjectPublicKeyInfo.Algorithm.pszObjId,
CRYPT_PUBKEY_ALG_OID_GROUP_ID | CRYPT_OID_PREFER_CNG_ALGID_FLAG);
if (certificateAlgorithmData.certificateAlgorithmInfo != NULL)
{
// Enumerate the algorithms that are supported by the
// certificate, and use our callback method to determine if
// the user supplied signature algorithm is supported by
// the certificate.
//
// Note that CRYPT_XML_GROUP_ID_SIGN is used to enumerate
// the signature methods
hr = CryptXmlEnumAlgorithmInfo(
CRYPT_XML_GROUP_ID_SIGN, // NOTE: CRYPT_XML_GROUP_ID_SIGN
CRYPT_XML_FLAG_DISABLE_EXTENSIONS,
(void*)&certificateAlgorithmData,
EnumSignatureMethodCallback);
// when the enumeration has returned successfully,
// certificateAlgorithmData.userSignatureAlgorithmSupported
// will be TRUE if the signing method is supported by
// the certificate
}
return certificateAlgorithmData.userSignatureAlgorithmSupported;
}
관련 항목
-
다음 단계
-
이 예제에서 사용됨
-
CryptXmlEnumAlgorithmInfo
-
상세 설명