117Sdinak /*
217Sdinak  * CDDL HEADER START
317Sdinak  *
417Sdinak  * The contents of this file are subject to the terms of the
5*3089Swyllys  * Common Development and Distribution License (the "License").
6*3089Swyllys  * You may not use this file except in compliance with the License.
717Sdinak  *
817Sdinak  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
917Sdinak  * or http://www.opensolaris.org/os/licensing.
1017Sdinak  * See the License for the specific language governing permissions
1117Sdinak  * and limitations under the License.
1217Sdinak  *
1317Sdinak  * When distributing Covered Code, include this CDDL HEADER in each
1417Sdinak  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
1517Sdinak  * If applicable, add the following below this CDDL HEADER, with the
1617Sdinak  * fields enclosed by brackets "[]" replaced with your own identifying
1717Sdinak  * information: Portions Copyright [yyyy] [name of copyright owner]
1817Sdinak  *
1917Sdinak  * CDDL HEADER END
2017Sdinak  */
2117Sdinak /*
22*3089Swyllys  * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
2317Sdinak  * Use is subject to license terms.
2417Sdinak  */
2517Sdinak 
2617Sdinak #pragma ident	"%Z%%M%	%I%	%E% SMI"
2717Sdinak 
2817Sdinak /*
2917Sdinak  * This file implements the token object delete operation for this tool.
3017Sdinak  * It loads the PKCS#11 modules, finds the object to delete, deletes it,
3117Sdinak  * and cleans up.  User must be R/W logged into the token.
3217Sdinak  */
3317Sdinak 
3417Sdinak #include <stdio.h>
3517Sdinak #include <string.h>
3617Sdinak #include <cryptoutil.h>
3717Sdinak #include <security/cryptoki.h>
3817Sdinak #include "common.h"
39*3089Swyllys #include <kmfapi.h>
40*3089Swyllys 
41*3089Swyllys static KMF_RETURN
42*3089Swyllys pk_destroy_keys(void *handle, KMF_KEY_HANDLE *keys,
43*3089Swyllys 	KMF_FINDKEY_PARAMS *fkparams, uint32_t numkeys)
44*3089Swyllys {
45*3089Swyllys 	int i;
46*3089Swyllys 	KMF_RETURN rv = KMF_OK;
47*3089Swyllys 	KMF_DELETEKEY_PARAMS dkparams;
48*3089Swyllys 
49*3089Swyllys 	(void) memset(&dkparams, 0, sizeof (dkparams));
50*3089Swyllys 	dkparams.kstype = fkparams->kstype;
51*3089Swyllys 
52*3089Swyllys 	switch (fkparams->kstype) {
53*3089Swyllys 	case KMF_KEYSTORE_NSS:
54*3089Swyllys 		dkparams.nssparms = fkparams->nssparms;
55*3089Swyllys 		dkparams.cred = fkparams->cred;
56*3089Swyllys 		break;
57*3089Swyllys 	case KMF_KEYSTORE_OPENSSL:
58*3089Swyllys 		break;
59*3089Swyllys 	case KMF_KEYSTORE_PK11TOKEN:
60*3089Swyllys 		dkparams.cred = fkparams->cred;
61*3089Swyllys 		break;
62*3089Swyllys 	default:
63*3089Swyllys 		return (PK_ERR_USAGE);
64*3089Swyllys 	}
65*3089Swyllys 
66*3089Swyllys 	for (i = 0; rv == KMF_OK && i < numkeys; i++) {
67*3089Swyllys 		rv = KMF_DeleteKeyFromKeystore(handle, &dkparams, &keys[i]);
68*3089Swyllys 	}
69*3089Swyllys 	return (rv);
70*3089Swyllys }
71*3089Swyllys 
72*3089Swyllys static KMF_RETURN
73*3089Swyllys pk_delete_keys(KMF_HANDLE_T kmfhandle, KMF_FINDKEY_PARAMS *parms, char *desc,
74*3089Swyllys 	int *keysdeleted)
75*3089Swyllys {
76*3089Swyllys 	KMF_RETURN rv = KMF_OK;
77*3089Swyllys 	uint32_t numkeys = 0;
78*3089Swyllys 
79*3089Swyllys 	*keysdeleted = 0;
80*3089Swyllys 	numkeys = 0;
81*3089Swyllys 	rv = KMF_FindKey(kmfhandle, parms, NULL, &numkeys);
82*3089Swyllys 	if (rv == KMF_OK && numkeys > 0) {
83*3089Swyllys 		KMF_KEY_HANDLE *keys = NULL;
84*3089Swyllys 		char prompt[1024];
85*3089Swyllys 
86*3089Swyllys 		(void) snprintf(prompt, sizeof (prompt),
87*3089Swyllys 			gettext("%d %s key(s) found, do you want "
88*3089Swyllys 			"to delete them (y/N) ?"), numkeys,
89*3089Swyllys 			(desc != NULL ? desc : ""));
90*3089Swyllys 
91*3089Swyllys 		if (!yesno(prompt,
92*3089Swyllys 			gettext("Respond with yes or no.\n"),
93*3089Swyllys 			B_FALSE)) {
94*3089Swyllys 			return (KMF_OK);
95*3089Swyllys 		}
96*3089Swyllys 		keys = (KMF_KEY_HANDLE *)malloc(numkeys *
97*3089Swyllys 				sizeof (KMF_KEY_HANDLE));
98*3089Swyllys 		if (keys == NULL)
99*3089Swyllys 			return (KMF_ERR_MEMORY);
100*3089Swyllys 		(void) memset(keys, 0, numkeys *
101*3089Swyllys 			sizeof (KMF_KEY_HANDLE));
102*3089Swyllys 
103*3089Swyllys 		rv = KMF_FindKey(kmfhandle, parms, keys, &numkeys);
104*3089Swyllys 		if (rv == KMF_OK) {
105*3089Swyllys 			rv = pk_destroy_keys(kmfhandle, keys,
106*3089Swyllys 				parms, numkeys);
107*3089Swyllys 		}
108*3089Swyllys 
109*3089Swyllys 		free(keys);
110*3089Swyllys 	}
111*3089Swyllys 
112*3089Swyllys 	if (rv == KMF_ERR_KEY_NOT_FOUND) {
113*3089Swyllys 		rv = KMF_OK;
114*3089Swyllys 	}
115*3089Swyllys 
116*3089Swyllys 	*keysdeleted = numkeys;
117*3089Swyllys 	return (rv);
118*3089Swyllys }
119*3089Swyllys 
120*3089Swyllys static KMF_RETURN
121*3089Swyllys pk_delete_certs(KMF_HANDLE_T kmfhandle, KMF_FINDCERT_PARAMS *fcparms,
122*3089Swyllys 	KMF_DELETECERT_PARAMS *dcparms)
123*3089Swyllys {
124*3089Swyllys 	KMF_RETURN rv = KMF_OK;
125*3089Swyllys 	uint32_t numcerts = 0;
126*3089Swyllys 
127*3089Swyllys 	rv = KMF_FindCert(kmfhandle, fcparms, NULL, &numcerts);
128*3089Swyllys 	if (rv == KMF_OK && numcerts > 0) {
129*3089Swyllys 		char prompt[1024];
130*3089Swyllys 		(void) snprintf(prompt, sizeof (prompt),
131*3089Swyllys 			gettext("%d certificate(s) found, do you want "
132*3089Swyllys 			"to delete them (y/N) ?"), numcerts);
133*3089Swyllys 
134*3089Swyllys 		if (!yesno(prompt,
135*3089Swyllys 			gettext("Respond with yes or no.\n"),
136*3089Swyllys 			B_FALSE)) {
137*3089Swyllys 			return (KMF_OK);
138*3089Swyllys 		}
139*3089Swyllys 
140*3089Swyllys 		rv = KMF_DeleteCertFromKeystore(kmfhandle, dcparms);
141*3089Swyllys 
142*3089Swyllys 	} else if (rv == KMF_ERR_CERT_NOT_FOUND) {
143*3089Swyllys 		rv = KMF_OK;
144*3089Swyllys 	}
145*3089Swyllys 
146*3089Swyllys 	return (rv);
147*3089Swyllys }
148*3089Swyllys 
149*3089Swyllys static KMF_RETURN
150*3089Swyllys delete_nss_keys(KMF_HANDLE_T kmfhandle, char *dir, char *prefix,
151*3089Swyllys 	char *token, int oclass, char *objlabel,
152*3089Swyllys 	KMF_CREDENTIAL *tokencred)
153*3089Swyllys {
154*3089Swyllys 	KMF_RETURN rv = KMF_OK;
155*3089Swyllys 	KMF_FINDKEY_PARAMS parms;
156*3089Swyllys 	char *keytype = NULL;
157*3089Swyllys 	int nk, numkeys = 0;
158*3089Swyllys 
159*3089Swyllys 	rv = configure_nss(kmfhandle, dir, prefix);
160*3089Swyllys 	if (rv != KMF_OK)
161*3089Swyllys 		return (rv);
162*3089Swyllys 
163*3089Swyllys 	(void) memset(&parms, 0, sizeof (parms));
164*3089Swyllys 	parms.kstype = KMF_KEYSTORE_NSS;
165*3089Swyllys 	parms.findLabel = objlabel;
166*3089Swyllys 	parms.cred = *tokencred;
167*3089Swyllys 	parms.nssparms.slotlabel = token;
168*3089Swyllys 
169*3089Swyllys 	if (oclass & PK_PRIKEY_OBJ) {
170*3089Swyllys 		parms.keyclass = KMF_ASYM_PRI;
171*3089Swyllys 		keytype = "private";
172*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, keytype, &nk);
173*3089Swyllys 		numkeys += nk;
174*3089Swyllys 	}
175*3089Swyllys 	if (rv == KMF_OK && (oclass & PK_SYMKEY_OBJ)) {
176*3089Swyllys 		parms.keyclass = KMF_SYMMETRIC;
177*3089Swyllys 		keytype = "symmetric";
178*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, keytype, &nk);
179*3089Swyllys 		numkeys += nk;
180*3089Swyllys 	}
181*3089Swyllys 	if (rv == KMF_OK && (oclass & PK_PUBKEY_OBJ)) {
182*3089Swyllys 		parms.keyclass = KMF_ASYM_PUB;
183*3089Swyllys 		keytype = "public";
184*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, keytype, &nk);
185*3089Swyllys 		numkeys += nk;
186*3089Swyllys 	}
187*3089Swyllys 	if (rv == KMF_OK && numkeys == 0)
188*3089Swyllys 		rv = KMF_ERR_KEY_NOT_FOUND;
189*3089Swyllys 
190*3089Swyllys 	return (rv);
191*3089Swyllys }
192*3089Swyllys 
193*3089Swyllys 
194*3089Swyllys static KMF_RETURN
195*3089Swyllys delete_nss_certs(KMF_HANDLE_T kmfhandle,
196*3089Swyllys 	char *dir, char *prefix,
197*3089Swyllys 	char *token, char *objlabel,
198*3089Swyllys 	KMF_BIGINT *serno, char *issuer, char *subject,
199*3089Swyllys 	KMF_CERT_VALIDITY find_criteria_flag)
200*3089Swyllys {
201*3089Swyllys 	KMF_RETURN rv = KMF_OK;
202*3089Swyllys 	KMF_DELETECERT_PARAMS dcparms;
203*3089Swyllys 	KMF_FINDCERT_PARAMS fcargs;
204*3089Swyllys 
205*3089Swyllys 	rv = configure_nss(kmfhandle, dir, prefix);
206*3089Swyllys 	if (rv != KMF_OK)
207*3089Swyllys 		return (rv);
208*3089Swyllys 
209*3089Swyllys 	(void) memset(&dcparms, 0, sizeof (dcparms));
210*3089Swyllys 	dcparms.kstype = KMF_KEYSTORE_NSS;
211*3089Swyllys 	dcparms.certLabel = objlabel;
212*3089Swyllys 	dcparms.issuer = issuer;
213*3089Swyllys 	dcparms.subject = subject;
214*3089Swyllys 	dcparms.serial = serno;
215*3089Swyllys 	dcparms.find_cert_validity = find_criteria_flag;
216*3089Swyllys 	dcparms.nssparms.slotlabel = token;
217*3089Swyllys 
218*3089Swyllys 	(void) memset(&fcargs, 0, sizeof (fcargs));
219*3089Swyllys 	fcargs.kstype = KMF_KEYSTORE_NSS;
220*3089Swyllys 	fcargs.certLabel = objlabel;
221*3089Swyllys 	fcargs.issuer = issuer;
222*3089Swyllys 	fcargs.subject = subject;
223*3089Swyllys 	fcargs.serial = serno;
224*3089Swyllys 	fcargs.find_cert_validity = find_criteria_flag;
225*3089Swyllys 	fcargs.nssparms.slotlabel = token;
226*3089Swyllys 
227*3089Swyllys 	rv = pk_delete_certs(kmfhandle, &fcargs, &dcparms);
228*3089Swyllys 
229*3089Swyllys 	return (rv);
230*3089Swyllys }
231*3089Swyllys 
232*3089Swyllys static KMF_RETURN
233*3089Swyllys delete_nss_crl(void *kmfhandle,
234*3089Swyllys 	char *dir, char *prefix, char *token,
235*3089Swyllys 	char *issuernickname, char *subject)
236*3089Swyllys {
237*3089Swyllys 	KMF_RETURN rv = KMF_OK;
238*3089Swyllys 	KMF_DELETECRL_PARAMS dcrlparms;
239*3089Swyllys 
240*3089Swyllys 	rv = configure_nss(kmfhandle, dir, prefix);
241*3089Swyllys 	if (rv != KMF_OK)
242*3089Swyllys 		return (rv);
243*3089Swyllys 
244*3089Swyllys 	(void) memset(&dcrlparms, 0, sizeof (dcrlparms));
245*3089Swyllys 
246*3089Swyllys 	dcrlparms.kstype = KMF_KEYSTORE_NSS;
247*3089Swyllys 	dcrlparms.nssparms.slotlabel = token;
248*3089Swyllys 	dcrlparms.nssparms.crl_issuerName = issuernickname;
249*3089Swyllys 	dcrlparms.nssparms.crl_subjName = subject;
250*3089Swyllys 
251*3089Swyllys 	rv = KMF_DeleteCRL(kmfhandle, &dcrlparms);
252*3089Swyllys 
253*3089Swyllys 	return (rv);
254*3089Swyllys }
255*3089Swyllys 
256*3089Swyllys static KMF_RETURN
257*3089Swyllys delete_pk11_keys(KMF_HANDLE_T kmfhandle,
258*3089Swyllys 	char *token, int oclass, char *objlabel,
259*3089Swyllys 	KMF_CREDENTIAL *tokencred)
260*3089Swyllys {
261*3089Swyllys 	KMF_RETURN rv = KMF_OK;
262*3089Swyllys 	KMF_FINDKEY_PARAMS parms;
263*3089Swyllys 	int nk, numkeys = 0;
264*3089Swyllys 
265*3089Swyllys 	/*
266*3089Swyllys 	 * Symmetric keys and RSA/DSA private keys are always
267*3089Swyllys 	 * created with the "CKA_PRIVATE" field == TRUE, so
268*3089Swyllys 	 * make sure we search for them with it also set.
269*3089Swyllys 	 */
270*3089Swyllys 	if (oclass & (PK_SYMKEY_OBJ | PK_PRIKEY_OBJ))
271*3089Swyllys 		oclass |= PK_PRIVATE_OBJ;
272*3089Swyllys 
273*3089Swyllys 	rv = select_token(kmfhandle, token, FALSE);
274*3089Swyllys 	if (rv != KMF_OK) {
275*3089Swyllys 		return (rv);
276*3089Swyllys 	}
277*3089Swyllys 
278*3089Swyllys 	(void) memset(&parms, 0, sizeof (parms));
279*3089Swyllys 	parms.kstype = KMF_KEYSTORE_PK11TOKEN;
280*3089Swyllys 	parms.findLabel = (char *)objlabel;
281*3089Swyllys 	parms.keytype = 0;
282*3089Swyllys 	parms.pkcs11parms.private = ((oclass & PK_PRIVATE_OBJ) > 0);
283*3089Swyllys 	parms.cred.cred = tokencred->cred;
284*3089Swyllys 	parms.cred.credlen = tokencred->credlen;
285*3089Swyllys 
286*3089Swyllys 	if (oclass & PK_PRIKEY_OBJ) {
287*3089Swyllys 		parms.keyclass = KMF_ASYM_PRI;
288*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, "private", &nk);
289*3089Swyllys 		numkeys += nk;
290*3089Swyllys 	}
291*3089Swyllys 
292*3089Swyllys 	if (rv == KMF_OK && (oclass & PK_SYMKEY_OBJ)) {
293*3089Swyllys 		parms.keyclass = KMF_SYMMETRIC;
294*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, "symmetric", &nk);
295*3089Swyllys 		numkeys += nk;
296*3089Swyllys 	}
297*3089Swyllys 
298*3089Swyllys 	if (rv == KMF_OK && (oclass & PK_PUBKEY_OBJ)) {
299*3089Swyllys 		parms.keyclass = KMF_ASYM_PUB;
300*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, "public", &nk);
301*3089Swyllys 		numkeys += nk;
302*3089Swyllys 	}
303*3089Swyllys 	if (rv == KMF_OK && numkeys == 0)
304*3089Swyllys 		rv = KMF_ERR_KEY_NOT_FOUND;
305*3089Swyllys 
306*3089Swyllys 	return (rv);
307*3089Swyllys }
308*3089Swyllys 
309*3089Swyllys static KMF_RETURN
310*3089Swyllys delete_pk11_certs(KMF_HANDLE_T kmfhandle,
311*3089Swyllys 	char *token, char *objlabel,
312*3089Swyllys 	KMF_BIGINT *serno, char *issuer, char *subject,
313*3089Swyllys 	KMF_CERT_VALIDITY find_criteria_flag)
314*3089Swyllys {
315*3089Swyllys 	KMF_RETURN kmfrv;
316*3089Swyllys 	KMF_DELETECERT_PARAMS dparms;
317*3089Swyllys 	KMF_FINDCERT_PARAMS fcargs;
318*3089Swyllys 
319*3089Swyllys 	kmfrv = select_token(kmfhandle, token, FALSE);
320*3089Swyllys 
321*3089Swyllys 	if (kmfrv != KMF_OK) {
322*3089Swyllys 		return (kmfrv);
323*3089Swyllys 	}
324*3089Swyllys 
325*3089Swyllys 	(void) memset(&dparms, 0, sizeof (dparms));
326*3089Swyllys 	dparms.kstype = KMF_KEYSTORE_PK11TOKEN;
327*3089Swyllys 	dparms.certLabel = objlabel;
328*3089Swyllys 	dparms.issuer = issuer;
329*3089Swyllys 	dparms.subject = subject;
330*3089Swyllys 	dparms.serial = serno;
331*3089Swyllys 	dparms.find_cert_validity = find_criteria_flag;
332*3089Swyllys 
333*3089Swyllys 	fcargs = dparms;
334*3089Swyllys 	kmfrv = pk_delete_certs(kmfhandle, &fcargs, &dparms);
335*3089Swyllys 
336*3089Swyllys 	return (kmfrv);
337*3089Swyllys }
338*3089Swyllys 
339*3089Swyllys static KMF_RETURN
340*3089Swyllys delete_file_certs(KMF_HANDLE_T kmfhandle,
341*3089Swyllys 	char *dir, char *filename, KMF_BIGINT *serial, char *issuer,
342*3089Swyllys 	char *subject, KMF_CERT_VALIDITY find_criteria_flag)
343*3089Swyllys {
344*3089Swyllys 	KMF_RETURN rv;
345*3089Swyllys 	KMF_DELETECERT_PARAMS dparms;
346*3089Swyllys 	KMF_FINDCERT_PARAMS fcargs;
347*3089Swyllys 
348*3089Swyllys 	(void *)memset(&dparms, 0, sizeof (dparms));
349*3089Swyllys 	(void *)memset(&fcargs, 0, sizeof (fcargs));
350*3089Swyllys 	fcargs.kstype = KMF_KEYSTORE_OPENSSL;
351*3089Swyllys 	fcargs.certLabel = NULL;
352*3089Swyllys 	fcargs.issuer = issuer;
353*3089Swyllys 	fcargs.subject = subject;
354*3089Swyllys 	fcargs.serial = serial;
355*3089Swyllys 	fcargs.sslparms.dirpath = dir;
356*3089Swyllys 	fcargs.sslparms.certfile = filename;
357*3089Swyllys 	fcargs.find_cert_validity = find_criteria_flag;
358*3089Swyllys 
359*3089Swyllys 	/* For now, delete parameters and find parameters are the same */
360*3089Swyllys 	dparms = fcargs;
361*3089Swyllys 
362*3089Swyllys 	rv = pk_delete_certs(kmfhandle, &fcargs, &dparms);
363*3089Swyllys 
364*3089Swyllys 	return (rv);
365*3089Swyllys }
366*3089Swyllys 
367*3089Swyllys static KMF_RETURN
368*3089Swyllys delete_file_keys(KMF_HANDLE_T kmfhandle, int oclass,
369*3089Swyllys 	char *dir, char *infile)
370*3089Swyllys {
371*3089Swyllys 	KMF_RETURN rv = KMF_OK;
372*3089Swyllys 	KMF_FINDKEY_PARAMS parms;
373*3089Swyllys 	char *keytype = "";
374*3089Swyllys 	int nk, numkeys = 0;
375*3089Swyllys 
376*3089Swyllys 	(void) memset(&parms, 0, sizeof (parms));
377*3089Swyllys 	parms.kstype = KMF_KEYSTORE_OPENSSL;
378*3089Swyllys 	parms.sslparms.dirpath = dir;
379*3089Swyllys 	parms.sslparms.keyfile = infile;
380*3089Swyllys 
381*3089Swyllys 	if (oclass & (PK_PUBKEY_OBJ | PK_PRIKEY_OBJ)) {
382*3089Swyllys 		parms.keyclass = KMF_ASYM_PRI;
383*3089Swyllys 		keytype = "Asymmetric";
384*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, keytype, &nk);
385*3089Swyllys 		numkeys += nk;
386*3089Swyllys 	}
387*3089Swyllys 	if (rv == KMF_OK && (oclass & PK_SYMKEY_OBJ)) {
388*3089Swyllys 		parms.keyclass = KMF_SYMMETRIC;
389*3089Swyllys 		keytype = "symmetric";
390*3089Swyllys 		rv = pk_delete_keys(kmfhandle, &parms, keytype, &nk);
391*3089Swyllys 		numkeys += nk;
392*3089Swyllys 	}
393*3089Swyllys 	if (rv == KMF_OK && numkeys == 0)
394*3089Swyllys 		rv = KMF_ERR_KEY_NOT_FOUND;
395*3089Swyllys 
396*3089Swyllys 	return (rv);
397*3089Swyllys }
398*3089Swyllys 
399*3089Swyllys static KMF_RETURN
400*3089Swyllys delete_file_crl(void *kmfhandle, char *dir, char *filename)
401*3089Swyllys {
402*3089Swyllys 	KMF_RETURN rv;
403*3089Swyllys 	KMF_DELETECRL_PARAMS dcrlparms;
404*3089Swyllys 
405*3089Swyllys 	(void) memset(&dcrlparms, 0, sizeof (dcrlparms));
406*3089Swyllys 
407*3089Swyllys 	dcrlparms.kstype = KMF_KEYSTORE_OPENSSL;
408*3089Swyllys 	dcrlparms.sslparms.dirpath = dir;
409*3089Swyllys 	dcrlparms.sslparms.crlfile = filename;
410*3089Swyllys 
411*3089Swyllys 	rv = KMF_DeleteCRL(kmfhandle, &dcrlparms);
412*3089Swyllys 
413*3089Swyllys 	return (rv);
414*3089Swyllys }
41517Sdinak 
41617Sdinak /*
41717Sdinak  * Delete token objects.
41817Sdinak  */
41917Sdinak int
42017Sdinak pk_delete(int argc, char *argv[])
42117Sdinak {
42217Sdinak 	int		opt;
423864Sdinak 	extern int	optind_av;
424864Sdinak 	extern char	*optarg_av;
425864Sdinak 	char		*token_spec = NULL;
426*3089Swyllys 	char		*subject = NULL;
427*3089Swyllys 	char		*issuer = NULL;
428*3089Swyllys 	char		*dir = NULL;
429*3089Swyllys 	char		*prefix = NULL;
430*3089Swyllys 	char		*infile = NULL;
431*3089Swyllys 	char		*object_label = NULL;
432*3089Swyllys 	char		*serstr = NULL;
43317Sdinak 
434*3089Swyllys 	int		oclass = 0;
435*3089Swyllys 	KMF_BIGINT	serial = { NULL, 0 };
436*3089Swyllys 	KMF_HANDLE_T	kmfhandle = NULL;
437*3089Swyllys 	KMF_KEYSTORE_TYPE	kstype = 0;
438*3089Swyllys 	KMF_RETURN	kmfrv;
439*3089Swyllys 	int		rv = 0;
440*3089Swyllys 	char			*find_criteria = NULL;
441*3089Swyllys 	KMF_CERT_VALIDITY	find_criteria_flag = KMF_ALL_CERTS;
442*3089Swyllys 	KMF_CREDENTIAL	tokencred = {NULL, 0};
44317Sdinak 
44417Sdinak 	/* Parse command line options.  Do NOT i18n/l10n. */
445864Sdinak 	while ((opt = getopt_av(argc, argv,
446*3089Swyllys 		"T:(token)y:(objtype)l:(label)"
447*3089Swyllys 		"k:(keystore)s:(subject)n:(nickname)"
448*3089Swyllys 		"d:(dir)p:(prefix)S:(serial)i:(issuer)"
449*3089Swyllys 		"c:(criteria)"
450*3089Swyllys 		"f:(infile)")) != EOF) {
451*3089Swyllys 
452*3089Swyllys 		if (EMPTYSTRING(optarg_av))
453*3089Swyllys 			return (PK_ERR_USAGE);
45417Sdinak 		switch (opt) {
455864Sdinak 		case 'T':	/* token specifier */
456864Sdinak 			if (token_spec)
457864Sdinak 				return (PK_ERR_USAGE);
458864Sdinak 			token_spec = optarg_av;
45917Sdinak 			break;
460864Sdinak 		case 'y':	/* object type:  public, private, both */
461*3089Swyllys 			if (oclass)
462864Sdinak 				return (PK_ERR_USAGE);
463*3089Swyllys 			oclass = OT2Int(optarg_av);
464*3089Swyllys 			if (oclass == -1)
465*3089Swyllys 				return (PK_ERR_USAGE);
46617Sdinak 			break;
46717Sdinak 		case 'l':	/* objects with specific label */
468*3089Swyllys 		case 'n':
46917Sdinak 			if (object_label)
47017Sdinak 				return (PK_ERR_USAGE);
471*3089Swyllys 			object_label = (char *)optarg_av;
472*3089Swyllys 			break;
473*3089Swyllys 		case 'k':
474*3089Swyllys 			kstype = KS2Int(optarg_av);
475*3089Swyllys 			if (kstype == 0)
476*3089Swyllys 				return (PK_ERR_USAGE);
477*3089Swyllys 			break;
478*3089Swyllys 		case 's':
479*3089Swyllys 			subject = optarg_av;
480*3089Swyllys 			break;
481*3089Swyllys 		case 'i':
482*3089Swyllys 			issuer = optarg_av;
483*3089Swyllys 			break;
484*3089Swyllys 		case 'd':
485*3089Swyllys 			dir = optarg_av;
486*3089Swyllys 			break;
487*3089Swyllys 		case 'p':
488*3089Swyllys 			prefix = optarg_av;
489*3089Swyllys 			break;
490*3089Swyllys 		case 'S':
491*3089Swyllys 			serstr = optarg_av;
492*3089Swyllys 			break;
493*3089Swyllys 		case 'f':
494*3089Swyllys 			infile = optarg_av;
495*3089Swyllys 			break;
496*3089Swyllys 		case 'c':
497*3089Swyllys 			find_criteria = optarg_av;
498*3089Swyllys 			if (!strcasecmp(find_criteria, "valid"))
499*3089Swyllys 				find_criteria_flag =
500*3089Swyllys 					KMF_NONEXPIRED_CERTS;
501*3089Swyllys 			else if (!strcasecmp(find_criteria, "expired"))
502*3089Swyllys 				find_criteria_flag = KMF_EXPIRED_CERTS;
503*3089Swyllys 			else if (!strcasecmp(find_criteria, "both"))
504*3089Swyllys 				find_criteria_flag = KMF_ALL_CERTS;
505*3089Swyllys 			else
506*3089Swyllys 				return (PK_ERR_USAGE);
50717Sdinak 			break;
50817Sdinak 		default:
50917Sdinak 			return (PK_ERR_USAGE);
51017Sdinak 			break;
51117Sdinak 		}
51217Sdinak 	}
51317Sdinak 
514*3089Swyllys 	/* Assume keystore = PKCS#11 if not specified */
515*3089Swyllys 	if (kstype == 0)
516*3089Swyllys 		kstype = KMF_KEYSTORE_PK11TOKEN;
517*3089Swyllys 
518*3089Swyllys 	/* if PUBLIC or PRIVATE obj was given, the old syntax was used. */
519*3089Swyllys 	if ((oclass & (PK_PUBLIC_OBJ | PK_PRIVATE_OBJ)) &&
520*3089Swyllys 		kstype != KMF_KEYSTORE_PK11TOKEN) {
521*3089Swyllys 
522*3089Swyllys 		(void) fprintf(stderr, gettext("The objtype parameter "
523*3089Swyllys 			"is only relevant if keystore=pkcs11\n"));
524*3089Swyllys 		return (PK_ERR_USAGE);
525864Sdinak 	}
526864Sdinak 
527*3089Swyllys 	/* If no object class specified, delete everything but CRLs */
528*3089Swyllys 	if (oclass == 0)
529*3089Swyllys 		oclass = PK_CERT_OBJ | PK_PUBKEY_OBJ | PK_PRIKEY_OBJ |
530*3089Swyllys 			PK_SYMKEY_OBJ;
53117Sdinak 
53217Sdinak 	/* No additional args allowed. */
533864Sdinak 	argc -= optind_av;
534864Sdinak 	argv += optind_av;
53517Sdinak 	if (argc)
53617Sdinak 		return (PK_ERR_USAGE);
53717Sdinak 	/* Done parsing command line options. */
53817Sdinak 
539*3089Swyllys 	if (kstype == KMF_KEYSTORE_PK11TOKEN && token_spec == NULL) {
540*3089Swyllys 		token_spec = PK_DEFAULT_PK11TOKEN;
541*3089Swyllys 	} else if (kstype == KMF_KEYSTORE_NSS && token_spec == NULL) {
542*3089Swyllys 		token_spec = DEFAULT_NSS_TOKEN;
54317Sdinak 	}
54417Sdinak 
545*3089Swyllys 	if (serstr != NULL) {
546*3089Swyllys 		uchar_t *bytes = NULL;
547*3089Swyllys 		size_t bytelen;
548*3089Swyllys 
549*3089Swyllys 		rv = KMF_HexString2Bytes((uchar_t *)serstr, &bytes, &bytelen);
550*3089Swyllys 		if (rv != KMF_OK || bytes == NULL) {
551*3089Swyllys 			(void) fprintf(stderr, gettext("serial number "
552*3089Swyllys 				"must be specified as a hex number "
553*3089Swyllys 				"(ex: 0x0102030405ffeeddee)\n"));
554*3089Swyllys 			return (PK_ERR_USAGE);
555*3089Swyllys 		}
556*3089Swyllys 		serial.val = bytes;
557*3089Swyllys 		serial.len = bytelen;
55817Sdinak 	}
55917Sdinak 
560*3089Swyllys 	if ((kstype == KMF_KEYSTORE_PK11TOKEN ||
561*3089Swyllys 		kstype == KMF_KEYSTORE_NSS) &&
562*3089Swyllys 		(oclass & (PK_KEY_OBJ | PK_PRIVATE_OBJ))) {
56317Sdinak 
564*3089Swyllys 		(void) get_token_password(kstype, token_spec,
565*3089Swyllys 			&tokencred);
56617Sdinak 	}
56717Sdinak 
568*3089Swyllys 	if ((kmfrv = KMF_Initialize(&kmfhandle, NULL, NULL)) != KMF_OK)
569*3089Swyllys 		return (kmfrv);
570*3089Swyllys 
571*3089Swyllys 	switch (kstype) {
572*3089Swyllys 		case KMF_KEYSTORE_PK11TOKEN:
573*3089Swyllys 			if (oclass & PK_KEY_OBJ) {
574*3089Swyllys 				kmfrv = delete_pk11_keys(kmfhandle,
575*3089Swyllys 						token_spec, oclass,
576*3089Swyllys 						object_label,
577*3089Swyllys 						&tokencred);
578*3089Swyllys 				/*
579*3089Swyllys 				 * If deleting groups of objects, it is OK
580*3089Swyllys 				 * to ignore the "key not found" case so that
581*3089Swyllys 				 * we can continue to find other objects.
582*3089Swyllys 				 */
583*3089Swyllys 				if (kmfrv == KMF_ERR_KEY_NOT_FOUND &&
584*3089Swyllys 					(oclass != PK_KEY_OBJ))
585*3089Swyllys 					kmfrv = KMF_OK;
586*3089Swyllys 				if (kmfrv != KMF_OK)
587*3089Swyllys 					break;
588*3089Swyllys 			}
589*3089Swyllys 			if (oclass & (PK_CERT_OBJ | PK_PUBLIC_OBJ)) {
590*3089Swyllys 				kmfrv = delete_pk11_certs(kmfhandle,
591*3089Swyllys 						token_spec,
592*3089Swyllys 						object_label,
593*3089Swyllys 						&serial, issuer,
594*3089Swyllys 						subject, find_criteria_flag);
595*3089Swyllys 				/*
596*3089Swyllys 				 * If cert delete failed, but we are looking at
597*3089Swyllys 				 * other objects, then it is OK.
598*3089Swyllys 				 */
599*3089Swyllys 				if (kmfrv == KMF_ERR_CERT_NOT_FOUND &&
600*3089Swyllys 					(oclass & (PK_CRL_OBJ | PK_KEY_OBJ)))
601*3089Swyllys 					kmfrv = KMF_OK;
602*3089Swyllys 				if (kmfrv != KMF_OK)
603*3089Swyllys 					break;
604*3089Swyllys 			}
605*3089Swyllys 			if (oclass & PK_CRL_OBJ)
606*3089Swyllys 				kmfrv = delete_file_crl(kmfhandle,
607*3089Swyllys 						dir, infile);
608*3089Swyllys 			break;
609*3089Swyllys 		case KMF_KEYSTORE_NSS:
610*3089Swyllys 			if (oclass & PK_KEY_OBJ) {
611*3089Swyllys 				kmfrv = delete_nss_keys(kmfhandle,
612*3089Swyllys 					dir, prefix, token_spec,
613*3089Swyllys 					oclass, (char  *)object_label,
614*3089Swyllys 					&tokencred);
615*3089Swyllys 				if (kmfrv != KMF_OK)
616*3089Swyllys 					break;
617*3089Swyllys 			}
618*3089Swyllys 			if (oclass & PK_CERT_OBJ) {
619*3089Swyllys 				kmfrv = delete_nss_certs(kmfhandle,
620*3089Swyllys 					dir, prefix, token_spec,
621*3089Swyllys 					(char  *)object_label,
622*3089Swyllys 					&serial, issuer, subject,
623*3089Swyllys 					find_criteria_flag);
624*3089Swyllys 				if (kmfrv != KMF_OK)
625*3089Swyllys 					break;
626*3089Swyllys 			}
627*3089Swyllys 			if (oclass & PK_CRL_OBJ)
628*3089Swyllys 				kmfrv = delete_nss_crl(kmfhandle,
629*3089Swyllys 					dir, prefix, token_spec,
630*3089Swyllys 					(char  *)object_label, subject);
631*3089Swyllys 			break;
632*3089Swyllys 		case KMF_KEYSTORE_OPENSSL:
633*3089Swyllys 			if (oclass & PK_KEY_OBJ) {
634*3089Swyllys 				kmfrv = delete_file_keys(kmfhandle, oclass,
635*3089Swyllys 					dir, infile);
636*3089Swyllys 				if (kmfrv != KMF_OK)
637*3089Swyllys 					break;
638*3089Swyllys 			}
639*3089Swyllys 			if (oclass & (PK_CERT_OBJ)) {
640*3089Swyllys 				kmfrv = delete_file_certs(kmfhandle,
641*3089Swyllys 					dir, infile, &serial, issuer,
642*3089Swyllys 					subject, find_criteria_flag);
643*3089Swyllys 				if (kmfrv != KMF_OK)
644*3089Swyllys 					break;
645*3089Swyllys 			}
646*3089Swyllys 			if (oclass & PK_CRL_OBJ)
647*3089Swyllys 				kmfrv = delete_file_crl(kmfhandle,
648*3089Swyllys 					dir, infile);
649*3089Swyllys 			break;
650*3089Swyllys 		default:
651*3089Swyllys 			rv = PK_ERR_USAGE;
652*3089Swyllys 			break;
65317Sdinak 	}
65417Sdinak 
655*3089Swyllys 	if (kmfrv != KMF_OK) {
656*3089Swyllys 		display_error(kmfhandle, kmfrv,
657*3089Swyllys 			gettext("Error deleting objects"));
65817Sdinak 	}
65917Sdinak 
660*3089Swyllys 	if (serial.val != NULL)
661*3089Swyllys 		free(serial.val);
662*3089Swyllys 	(void) KMF_Finalize(kmfhandle);
663*3089Swyllys 	return (kmfrv);
66417Sdinak }
665