1 /* -*- Mode: C; tab-width: 4 -*-
3 * Copyright (c) 2011-2012 Apple Inc. All rights reserved.
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
18 // ***************************************************************************
20 // Interface to DNSSEC cryptographic algorithms. The crypto support itself is
21 // provided by the platform and the functions in this file just provide an
22 // interface to access them in a more generic way.
23 // ***************************************************************************
25 #include "mDNSEmbeddedAPI.h"
26 #include "CryptoAlg.h"
28 AlgFuncs
*DigestAlgFuncs
[DIGEST_TYPE_MAX
];
29 AlgFuncs
*CryptoAlgFuncs
[CRYPTO_ALG_MAX
];
30 AlgFuncs
*EncAlgFuncs
[ENC_ALG_MAX
];
32 mDNSexport mStatus
DigestAlgInit(mDNSu8 digestType
, AlgFuncs
*func
)
34 if (digestType
>= DIGEST_TYPE_MAX
)
36 LogMsg("DigestAlgInit: digestType %d exceeds bounds", digestType
);
37 return mStatus_BadParamErr
;
39 // As digestTypes may not be consecutive, check for specific digest types
41 if (digestType
!= SHA1_DIGEST_TYPE
&&
42 digestType
!= SHA256_DIGEST_TYPE
)
44 LogMsg("DigestAlgInit: digestType %d not supported", digestType
);
45 return mStatus_BadParamErr
;
47 DigestAlgFuncs
[digestType
] = func
;
48 return mStatus_NoError
;
51 mDNSexport mStatus
CryptoAlgInit(mDNSu8 alg
, AlgFuncs
*func
)
53 if (alg
>= CRYPTO_ALG_MAX
)
55 LogMsg("CryptoAlgInit: alg %d exceeds bounds", alg
);
56 return mStatus_BadParamErr
;
58 // As algs may not be consecutive, check for specific algorithms
60 if (alg
!= CRYPTO_RSA_SHA1
&& alg
!= CRYPTO_RSA_SHA256
&& alg
!= CRYPTO_RSA_SHA512
&&
61 alg
!= CRYPTO_DSA_NSEC3_SHA1
&& alg
!= CRYPTO_RSA_NSEC3_SHA1
)
63 LogMsg("CryptoAlgInit: alg %d not supported", alg
);
64 return mStatus_BadParamErr
;
67 CryptoAlgFuncs
[alg
] = func
;
68 return mStatus_NoError
;
71 mDNSexport mStatus
EncAlgInit(mDNSu8 alg
, AlgFuncs
*func
)
73 if (alg
>= ENC_ALG_MAX
)
75 LogMsg("EncAlgInit: alg %d exceeds bounds", alg
);
76 return mStatus_BadParamErr
;
79 // As algs may not be consecutive, check for specific algorithms
81 if (alg
!= ENC_BASE32
&& alg
!= ENC_BASE64
)
83 LogMsg("EncAlgInit: alg %d not supported", alg
);
84 return mStatus_BadParamErr
;
87 EncAlgFuncs
[alg
] = func
;
88 return mStatus_NoError
;
91 mDNSexport AlgContext
*AlgCreate(AlgType type
, mDNSu8 alg
)
93 AlgFuncs
*func
= mDNSNULL
;
96 if (type
== CRYPTO_ALG
)
98 if (alg
>= CRYPTO_ALG_MAX
) return mDNSNULL
;
99 func
= CryptoAlgFuncs
[alg
];
101 else if (type
== DIGEST_ALG
)
103 if (alg
>= DIGEST_TYPE_MAX
) return mDNSNULL
;
104 func
= DigestAlgFuncs
[alg
];
106 else if (type
== ENC_ALG
)
108 if (alg
>= ENC_ALG_MAX
) return mDNSNULL
;
109 func
= EncAlgFuncs
[alg
];
114 // If there is no support from the platform, this case can happen.
115 LogInfo("AlgCreate: func is NULL");
122 ctx
= mDNSPlatformMemAllocate(sizeof(AlgContext
));
123 if (!ctx
) return mDNSNULL
;
124 // Create expects ctx->alg to be initialized
126 err
= func
->Create(ctx
);
127 if (err
== mStatus_NoError
)
132 mDNSPlatformMemFree(ctx
);
137 mDNSexport mStatus
AlgDestroy(AlgContext
*ctx
)
139 AlgFuncs
*func
= mDNSNULL
;
141 if (ctx
->type
== CRYPTO_ALG
)
142 func
= CryptoAlgFuncs
[ctx
->alg
];
143 else if (ctx
->type
== DIGEST_ALG
)
144 func
= DigestAlgFuncs
[ctx
->alg
];
145 else if (ctx
->type
== ENC_ALG
)
146 func
= EncAlgFuncs
[ctx
->alg
];
150 LogMsg("AlgDestroy: ERROR!! func is NULL");
151 mDNSPlatformMemFree(ctx
);
152 return mStatus_BadParamErr
;
158 mDNSPlatformMemFree(ctx
);
159 return mStatus_NoError
;
162 mDNSexport mDNSu32
AlgLength(AlgContext
*ctx
)
164 AlgFuncs
*func
= mDNSNULL
;
166 if (ctx
->type
== CRYPTO_ALG
)
167 func
= CryptoAlgFuncs
[ctx
->alg
];
168 else if (ctx
->type
== DIGEST_ALG
)
169 func
= DigestAlgFuncs
[ctx
->alg
];
170 else if (ctx
->type
== ENC_ALG
)
171 func
= EncAlgFuncs
[ctx
->alg
];
173 // This should never happen as AlgCreate would have failed
176 LogMsg("AlgLength: ERROR!! func is NULL");
181 return (func
->Length(ctx
));
186 mDNSexport mStatus
AlgAdd(AlgContext
*ctx
, const void *data
, mDNSu32 len
)
188 AlgFuncs
*func
= mDNSNULL
;
190 if (ctx
->type
== CRYPTO_ALG
)
191 func
= CryptoAlgFuncs
[ctx
->alg
];
192 else if (ctx
->type
== DIGEST_ALG
)
193 func
= DigestAlgFuncs
[ctx
->alg
];
194 else if (ctx
->type
== ENC_ALG
)
195 func
= EncAlgFuncs
[ctx
->alg
];
197 // This should never happen as AlgCreate would have failed
200 LogMsg("AlgAdd: ERROR!! func is NULL");
201 return mStatus_BadParamErr
;
205 return (func
->Add(ctx
, data
, len
));
207 return mStatus_BadParamErr
;
210 mDNSexport mStatus
AlgVerify(AlgContext
*ctx
, mDNSu8
*key
, mDNSu32 keylen
, mDNSu8
*signature
, mDNSu32 siglen
)
212 AlgFuncs
*func
= mDNSNULL
;
214 if (ctx
->type
== CRYPTO_ALG
)
215 func
= CryptoAlgFuncs
[ctx
->alg
];
216 else if (ctx
->type
== DIGEST_ALG
)
217 func
= DigestAlgFuncs
[ctx
->alg
];
218 else if (ctx
->type
== ENC_ALG
)
219 func
= EncAlgFuncs
[ctx
->alg
];
221 // This should never happen as AlgCreate would have failed
224 LogMsg("AlgVerify: ERROR!! func is NULL");
225 return mStatus_BadParamErr
;
229 return (func
->Verify(ctx
, key
, keylen
, signature
, siglen
));
231 return mStatus_BadParamErr
;
234 mDNSexport mDNSu8
* AlgEncode(AlgContext
*ctx
)
236 AlgFuncs
*func
= mDNSNULL
;
238 if (ctx
->type
== CRYPTO_ALG
)
239 func
= CryptoAlgFuncs
[ctx
->alg
];
240 else if (ctx
->type
== DIGEST_ALG
)
241 func
= DigestAlgFuncs
[ctx
->alg
];
242 else if (ctx
->type
== ENC_ALG
)
243 func
= EncAlgFuncs
[ctx
->alg
];
245 // This should never happen as AlgCreate would have failed
248 LogMsg("AlgEncode: ERROR!! func is NULL");
253 return (func
->Encode(ctx
));
258 mDNSexport mStatus
AlgFinal(AlgContext
*ctx
, void *data
, mDNSu32 len
)
260 AlgFuncs
*func
= mDNSNULL
;
262 if (ctx
->type
== CRYPTO_ALG
)
263 func
= CryptoAlgFuncs
[ctx
->alg
];
264 else if (ctx
->type
== DIGEST_ALG
)
265 func
= DigestAlgFuncs
[ctx
->alg
];
266 else if (ctx
->type
== ENC_ALG
)
267 func
= EncAlgFuncs
[ctx
->alg
];
269 // This should never happen as AlgCreate would have failed
272 LogMsg("AlgEncode: ERROR!! func is NULL");
277 return (func
->Final(ctx
, data
, len
));
279 return mStatus_BadParamErr
;