Esempio n. 1
0
static int generate_pwd_shares(sc_card_t *card, char **pwd, int *pwdlen, int password_shares_threshold, int password_shares_total)
{
	int r, i;
	BIGNUM prime;
	BIGNUM secret;
	char buf[64];
	char hex[64];
	int l;

	secret_share_t *shares = NULL;
	secret_share_t *sp;

	u8 rngseed[16];

	printf(	"\nThe DKEK will be enciphered using a randomly generated 64 bit password.\n");
	printf(	"This password is split using a (%i-of-%i) threshold scheme.\n\n", password_shares_threshold, password_shares_total);

	printf(	"Please keep the generated and encrypted DKEK file in a safe location. We also recommend \n");
	printf(	"to keep a paper printout, in case the electronic version becomes unavailable. A printable version\n");
	printf(	"of the file can be generated using \"openssl base64 -in <filename>\".\n");

	printf("\n\nPress <enter> to continue");

	waitForEnterKeyPressed();

	*pwd = calloc(1, 8);
	*pwdlen = 8;

	r = sc_get_challenge(card, *pwd, 8);
	if (r < 0) {
		printf("Error generating random key failed with ", sc_strerror(r));
		OPENSSL_cleanse(pwd, *pwdlen);
		free(pwd);
		return r;
	}
	**pwd |= 0x80;

	/*
	 * Initialize prime and secret
	 */
	BN_init(&prime);
	BN_init(&secret);

	/*
	 * Encode the secret value
	 */
	BN_bin2bn(*pwd, *pwdlen, &secret);

	/*
	 * Generate seed and calculate a prime depending on the size of the secret
	 */
	r = sc_get_challenge(card, rngseed, 16);
	if (r < 0) {
		printf("Error generating random seed failed with ", sc_strerror(r));
		OPENSSL_cleanse(pwd, *pwdlen);
		free(pwd);
		return r;
	}

	generatePrime(&prime, &secret, password_shares_total, rngseed);

	// Allocate data buffer for the generated shares
	shares = malloc(password_shares_total * sizeof(secret_share_t));

	createShares(&secret, password_shares_threshold, password_shares_total, prime, shares);

	sp = shares;
	for (i = 0; i < password_shares_total; i++) {
		clearScreen();

		printf("Press <enter> to display key share %i of %i\n\n", i + 1, password_shares_total);
		waitForEnterKeyPressed();

		clearScreen();

		printf("Share %i of %i\n\n", i + 1, password_shares_total);

		l = BN_bn2bin(&prime, buf);
		sc_bin_to_hex(buf, l, hex, 64, ':');
		printf("\nPrime       : %s\n", hex);

		printf("Share ID    : %s\n", BN_bn2dec(&(sp->x)));
		l = BN_bn2bin(&(sp->y), buf);
		sc_bin_to_hex(buf, l, hex, 64, ':');
		printf("Share value : %s\n", hex);

		printf("\n\nPlease note ALL values above and press <enter> when finished");
		waitForEnterKeyPressed();

		sp++;
	}

	clearScreen();

	cleanUpShares(shares, password_shares_total);

	BN_clear_free(&prime);
	BN_clear_free(&secret);

	return 0;
}
Esempio n. 2
0
static int recreate_password_from_shares(char **pwd, int *pwdlen, int num_of_password_shares)
{
	int r, i;
	BIGNUM *prime;
	BIGNUM *secret;
	BIGNUM *p;
	char inbuf[64];
	unsigned char bin[64];
	size_t binlen = 0;
	unsigned char *ip;
	secret_share_t *shares = NULL;
	secret_share_t *sp;

	if (num_of_password_shares < 2) {
		fprintf(stderr, "--pwd-shares-total must 2 or larger\n");
		return -1;
	}

	// Allocate data buffer for the shares
	shares = malloc(num_of_password_shares * sizeof(secret_share_t));
	if (!shares)
		return -1;

	/*
	 * Initialize prime and secret
	 */
	prime = BN_new();
	secret = BN_new();

	printf("\nDeciphering the DKEK for import into the SmartCard-HSM requires %i key custodians", num_of_password_shares);
	printf("\nto present their share. Only the first key custodian needs to enter the public prime.");
	printf("\nPlease remember to present the share id as well as the share value.");
	printf("\n\nPlease enter prime: ");
	memset(inbuf, 0, sizeof(inbuf));
	if (fgets(inbuf, sizeof(inbuf), stdin) == NULL) {
		fprintf(stderr, "Input aborted\n");
		free(shares);
		return -1;
	}
	binlen = 64;
	sc_hex_to_bin(inbuf, bin, &binlen);
	BN_bin2bn(bin, binlen, prime);

	sp = shares;
	for (i = 0; i < num_of_password_shares; i++) {
		clearScreen();

		printf("Press <enter> to enter share %i of %i\n\n", i + 1, num_of_password_shares);
		waitForEnterKeyPressed();

		clearScreen();

		sp->x = BN_new();
		sp->y = BN_new();

		printf("Share %i of %i\n\n", i + 1, num_of_password_shares);

		printf("Please enter share ID: ");
		memset(inbuf, 0, sizeof(inbuf));
		if (fgets(inbuf, sizeof(inbuf), stdin) == NULL) {
			fprintf(stderr, "Input aborted\n");
			free(shares);
			return -1;
		}
		p = (sp->x);
		BN_hex2bn(&p, inbuf);

		printf("Please enter share value: ");
		memset(inbuf, 0, sizeof(inbuf));
		if (fgets(inbuf, sizeof(inbuf), stdin) == NULL) {
			fprintf(stderr, "Input aborted\n");
			free(shares);
			return -1;
		}
		binlen = 64;
		sc_hex_to_bin(inbuf, bin, &binlen);
		BN_bin2bn(bin, binlen, (sp->y));

		sp++;
	}

	clearScreen();

	r = reconstructSecret(shares, num_of_password_shares, prime, secret);

	if (r < 0) {
		printf("\nError during reconstruction of secret. Wrong shares?\n");
		cleanUpShares(shares, num_of_password_shares);
		return r;
	}

	/*
	 * Encode the secret value
	 */
	ip = (unsigned char *) inbuf;
	*pwdlen = BN_bn2bin(secret, ip);
	*pwd = calloc(1, *pwdlen);
	if (*pwd) {
		memcpy(*pwd, ip, *pwdlen);
	}

	cleanUpShares(shares, num_of_password_shares);

	BN_clear_free(prime);
	BN_clear_free(secret);

	return *pwd ? 0 : -1;
}
Esempio n. 3
0
static int recreate_password_from_shares(char **pwd, int *pwdlen, int num_of_password_shares) {

	int r, i;
	BIGNUM prime;
	BIGNUM secret;
	BIGNUM *p;
	char inbuf[64];
	char bin[64];
	int binlen = 0;
	char *ip;
	secret_share_t *shares = NULL;
	secret_share_t *sp;

	/*
	 * Initialize prime and secret
	 */
	BN_init(&prime);
	BN_init(&secret);

	// Allocate data buffer for the shares
	shares = malloc(num_of_password_shares * sizeof(secret_share_t));

	printf("\nDeciphering the DKEK for import into the SmartCard-HSM requires %i key custodians", num_of_password_shares);
	printf("\nto present their share. Only the first key custodian needs to enter the public prime.");
	printf("\nPlease remember to present the share id as well as the share value.");
	printf("\n\nPlease enter prime: ");
	memset(inbuf, 0, sizeof(inbuf));
	fgets(inbuf, sizeof(inbuf), stdin);
	binlen = 64;
	sc_hex_to_bin(inbuf, bin, &binlen);
	BN_bin2bn(bin, binlen, &prime);

	sp = shares;
	for (i = 0; i < num_of_password_shares; i++) {
		clearScreen();

		printf("Press <enter> to enter share %i of %i\n\n", i + 1, num_of_password_shares);
		waitForEnterKeyPressed();

		clearScreen();

		BN_init(&(sp->x));
		BN_init(&(sp->y));

		printf("Share %i of %i\n\n", i + 1, num_of_password_shares);

		printf("Please enter share ID: ");
		memset(inbuf, 0, sizeof(inbuf));
		fgets(inbuf, sizeof(inbuf), stdin);
		p = &(sp->x);
		BN_hex2bn(&p, inbuf);

		printf("Please enter share value: ");
		memset(inbuf, 0, sizeof(inbuf));
		fgets(inbuf, sizeof(inbuf), stdin);
		binlen = 64;
		sc_hex_to_bin(inbuf, bin, &binlen);
		BN_bin2bn(bin, binlen, &(sp->y));

		sp++;
	}

	clearScreen();

	r = reconstructSecret(shares, num_of_password_shares, prime, &secret);

	if (r < 0) {
		printf("\nError during reconstruction of secret. Wrong shares?\n");
		return r;
	}

	/*
	 * Encode the secret value
	 */
	ip = inbuf;
	*pwdlen = BN_bn2bin(&secret, ip);
	*pwd = calloc(1, *pwdlen);
	memcpy(*pwd, ip, *pwdlen);

	cleanUpShares(shares, num_of_password_shares);

	BN_clear_free(&prime);
	BN_clear_free(&secret);

	return 0;
}
Esempio n. 4
0
static int generate_pwd_shares(sc_card_t *card, char **pwd, int *pwdlen, int password_shares_threshold, int password_shares_total)
{
	int r, i;
	BIGNUM *prime;
	BIGNUM *secret;
	unsigned char buf[64];
	char hex[64];
	int l;

	secret_share_t *shares = NULL;
	secret_share_t *sp;

	u8 rngseed[16];

	if ((password_shares_threshold == -1) || (password_shares_total == -1)) {
		fprintf(stderr, "Must specify both, --pwd-shares-total and --pwd-shares-threshold\n");
		return -1;
	}

	if (password_shares_total < 3) {
		fprintf(stderr, "--pwd-shares-total must be 3 or larger\n");
		return -1;
	}

	if (password_shares_threshold < 2) {
		fprintf(stderr, "--pwd-shares-threshold must 2 or larger\n");
		return -1;
	}

	if (password_shares_threshold > password_shares_total) {
		fprintf(stderr, "--pwd-shares-threshold must be smaller or equal to --pwd-shares-total\n");
		return -1;
	}

	printf(	"\nThe DKEK will be enciphered using a randomly generated 64 bit password.\n");
	printf(	"This password is split using a (%i-of-%i) threshold scheme.\n\n", password_shares_threshold, password_shares_total);

	printf(	"Please keep the generated and encrypted DKEK file in a safe location. We also recommend \n");
	printf(	"to keep a paper printout, in case the electronic version becomes unavailable. A printable version\n");
	printf(	"of the file can be generated using \"openssl base64 -in <filename>\".\n");

	printf("\n\nPress <enter> to continue");

	waitForEnterKeyPressed();

	*pwd = calloc(1, 8);
	*pwdlen = 8;

	r = sc_get_challenge(card, (unsigned char *)*pwd, 8);
	if (r < 0) {
		printf("Error generating random key failed with %s", sc_strerror(r));
		OPENSSL_cleanse(*pwd, *pwdlen);
		free(*pwd);
		return r;
	}
	**pwd &= 0x7F; // Make sure the bit size of the secret is not bigger than 63 bits

	/*
	 * Initialize prime and secret
	 */
	prime = BN_new();
	secret = BN_new();

	/*
	 * Encode the secret value
	 */
	BN_bin2bn((unsigned char *)*pwd, *pwdlen, secret);

	/*
	 * Generate seed and calculate a prime depending on the size of the secret
	 */
	r = sc_get_challenge(card, rngseed, SEED_LENGTH);
	if (r < 0) {
		printf("Error generating random seed failed with %s", sc_strerror(r));
		OPENSSL_cleanse(*pwd, *pwdlen);
		free(*pwd);
		return r;
	}

	r = generatePrime(prime, secret, 64, rngseed, SEED_LENGTH);
	if (r < 0) {
		printf("Error generating valid prime number. Please try again.");
		OPENSSL_cleanse(*pwd, *pwdlen);
		free(*pwd);
		return r;
	}

	// Allocate data buffer for the generated shares
	shares = malloc(password_shares_total * sizeof(secret_share_t));

	createShares(secret, password_shares_threshold, password_shares_total, prime, shares);

	sp = shares;
	for (i = 0; i < password_shares_total; i++) {
		clearScreen();

		printf("Press <enter> to display key share %i of %i\n\n", i + 1, password_shares_total);
		waitForEnterKeyPressed();

		clearScreen();

		printf("Share %i of %i\n\n", i + 1, password_shares_total);

		l = BN_bn2bin(prime, buf);
		sc_bin_to_hex(buf, l, hex, 64, ':');
		printf("\nPrime       : %s\n", hex);

		printf("Share ID    : %s\n", BN_bn2dec((sp->x)));
		l = BN_bn2bin((sp->y), buf);
		sc_bin_to_hex(buf, l, hex, 64, ':');
		printf("Share value : %s\n", hex);

		printf("\n\nPlease note ALL values above and press <enter> when finished");
		waitForEnterKeyPressed();

		sp++;
	}

	clearScreen();

	cleanUpShares(shares, password_shares_total);

	BN_clear_free(prime);
	BN_clear_free(secret);

	return 0;
}