1 /* -*- mode: c; c-file-style:"stroustrup"; -*- */
2 
3 /*
4  * Copyright (c) 2018 Mastercard
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *   http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  */
18 
19 #include <config.h>
20 #include <stdio.h>
21 #include <stdlib.h>
22 #include <string.h>
23 #include <unistd.h>
24 #include "pkcs11lib.h"
25 
26 #ifdef _WIN32
27 #include <openssl/applink.c>
28 #endif
29 
30 #define COMMAND_SUMMARY \
31     "Delete object(s) from PKCS#11 token.\n\n"
32 
33 
34 /* prototypes */
35 void print_version_info(char *progname);
36 void print_usage(char *);
37 int main( int argc, char **argv);
38 
39 
print_usage(char * progname)40 void print_usage(char *progname)
41 {
42     fprintf( stderr, "USAGE: %s OPTIONS ARGUMENTS\n"
43 	     "\n"
44 	     COMMAND_SUMMARY
45 	     "OPTIONS:\n"
46 	     "* -l <pkcs#11 library path> : path to PKCS#11 library\n"
47 	     "  -m <NSS config dir> ( e.g. '.' or 'sql:.' ) : NSS db directory \n"
48 	     "  -s <slot number>\n"
49 	     "  -t <token label> : if present, -s option is ignored\n"
50 	     "  -p <token PIN> | :::exec:<command> | :::nologin\n"
51 	     "  -S : login with SO privilege\n"
52 	     "  -y : force positive answer (non-interactive)\n"
53 	     "  -v : verbose\n"
54 	     "  -h : print usage information\n"
55 	     "  -V : print version information\n"
56 	     "|\n"
57 	     "+-> arguments marked with an asterix(*) are mandatory\n"
58              "|   (except if environment variable sets the value)\n"
59 	     "+-> arguments marked with a plus sign(+) can be repeated\n"
60 	     "\n"
61 	     "ARGUMENTS:\n"
62 	     " LABEL [LABEL ...]: object label(s) to erase\n"
63 	     "                    can be prefixed with cert/, prvk/, pubk/ or seck/)\n"
64 	     "                    if no prefix, objects from all classes sharing the\n"
65 	     "                    same label are deleted\n"
66 	     "\n"
67              " ENVIRONMENT VARIABLES:\n"
68 	     "    PKCS11LIB         : path to PKCS#11 library,\n"
69              "                        overriden by option -l\n"
70 	     "    PKCS11NSSDIR      : NSS configuration directory directive,\n"
71              "                        overriden by option -m\n"
72 	     "    PKCS11SLOT        : token slot (integer)\n"
73 	     "                        overriden by PKCS11TOKENLABEL,\n"
74 	     "                        options -t or -s\n"
75 	     "    PKCS11TOKENLABEL  : token label\n"
76 	     "                        overriden by options -t or -s\n"
77 	     "    PKCS11PASSWORD    : password\n"
78              "                        overriden by option -p\n"
79 	     "\n"
80 	     , pkcs11_ll_basename(progname) );
81 
82     exit( RC_ERROR_USAGE );
83 }
84 
main(int argc,char ** argv)85 int main( int argc, char ** argv )
86 {
87     extern char *optarg;
88     extern int optind, optopt;
89     int argnum = 0;
90     int errflag = 0;
91     char * library = NULL;
92     char * nsscfgdir = NULL;
93     char * password = NULL;
94     char * slotenv = NULL;
95     int slot = -1;
96     int interactive = 1;
97     char * tokenlabel = NULL;
98     int so=0;
99     int ask_confirm=1;
100     int verbose=0;
101 
102     pkcs11Context * p11Context = NULL;
103     func_rc retcode = rc_error_usage;
104 
105     library = getenv("PKCS11LIB");
106     nsscfgdir = getenv("PKCS11NSSDIR");
107     tokenlabel = getenv("PKCS11TOKENLABEL");
108     if(tokenlabel==NULL) {
109 	slotenv = getenv("PKCS11SLOT");
110 	if (slotenv!=NULL) {
111 	    slot=atoi(slotenv);
112 	}
113     }
114     password = getenv("PKCS11PASSWORD");
115 
116     /* if a slot or a token is given, interactive is null */
117     if(slotenv!=NULL || tokenlabel!=NULL) {
118 	interactive=0;
119     }
120 
121     /* get the command-line arguments */
122     while ( ( argnum = getopt( argc, argv, "l:m:p:s:t:yvShV" ) ) != -1 )
123     {
124 	switch ( argnum )
125 	{
126 	case 'l' :
127 	    library =  optarg;
128 	    break;
129 
130 	case 'm':
131 	    nsscfgdir = optarg;
132 	    break;
133 
134 	case 'p' :
135 	    password = optarg;
136 	    break;
137 
138 	case 's':
139 	    slot = atoi(optarg);
140 	    tokenlabel = NULL;
141 	    interactive=0;
142 	    break;
143 
144 	case 't':
145 	    tokenlabel = optarg;
146 	    slot = -1;
147 	    interactive = 0;
148 	    break;
149 
150 	case 'y':
151 	    ask_confirm = 0;
152 	    break;
153 
154 	case 'v':
155 	    verbose = 1;
156 	    break;
157 
158 	case 'S':
159 	    so=1;
160 	  break;
161 
162 	case 'h':
163 	    print_usage(argv[0]);
164 	    break;
165 
166 	case 'V':
167 	    print_version_info(argv[0]);
168 	    break;
169 
170 	default:
171 	    errflag++;
172 	    break;
173 	}
174     }
175 
176     if ( errflag ) {
177 	fprintf(stderr, "Try `%s -h' for more information.\n", argv[0]);
178 	goto err;
179     }
180 
181 
182     if ( library == NULL || optind==argc ) {
183 	fprintf( stderr, "At least one required option or argument is wrong or missing.\n"
184 		 "Try `%s -h' for more information.\n", argv[0]);
185 	goto err;
186     }
187 
188     if((p11Context = pkcs11_newContext( library, nsscfgdir ))==NULL) {
189       goto err;
190     }
191 
192     /* validate the given provider library exists and can be opened */
193     if (( retcode = pkcs11_initialize( p11Context ) ) != CKR_OK ) {
194       goto err;
195     }
196 
197     retcode = pkcs11_open_session( p11Context, slot, tokenlabel, password, so, interactive);
198 
199     if ( retcode == rc_ok )
200     {
201 	while(optind<argc) {
202 	    pkcs11_rm_objects_with_label(p11Context, argv[optind++], ask_confirm, verbose);
203 	}
204 
205 	pkcs11_close_session( p11Context );
206     }
207     pkcs11_finalize( p11Context );
208 
209     /* free allocated memory */
210  err:
211     pkcs11_freeContext(p11Context);
212 
213     return retcode;
214 }
215