|
Packit |
6b81fa |
/* libp11 example code: listkeys.c
|
|
Packit |
6b81fa |
*
|
|
Packit |
6b81fa |
* This examply simply connects to your smart card
|
|
Packit |
6b81fa |
* and list the keys.
|
|
Packit |
6b81fa |
*
|
|
Packit |
6b81fa |
* Feel free to copy all of the code as needed.
|
|
Packit |
6b81fa |
*
|
|
Packit |
6b81fa |
*/
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
#include <sys/types.h>
|
|
Packit |
6b81fa |
#include <sys/stat.h>
|
|
Packit |
6b81fa |
#include <fcntl.h>
|
|
Packit |
6b81fa |
#include <stdio.h>
|
|
Packit |
6b81fa |
#include <unistd.h>
|
|
Packit |
6b81fa |
#include <string.h>
|
|
Packit |
6b81fa |
#include <sys/types.h>
|
|
Packit |
6b81fa |
#include <libp11.h>
|
|
Packit |
6b81fa |
#include <unistd.h>
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
#define RANDOM_SOURCE "/dev/urandom"
|
|
Packit |
6b81fa |
#define RANDOM_SIZE 20
|
|
Packit |
6b81fa |
#define MAX_SIGSIZE 256
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
static void list_keys(const char *title,
|
|
Packit |
6b81fa |
const PKCS11_KEY *keys, const unsigned int nkeys);
|
|
Packit |
6b81fa |
static void error_queue(const char *name);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
#define CHECK_ERR(cond, txt, code) \
|
|
Packit |
6b81fa |
do { \
|
|
Packit |
6b81fa |
if (cond) { \
|
|
Packit |
6b81fa |
fprintf(stderr, "%s\n", (txt)); \
|
|
Packit |
6b81fa |
rc=(code); \
|
|
Packit |
6b81fa |
goto end; \
|
|
Packit |
6b81fa |
} \
|
|
Packit |
6b81fa |
} while (0)
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
int main(int argc, char *argv[])
|
|
Packit |
6b81fa |
{
|
|
Packit |
6b81fa |
PKCS11_CTX *ctx=NULL;
|
|
Packit |
6b81fa |
PKCS11_SLOT *slots=NULL, *slot;
|
|
Packit |
6b81fa |
PKCS11_KEY *keys;
|
|
Packit |
6b81fa |
unsigned int nslots, nkeys;
|
|
Packit |
6b81fa |
int rc = 0;
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
if (argc < 2) {
|
|
Packit |
6b81fa |
fprintf(stderr,
|
|
Packit |
6b81fa |
"usage: %s /usr/lib/opensc-pkcs11.so [PIN]\n",
|
|
Packit |
6b81fa |
argv[0]);
|
|
Packit |
6b81fa |
return 1;
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
ctx = PKCS11_CTX_new();
|
|
Packit |
6b81fa |
error_queue("PKCS11_CTX_new");
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
/* load pkcs #11 module */
|
|
Packit |
6b81fa |
rc = PKCS11_CTX_load(ctx, argv[1]);
|
|
Packit |
6b81fa |
error_queue("PKCS11_CTX_load");
|
|
Packit |
6b81fa |
CHECK_ERR(rc < 0, "loading pkcs11 engine failed", 1);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
/* get information on all slots */
|
|
Packit |
6b81fa |
rc = PKCS11_enumerate_slots(ctx, &slots, &nslots);
|
|
Packit |
6b81fa |
error_queue("PKCS11_enumerate_slots");
|
|
Packit |
6b81fa |
CHECK_ERR(rc < 0, "no slots available", 2);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
/* get first slot with a token */
|
|
Packit |
6b81fa |
slot = PKCS11_find_token(ctx, slots, nslots);
|
|
Packit |
6b81fa |
error_queue("PKCS11_find_token");
|
|
Packit |
6b81fa |
CHECK_ERR(!slot || !slot->token, "no token available", 3);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
printf("Slot manufacturer......: %s\n", slot->manufacturer);
|
|
Packit |
6b81fa |
printf("Slot description.......: %s\n", slot->description);
|
|
Packit |
6b81fa |
printf("Slot token label.......: %s\n", slot->token->label);
|
|
Packit |
6b81fa |
printf("Slot token manufacturer: %s\n", slot->token->manufacturer);
|
|
Packit |
6b81fa |
printf("Slot token model.......: %s\n", slot->token->model);
|
|
Packit |
6b81fa |
printf("Slot token serialnr....: %s\n", slot->token->serialnr);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
/* get public keys */
|
|
Packit |
6b81fa |
rc = PKCS11_enumerate_public_keys(slot->token, &keys, &nkeys);
|
|
Packit |
6b81fa |
error_queue("PKCS11_enumerate_public_keys");
|
|
Packit |
6b81fa |
CHECK_ERR(rc < 0, "PKCS11_enumerate_public_keys failed", 4);
|
|
Packit |
6b81fa |
CHECK_ERR(nkeys == 0, "No public keys found", 5);
|
|
Packit |
6b81fa |
list_keys("Public keys", keys, nkeys);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
if (slot->token->loginRequired && argc > 2) {
|
|
Packit |
6b81fa |
/* perform pkcs #11 login */
|
|
Packit |
6b81fa |
rc = PKCS11_login(slot, 0, argv[2]);
|
|
Packit |
6b81fa |
error_queue("PKCS11_login");
|
|
Packit |
6b81fa |
CHECK_ERR(rc < 0, "PKCS11_login failed", 6);
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
/* get private keys */
|
|
Packit |
6b81fa |
rc = PKCS11_enumerate_keys(slot->token, &keys, &nkeys);
|
|
Packit |
6b81fa |
error_queue("PKCS11_enumerate_keys");
|
|
Packit |
6b81fa |
CHECK_ERR(rc < 0, "PKCS11_enumerate_keys failed", 7);
|
|
Packit |
6b81fa |
CHECK_ERR(nkeys == 0, "No private keys found", 8);
|
|
Packit |
6b81fa |
list_keys("Private keys", keys, nkeys);
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
end:
|
|
Packit |
6b81fa |
if (slots)
|
|
Packit |
6b81fa |
PKCS11_release_all_slots(ctx, slots, nslots);
|
|
Packit |
6b81fa |
if (ctx) {
|
|
Packit |
6b81fa |
PKCS11_CTX_unload(ctx);
|
|
Packit |
6b81fa |
PKCS11_CTX_free(ctx);
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
if (rc)
|
|
Packit |
6b81fa |
printf("Failed (error code %d).\n", rc);
|
|
Packit |
6b81fa |
else
|
|
Packit |
6b81fa |
printf("Success.\n");
|
|
Packit |
6b81fa |
return rc;
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
static void list_keys(const char *title, const PKCS11_KEY *keys,
|
|
Packit |
6b81fa |
const unsigned int nkeys) {
|
|
Packit |
6b81fa |
unsigned int i;
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
printf("\n%s:\n", title);
|
|
Packit |
6b81fa |
for (i = 0; i < nkeys; i++)
|
|
Packit |
6b81fa |
printf(" * %s key: %s\n",
|
|
Packit |
6b81fa |
keys[i].isPrivate ? "Private" : "Public", keys[i].label);
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
static void error_queue(const char *name)
|
|
Packit |
6b81fa |
{
|
|
Packit |
6b81fa |
if (ERR_peek_last_error()) {
|
|
Packit |
6b81fa |
fprintf(stderr, "%s generated errors:\n", name);
|
|
Packit |
6b81fa |
ERR_print_errors_fp(stderr);
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
}
|
|
Packit |
6b81fa |
|
|
Packit |
6b81fa |
/* vim: set noexpandtab: */
|