View | Details | Raw Unified | Return to bug 2638 | Differences between
and this patch

Collapse All | Expand All

(-)a/ssh-pkcs11.c (-25 / +94 lines)
Lines 230-235 pkcs11_find(struct pkcs11_provider *p, CK_ULONG slotidx, CK_ATTRIBUTE *attr, Link Here
230
	return (ret);
230
	return (ret);
231
}
231
}
232
232
233
static int
234
pkcs11_login(struct pkcs11_key *k11, CK_USER_TYPE type)
235
{
236
	struct pkcs11_slotinfo	*si;
237
	CK_FUNCTION_LIST	*f;
238
	char			*pin = NULL, prompt[1024];
239
	CK_RV			 rv;
240
241
	if (!k11->provider || !k11->provider->valid) {
242
		error("no pkcs11 (valid) provider found");
243
		return (-1);
244
	}
245
246
	f = k11->provider->function_list;
247
	si = &k11->provider->slotinfo[k11->slotidx];
248
249
	if (!pkcs11_interactive) {
250
		error("need pin entry%s",
251
		    (si->token.flags & CKF_PROTECTED_AUTHENTICATION_PATH) ?
252
		    " on reader keypad" : "");
253
		return (-1);
254
	}
255
	if (si->token.flags & CKF_PROTECTED_AUTHENTICATION_PATH)
256
		verbose("Deferring PIN entry to reader keypad.");
257
	else {
258
		snprintf(prompt, sizeof(prompt), "Enter PIN for '%s': ",
259
		    si->token.label);
260
		if ((pin = read_passphrase(prompt, RP_ALLOW_EOF)) == NULL) {
261
			debug("%s: no pin specified", __func__);
262
			return (-1);	/* bail out */
263
		}
264
	}
265
	rv = f->C_Login(si->session, type, (u_char *)pin,
266
	    (pin != NULL) ? strlen(pin) : 0);
267
	if (pin != NULL)
268
		freezero(pin, strlen(pin));
269
	if (rv != CKR_OK && rv != CKR_USER_ALREADY_LOGGED_IN) {
270
		error("C_Login failed: %lu", rv);
271
		return (-1);
272
	}
273
	si->logged_in = 1;
274
	return (0);
275
}
276
277
static int
278
pkcs11_check_obj_bool_attrib(struct pkcs11_key *k11, CK_OBJECT_HANDLE obj,
279
    CK_ATTRIBUTE_TYPE type, int *val)
280
{
281
	struct pkcs11_slotinfo	*si;
282
	CK_FUNCTION_LIST	*f;
283
	CK_BBOOL		flag = 0;
284
	CK_ATTRIBUTE		attr;
285
	CK_RV			 rv;
286
287
	*val = 0;
288
289
	if (!k11->provider || !k11->provider->valid) {
290
		error("no pkcs11 (valid) provider found");
291
		return (-1);
292
	}
293
294
	f = k11->provider->function_list;
295
	si = &k11->provider->slotinfo[k11->slotidx];
296
297
	attr.type = type;
298
	attr.pValue = &flag;
299
	attr.ulValueLen = sizeof(flag);
300
301
	rv = f->C_GetAttributeValue(si->session, obj, &attr, 1);
302
	if (rv != CKR_OK) {
303
		error("C_GetAttributeValue failed: %lu", rv);
304
		return (-1);
305
	}
306
	*val = flag != 0;
307
	debug("%s: provider %p slot %lu object %lu: attrib %lu = %d",
308
	    __func__, k11->provider, k11->slotidx, obj, type, *val);
309
	return (0);
310
}
311
233
static int
312
static int
234
pkcs11_get_key(struct pkcs11_key *k11, CK_MECHANISM_TYPE mech_type)
313
pkcs11_get_key(struct pkcs11_key *k11, CK_MECHANISM_TYPE mech_type)
235
{
314
{
Lines 241-247 pkcs11_get_key(struct pkcs11_key *k11, CK_MECHANISM_TYPE mech_type) Link Here
241
	CK_BBOOL		 true_val;
320
	CK_BBOOL		 true_val;
242
	CK_MECHANISM		 mech;
321
	CK_MECHANISM		 mech;
243
	CK_ATTRIBUTE		 key_filter[3];
322
	CK_ATTRIBUTE		 key_filter[3];
244
	char			*pin = NULL, prompt[1024];
323
	int			 always_auth = 0;
324
	int			 did_login = 0;
245
325
246
	if (!k11->provider || !k11->provider->valid) {
326
	if (!k11->provider || !k11->provider->valid) {
247
		error("no pkcs11 (valid) provider found");
327
		error("no pkcs11 (valid) provider found");
Lines 252-283 pkcs11_get_key(struct pkcs11_key *k11, CK_MECHANISM_TYPE mech_type) Link Here
252
	si = &k11->provider->slotinfo[k11->slotidx];
332
	si = &k11->provider->slotinfo[k11->slotidx];
253
333
254
	if ((si->token.flags & CKF_LOGIN_REQUIRED) && !si->logged_in) {
334
	if ((si->token.flags & CKF_LOGIN_REQUIRED) && !si->logged_in) {
255
		if (!pkcs11_interactive) {
335
		if (pkcs11_login(k11, CKU_USER) < 0) {
256
			error("need pin entry%s", (si->token.flags &
336
			error("login failed");
257
			    CKF_PROTECTED_AUTHENTICATION_PATH) ?
258
			    " on reader keypad" : "");
259
			return (-1);
337
			return (-1);
260
		}
338
		}
261
		if (si->token.flags & CKF_PROTECTED_AUTHENTICATION_PATH)
339
		did_login = 1;
262
			verbose("Deferring PIN entry to reader keypad.");
263
		else {
264
			snprintf(prompt, sizeof(prompt),
265
			    "Enter PIN for '%s': ", si->token.label);
266
			pin = read_passphrase(prompt, RP_ALLOW_EOF);
267
			if (pin == NULL)
268
				return (-1);	/* bail out */
269
		}
270
		rv = f->C_Login(si->session, CKU_USER, (u_char *)pin,
271
		    (pin != NULL) ? strlen(pin) : 0);
272
		if (pin != NULL) {
273
			explicit_bzero(pin, strlen(pin));
274
			free(pin);
275
		}
276
		if (rv != CKR_OK && rv != CKR_USER_ALREADY_LOGGED_IN) {
277
			error("C_Login failed: %lu", rv);
278
			return (-1);
279
		}
280
		si->logged_in = 1;
281
	}
340
	}
282
341
283
	memset(&key_filter, 0, sizeof(key_filter));
342
	memset(&key_filter, 0, sizeof(key_filter));
Lines 312-317 pkcs11_get_key(struct pkcs11_key *k11, CK_MECHANISM_TYPE mech_type) Link Here
312
		return (-1);
371
		return (-1);
313
	}
372
	}
314
373
374
	pkcs11_check_obj_bool_attrib(k11, obj, CKA_ALWAYS_AUTHENTICATE,
375
	    &always_auth); /* ignore errors here */
376
	if (always_auth && !did_login) {
377
		debug("%s: always-auth key", __func__);
378
		if (pkcs11_login(k11, CKU_CONTEXT_SPECIFIC) < 0) {
379
			error("login failed for always-auth key");
380
			return (-1);
381
		}
382
	}
383
315
	return (0);
384
	return (0);
316
}
385
}
317
386

Return to bug 2638