]>
Commit | Line | Data |
---|---|---|
b1ab9ed8 A |
1 | /* |
2 | * Copyright (c) 2000-2001 Apple Computer, Inc. All Rights Reserved. | |
3 | * | |
4 | * The contents of this file constitute Original Code as defined in and are | |
5 | * subject to the Apple Public Source License Version 1.2 (the 'License'). | |
6 | * You may not use this file except in compliance with the License. Please obtain | |
7 | * a copy of the License at http://www.apple.com/publicsource and read it before | |
8 | * using this file. | |
9 | * | |
10 | * This Original Code and all software distributed under the License are | |
11 | * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS | |
12 | * OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, INCLUDING WITHOUT | |
13 | * LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR | |
14 | * PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. Please see the License for the | |
15 | * specific language governing rights and limitations under the License. | |
16 | */ | |
17 | ||
18 | /* | |
19 | * MacContext.cpp - AppleCSPContext for HMACSHA1 | |
20 | */ | |
21 | ||
22 | #include "MacContext.h" | |
23 | #include <HMACSHA1.h> | |
24 | #include <Security/cssmerr.h> | |
25 | #include <CommonCrypto/CommonDigest.h> /* for digest sizes */ | |
26 | #ifdef CRYPTKIT_CSP_ENABLE | |
27 | #include <security_cryptkit/HmacSha1Legacy.h> | |
28 | #endif /* CRYPTKIT_CSP_ENABLE */ | |
29 | ||
30 | MacContext::~MacContext() | |
31 | { | |
32 | memset(&hmacCtx, 0, sizeof(hmacCtx)); | |
33 | } | |
34 | ||
35 | /* called out from CSPFullPluginSession.... | |
36 | * both generate and verify */ | |
37 | void MacContext::init(const Context &context, bool isSigning) | |
38 | { | |
39 | CCHmacAlgorithm ccAlg; | |
40 | ||
41 | /* obtain key from context */ | |
42 | CSSM_SIZE keyLen; | |
43 | uint8 *keyData = NULL; | |
44 | ||
45 | symmetricKeyBits(context, session(), mAlg, | |
46 | isSigning ? CSSM_KEYUSE_SIGN : CSSM_KEYUSE_VERIFY, | |
47 | keyData, keyLen); | |
48 | uint32 minKey = 0; | |
49 | switch(mAlg) { | |
50 | case CSSM_ALGID_SHA1HMAC: | |
51 | minKey = HMAC_SHA_MIN_KEY_SIZE; | |
52 | mDigestSize = CC_SHA1_DIGEST_LENGTH; | |
53 | ccAlg = kCCHmacAlgSHA1; | |
54 | break; | |
55 | case CSSM_ALGID_MD5HMAC: | |
56 | minKey = HMAC_MD5_MIN_KEY_SIZE; | |
57 | mDigestSize = CC_MD5_DIGEST_LENGTH; | |
58 | ccAlg = kCCHmacAlgMD5; | |
59 | break; | |
60 | default: | |
61 | assert(0); // factory should not have called us | |
62 | CssmError::throwMe(CSSMERR_CSP_INVALID_ALGORITHM); | |
63 | } | |
64 | if((keyLen < minKey) || (keyLen > HMAC_MAX_KEY_SIZE)) { | |
65 | CssmError::throwMe(CSSMERR_CSP_INVALID_ATTR_KEY); | |
66 | } | |
67 | CCHmacInit(&hmacCtx, ccAlg, keyData, keyLen); | |
68 | } | |
69 | ||
70 | void MacContext::update(const CssmData &data) | |
71 | { | |
72 | CCHmacUpdate(&hmacCtx, data.data(), data.length()); | |
73 | } | |
74 | ||
75 | /* generate only */ | |
76 | void MacContext::final(CssmData &out) | |
77 | { | |
78 | if(out.length() < mDigestSize) { | |
79 | CssmError::throwMe(CSSMERR_CSP_OUTPUT_LENGTH_ERROR); | |
80 | } | |
81 | CCHmacFinal(&hmacCtx, out.data()); | |
82 | out.Length = mDigestSize; | |
83 | } | |
84 | ||
85 | /* verify only */ | |
86 | #define MAX_DIGEST_SIZE CC_SHA1_DIGEST_LENGTH | |
87 | ||
88 | void MacContext::final(const CssmData &in) | |
89 | { | |
90 | unsigned char mac[MAX_DIGEST_SIZE]; | |
91 | ||
92 | CCHmacFinal(&hmacCtx, mac); | |
93 | if(memcmp(mac, in.data(), mDigestSize)) { | |
94 | CssmError::throwMe(CSSMERR_CSP_VERIFY_FAILED); | |
95 | } | |
96 | } | |
97 | ||
98 | size_t MacContext::outputSize(bool final, size_t inSize) | |
99 | { | |
100 | return mDigestSize; | |
101 | } | |
102 | ||
103 | #ifdef CRYPTKIT_CSP_ENABLE | |
104 | ||
105 | MacLegacyContext::~MacLegacyContext() | |
106 | { | |
107 | if(mHmac) { | |
108 | hmacLegacyFree(mHmac); | |
109 | mHmac = NULL; | |
110 | } | |
111 | } | |
112 | ||
113 | /* called out from CSPFullPluginSession.... | |
114 | * both generate and verify: */ | |
115 | void MacLegacyContext::init(const Context &context, bool isSigning) | |
116 | { | |
117 | if(mHmac == NULL) { | |
118 | mHmac = hmacLegacyAlloc(); | |
119 | if(mHmac == NULL) { | |
120 | CssmError::throwMe(CSSMERR_CSP_MEMORY_ERROR); | |
121 | } | |
122 | } | |
123 | ||
124 | /* obtain key from context */ | |
125 | CSSM_SIZE keyLen; | |
126 | uint8 *keyData = NULL; | |
127 | ||
128 | /* FIXME - this may require a different key alg */ | |
129 | symmetricKeyBits(context, session(), CSSM_ALGID_SHA1HMAC, | |
130 | isSigning ? CSSM_KEYUSE_SIGN : CSSM_KEYUSE_VERIFY, | |
131 | keyData, keyLen); | |
132 | if((keyLen < HMAC_SHA_MIN_KEY_SIZE) || (keyLen > HMAC_MAX_KEY_SIZE)) { | |
133 | CssmError::throwMe(CSSMERR_CSP_INVALID_ATTR_KEY); | |
134 | } | |
135 | ||
427c49bc | 136 | OSStatus ortn = hmacLegacyInit(mHmac, keyData, (UInt32)keyLen); |
b1ab9ed8 A |
137 | if(ortn) { |
138 | MacOSError::throwMe(ortn); | |
139 | } | |
140 | } | |
141 | ||
142 | void MacLegacyContext::update(const CssmData &data) | |
143 | { | |
144 | OSStatus ortn = hmacLegacyUpdate(mHmac, | |
145 | data.data(), | |
427c49bc | 146 | (UInt32)data.length()); |
b1ab9ed8 A |
147 | if(ortn) { |
148 | MacOSError::throwMe(ortn); | |
149 | } | |
150 | } | |
151 | ||
152 | /* generate only */ | |
153 | void MacLegacyContext::final(CssmData &out) | |
154 | { | |
155 | if(out.length() < kHMACSHA1DigestSize) { | |
156 | CssmError::throwMe(CSSMERR_CSP_OUTPUT_LENGTH_ERROR); | |
157 | } | |
158 | hmacLegacyFinal(mHmac, out.data()); | |
159 | } | |
160 | ||
161 | /* verify only */ | |
162 | void MacLegacyContext::final(const CssmData &in) | |
163 | { | |
164 | unsigned char mac[kHMACSHA1DigestSize]; | |
165 | hmacLegacyFinal(mHmac, mac); | |
166 | if(memcmp(mac, in.data(), kHMACSHA1DigestSize)) { | |
167 | CssmError::throwMe(CSSMERR_CSP_VERIFY_FAILED); | |
168 | } | |
169 | } | |
170 | ||
171 | size_t MacLegacyContext::outputSize(bool final, size_t inSize) | |
172 | { | |
173 | return kHMACSHA1DigestSize; | |
174 | } | |
175 | ||
176 | #endif /* CRYPTKIT_CSP_ENABLE */ |