1/*
2 * Copyright (c) 2003-2004 Apple Computer, Inc. All Rights Reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
11 * file.
12 *
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
20 *
21 * @APPLE_LICENSE_HEADER_END@
22 */
23/*
24 * pkcs12SafeBag.h : internal representation of various kinds
25 *                   of P12 SafeBags
26 */
27
28#ifndef	_PKCS12_SAFE_BAG_H_
29#define _PKCS12_SAFE_BAG_H_
30
31#include <Security/cssmtype.h>
32#include <security_pkcs12/pkcs12BagAttrs.h>
33#include <security_pkcs12/pkcs12Templates.h>
34#include <security_asn1/SecNssCoder.h>
35#include <CoreFoundation/CoreFoundation.h>
36#include <Security/SecCertificate.h>
37
38/*
39 * Abstract superclass of all safe bags.
40 */
41class P12SafeBag {
42public:
43	/*
44	 * Constructors:
45	 *
46	 * While decoding, specified attr array includes friendlyName
47	 * and localKeyId; we'll parse the array and snag those if
48	 * present as "specially treated" attrs. The rest of the
49	 * attrs - which we don't grok - get piled into mBagAttrs.
50	 */
51	P12SafeBag(
52		NSS_Attribute 		**attrs, // including friendlyName, etc.
53		SecNssCoder 		&coder);
54
55	/*
56	 * Constructor for encoding. The specified attr array only contains
57	 * attrs other than friendlyName and localKeyId; those attrs
58	 * are passed in explicitly.
59	 *
60	 * All arguments except for the coder are optional.
61	 */
62	P12SafeBag(
63		CFStringRef			fname,
64		CFDataRef			keyId,
65		P12BagAttrs			*otherAttrs,
66		SecNssCoder 		&coder);
67
68	~P12SafeBag();
69
70	/* getters in CF terms - result is created and returned */
71	CFStringRef friendlyName();
72	CFDataRef 	localKeyId();
73
74	/* getters in CSSM_DATA terms - result is just a reference */
75	CSSM_DATA 	&friendlyNameCssm()		{ return mFriendlyName; }
76	CSSM_DATA	&localKeyIdCssm()		{ return mLocalKeyId; }
77
78	/*
79	 * Get all attrs, including friendlyName and localKeyId,
80	 * in preparation for encoding.
81	 */
82	NSS_Attribute **getAllAttrs();
83
84	/*
85	 * Copy out all attrs in API form. All incoming ptrs
86	 * are optional.
87	 */
88	void copyAllAttrs(
89		CFStringRef 		*friendlyName,
90		CFDataRef			*localKeyId,
91		P12BagAttrs			**bagAttrs);
92
93private:
94	/*
95	 * Setters in CF terms, used when constructing prior
96	 * to encoding.
97	 */
98	void friendlyName(
99		CFStringRef 		fname);
100	void localKeyId(
101		CFDataRef 			keyId);
102
103	/*
104	 * Create an NSS_Attribute * for friendlyName or keyId
105	 */
106	NSS_Attribute *makeAttr(
107		const CSSM_OID		&attrId,
108		const CSSM_DATA		&attrValue);
109
110protected:
111	/*
112	 * The common contents of all safe bag types, all optional.
113	 * FriendlyName is stored in P12-native form, just as it's
114	 * stored in the PFX. This is the contents of a BMPString.
115	 */
116	CSSM_DATA				mFriendlyName;
117	CSSM_DATA				mLocalKeyId;
118	P12BagAttrs				mBagAttrs;
119	SecNssCoder				&mCoder;	// all our data mallocd here
120};
121
122/*
123 * Individual bag types
124 */
125class P12CertBag : public P12SafeBag {
126public:
127	/* for decode */
128	P12CertBag(
129		NSS_P12_CertBagType	certType,	// CT_X509, CT_SDSI
130		CSSM_DATA			&certData,
131		NSS_Attribute		**attrs,	// optional
132		SecNssCoder			&coder);
133
134	/* for encode */
135	P12CertBag(
136		NSS_P12_CertBagType	certType,	// CT_X509, CT_SDSI
137		CSSM_DATA			&certData,
138		CFStringRef			fname,
139		CFDataRef			keyId,
140		P12BagAttrs			*otherAttrs,// optional
141		SecNssCoder			&coder);
142
143	~P12CertBag();
144
145	/* getters - result is just a ref to our data */
146	NSS_P12_CertBagType		certType() 	{ return mCertType; }
147	CSSM_DATA				&certData()	{ return mCertData; }
148
149	/* convert to P12CertBag to SecCertificateRef */
150	SecCertificateRef 		getSecCert();
151
152private:
153	NSS_P12_CertBagType		mCertType;
154	CSSM_DATA				mCertData;
155	SecCertificateRef		mCertRef;	/* created lazily */
156};
157
158class P12CrlBag : public P12SafeBag {
159public:
160	/* decode */
161	P12CrlBag(
162		NSS_P12_CrlBagType	crlType,	// CRT_X509, only for now
163		CSSM_DATA			&crlData,
164		NSS_Attribute		**attrs,	// optional
165		SecNssCoder			&coder);
166
167	/* encode */
168	P12CrlBag(
169		NSS_P12_CrlBagType	crlType,	// CRT_X509, only for now
170		CFDataRef			crlData,
171		CFStringRef			fname,
172		CFDataRef			keyId,
173		P12BagAttrs			*otherAttrs,
174		SecNssCoder			&coder);
175
176	~P12CrlBag();
177
178	/* getters - result is just a ref to our data */
179	NSS_P12_CrlBagType		crlType() 	{ return mCrlType; }
180	CSSM_DATA				&crlData()	{ return mCrlData; }
181
182
183private:
184	NSS_P12_CrlBagType		mCrlType;
185	CSSM_DATA				mCrlData;
186};
187
188/* for both shrouded and plain */
189class P12KeyBag : public P12SafeBag {
190public:
191	/* decode */
192	P12KeyBag(
193		CSSM_KEY_PTR		key,
194		CSSM_CSP_HANDLE		cspHand,
195		NSS_Attribute		**attrs,	// optional
196		CSSM_DATA			&labelData,
197		SecNssCoder			&coder);
198
199	/* encode */
200	P12KeyBag(
201		const CSSM_KEY		*key,
202		CSSM_CSP_HANDLE		cspHand,
203		CFStringRef			fname,
204		CFDataRef			keyId,
205		P12BagAttrs			*otherAttrs,
206		SecNssCoder			&coder,
207		/* for SecPkcs12ExportKeychainItems() */
208		SecKeyRef			keyRef = NULL);
209
210	~P12KeyBag();
211
212	void setLabel(
213		const CSSM_DATA		&newLabel);
214
215	/* reusable key setter */
216	void setKey(
217		CSSM_KEY_PTR		cssmKey);
218
219	/*
220	 * Keys are kind of special in that they can't easily be copied.
221	 * On encode, the app owns the key. On decode, we own the
222	 * reference key but caller (P12Coder) owns the actual
223	 * memory associated with the CSSM_KEY.
224	 */
225	CSSM_KEY_PTR			key()				{ return mKey; }
226	CSSM_DATA				&label()			{ return mLabel; }
227	const CSSM_ACCESS_CREDENTIALS
228							*privKeyCreds()		{ return mPrivKeyCreds; }
229	bool					dupKey()			{ return mDupKey; }
230	void					dupKey(bool b)		{ mDupKey = b; }
231
232private:
233	CSSM_KEY_PTR			mKey;
234	CSSM_CSP_HANDLE			mCspHand;
235
236	/*
237	 * When constructed via SecPkcs12ExportKeychainItems(), we
238	 * have to hold a reference to the SecKeyRef which was
239	 * used to create this object.
240	 */
241	SecKeyRef				mKeyRef;
242
243	/*
244	 * When false, app owns key. When true, we have to free
245	 * key in our destructor.
246	 *
247	 * NOTE: mKeyRef and mWeOwnKey are mutually exclusive.
248	 */
249	 bool					mWeOwnKey;
250
251	/* somewhat unique label when stored in DLDB */
252	CSSM_DATA				mLabel;
253
254	/* for encode only, owned by app */
255	const CSSM_ACCESS_CREDENTIALS *mPrivKeyCreds;
256
257	/* indicates a key we looked up, not imported */
258	bool					mDupKey;
259
260	void freeKey();
261
262};
263
264/*
265 * Others we don't implement
266 */
267class P12OpaqueBag : public P12SafeBag {
268public:
269	/* decode */
270	P12OpaqueBag(
271		const CSSM_OID		&oid,
272		const CSSM_DATA		&blob,
273		NSS_Attribute		**attrs,	// optional
274		SecNssCoder			&coder);
275
276	/* encode */
277	P12OpaqueBag(
278		CFDataRef			oid,
279		CFDataRef			blob,
280		CFStringRef			fname,
281		CFDataRef			keyId,
282		P12BagAttrs			*otherAttrs,
283		SecNssCoder			&coder);
284
285	~P12OpaqueBag();
286
287	CSSM_OID 				&oid()		{ return mOid; }
288	CSSM_DATA				&blob()		{ return mBlob; }
289
290private:
291	CSSM_OID				mOid;
292	CSSM_DATA				mBlob;
293};
294
295
296#endif	/* _PKCS12_SAFE_BAG_H_ */
297
298