Commit 3a5eb0b7 authored by Mike Hibler's avatar Mike Hibler

More cleanup, get frisbee on board with signed/encrypted images.

parent 81f23715
......@@ -13,8 +13,12 @@ DISTFILES = TODO client.c decls.h event.c event.h log.c log.h \
network.c queue.h server.c trace.c trace.h utils.c utils.h
EXPANDCOPYRIGHT = /usr/site/lib/copyright/expand-copyr
# Set to 1 for "secure frisbee" support. Requires openssl libraries.
#
# Support encrypted and signed-checksumed images.
# Requires openssl libraries.
#
WITH_CRYPTO = 1
WITH_SIGNING = 1
SYSTEM := $(shell uname -s)
......@@ -103,7 +107,10 @@ IUZFLAGS = -DFRISBEE
IUZLIBS =
ifeq ($(WITH_CRYPTO),1)
IUZFLAGS += -DWITH_CRYPTO -DSIGN_CHECKSUM
IUZFLAGS += -DWITH_CRYPTO
ifeq ($(WITH_SIGNING),1)
IUZFLAGS += -DSIGN_CHECKSUM
endif
IUZLIBS += -lcrypto
endif
......
......@@ -78,7 +78,7 @@ static int GotBlock(Packet_t *p);
static void RequestChunk(int timedout);
static int RequestStamp(int chunk, int block, int count, void *arg);
static int RequestRedoTime(int chunk, unsigned long long curtime);
extern int ImageUnzipInitKeys(char *uuid, char *sig_keyfile,
extern int ImageUnzipInitKeys(char *uuidstr, char *sig_keyfile,
char *enc_keyfile);
extern int ImageUnzipInit(char *filename, int slice, int debug, int zero,
int nothreads, int dostype, int dodots,
......@@ -219,7 +219,7 @@ main(int argc, char **argv)
char *filename = NULL;
int dostype = -1;
int slice = 0;
char *sig_keyfile = 0, *enc_keyfile = 0, *uuid = 0;
char *sig_keyfile = 0, *enc_keyfile = 0, *uuidstr = 0;
while ((ch = getopt(argc, argv, "dqhp:m:s:i:tbznT:r:E:D:C:W:S:M:R:I:ONc:e:u:K:B:F:Q:P:X:")) != -1)
switch(ch) {
......@@ -391,12 +391,8 @@ main(int argc, char **argv)
break;
case 'u':
{
extern char *str_to_uuid(char *);
uuid = str_to_uuid(optarg);
uuidstr = optarg;
break;
}
case 'K':
keepalive = atoi(optarg);
......@@ -626,7 +622,7 @@ main(int argc, char **argv)
/*
* Initialize keys for authentication/encryption.
*/
ImageUnzipInitKeys(uuid, sig_keyfile, enc_keyfile);
ImageUnzipInitKeys(uuidstr, sig_keyfile, enc_keyfile);
/*
* Pass in assorted parameters and fire off the disk writer thread.
......
......@@ -254,22 +254,3 @@ hexstr_to_mem(unsigned char * dest, const char * source, int memsize)
}
return result;
}
/*
* XXX hack for frisbee use.
* So we don't have to worry about UUID_LENGTH constant there.
*/
char *
str_to_uuid(char *srcstr)
{
unsigned char *buf = calloc(UUID_LENGTH, 1);
if (!buf)
return NULL;
if (!hexstr_to_mem(buf, srcstr, UUID_LENGTH)) {
free(buf);
return NULL;
}
return (char *)buf;
}
......@@ -291,9 +291,12 @@ dumpfile(char *name, int fd)
magic - COMPRESSED_MAGIC_BASE + 1);
if (magic >= COMPRESSED_V4) {
sigtype = hdr->csum_type;
if (sigtype != CSUM_NONE)
printf(", signed (%d)",
sigtype);
if (sigtype != CSUM_NONE) {
printf(", ");
if (sigtype & CSUM_SIGNED)
printf("signed ");
printf("csum (0x%x)", sigtype);
}
enctype = hdr->enc_cipher;
if (enctype != ENC_NONE)
printf(", encrypted (%d)",
......@@ -461,10 +464,10 @@ dumpchunk(char *name, char *buf, int chunkno, int checkindex)
}
}
if (checksums && hdr->csum_type != CSUM_NONE) {
if (hdr->csum_type != CSUM_SHA1) {
if ((hdr->csum_type & CSUM_TYPE) != CSUM_SHA1) {
printf("%s: unsupported checksum type %d in "
"chunk %d", name,
hdr->csum_type,
(hdr->csum_type & CSUM_TYPE),
chunkno);
return 1;
}
......@@ -517,6 +520,9 @@ dumpchunk(char *name, char *buf, int chunkno, int checkindex)
if (hdr->csum_type != CSUM_NONE) {
len = 0;
switch (hdr->csum_type) {
case CSUM_SIGNED|CSUM_SHA1:
len = CSUM_MAX_LEN;
break;
case CSUM_SHA1:
len = CSUM_SHA1_LEN;
break;
......
......@@ -131,7 +131,7 @@ static int *chunklist, *nextchunk;
#endif
/* UUID for the current image, all chunks must have the same ID */
static unsigned char imageid[UUID_LENGTH];
static unsigned char uuid[UUID_LENGTH];
static int has_id = 0;
/*
......@@ -200,7 +200,7 @@ unsigned long splits;
/* security */
static int do_checksum = 0;
static int do_decrypt = 0;
static char *cipherarg = NULL;
static int cipher = ENC_NONE;
static unsigned char encryption_key[ENC_MAX_KEYLEN];
#endif
......@@ -653,8 +653,10 @@ main(int argc, char *argv[])
case 'e':
/* Encryption cipher */
cipherarg = optarg;
if (strcmp(cipherarg, "bf_cbc") != 0) {
if (strcmp(optarg, "bf_cbc") == 0) {
cipher = ENC_BLOWFISH_CBC;
}
else {
fprintf(stderr,
"Only know \"bf_cbc\" (blowfish CBC)\n");
usage();
......@@ -666,12 +668,15 @@ main(int argc, char *argv[])
if (!encrypt_readkey(optarg, encryption_key,
ENC_MAX_KEYLEN))
exit(1);
/* XXX can you intuit the cipher from the key? */
if (cipher == ENC_NONE)
cipher = ENC_BLOWFISH_CBC;
do_decrypt = 1;
break;
#endif
case 'u':
/* UUID for image id. */
if (!hexstr_to_mem(imageid, optarg, UUID_LENGTH))
if (!hexstr_to_mem(uuid, optarg, UUID_LENGTH))
usage();
has_id = 1;
break;
......@@ -913,14 +918,17 @@ main(int argc, char *argv[])
* When compiled for frisbee, act as a library.
*/
int
ImageUnzipInitKeys(char *uuid, char *sig_keyfile, char *enc_keyfile)
ImageUnzipInitKeys(char *uuidstr, char *sig_keyfile, char *enc_keyfile)
{
if (uuid) {
memcpy(imageid, uuid, UUID_LENGTH);
if (uuidstr) {
if (!hexstr_to_mem(uuid, uuidstr, UUID_LENGTH)) {
fprintf(stderr, "Bogus UUID\n");
exit(1);
}
has_id = 1;
}
#ifdef WITH_CRYPTO
#ifdef WITH_CRYPTO
if (sig_keyfile) {
#ifdef SIGN_CHECKSUM
if (!init_checksum(sig_keyfile))
......@@ -1233,12 +1241,12 @@ decrypt_buffer(unsigned char *dest, const unsigned char *source,
int final_count = 0;
int error = 0;
EVP_CIPHER_CTX context;
EVP_CIPHER const *cipher;
EVP_CIPHER const *ecipher;
EVP_CIPHER_CTX_init(&context);
cipher = EVP_bf_cbc();
ecipher = EVP_bf_cbc();
EVP_DecryptInit(&context, cipher, NULL, header->enc_iv);
EVP_DecryptInit(&context, ecipher, NULL, header->enc_iv);
EVP_CIPHER_CTX_set_key_length(&context, ENC_MAX_KEYLEN);
EVP_DecryptInit(&context, NULL, encryption_key, NULL);
......@@ -1361,15 +1369,15 @@ inflate_subblock(const char *chunkbufp)
*/
if (has_id == 0) {
has_id = 1;
memcpy(imageid, blockhdr->imageid, UUID_LENGTH);
} else if (memcmp(imageid, blockhdr->imageid, UUID_LENGTH)) {
memcpy(uuid, blockhdr->imageid, UUID_LENGTH);
} else if (memcmp(uuid, blockhdr->imageid, UUID_LENGTH)) {
char uuidstr[UUID_LENGTH*2 + 1];
fprintf(stderr, "Incorrect Image ID in chunk %d:\n",
blockhdr->blockindex);
mem_to_hexstr(uuidstr, blockhdr->imageid, UUID_LENGTH);
fprintf(stderr, " In chunk: 0x%s\n", uuidstr);
mem_to_hexstr(uuidstr, imageid, UUID_LENGTH);
mem_to_hexstr(uuidstr, uuid, UUID_LENGTH);
fprintf(stderr, " Should be: 0x%s\n", uuidstr);
exit(1);
}
......@@ -1383,9 +1391,9 @@ inflate_subblock(const char *chunkbufp)
fprintf(stderr, "Chunk has no cipher\n");
exit(1);
}
if (blockhdr->enc_cipher != ENC_BLOWFISH_CBC) {
if (blockhdr->enc_cipher != cipher) {
fprintf(stderr,
"Chunk cipher type %d not supported\n",
"Wrong cipher type %d in chunk\n",
blockhdr->enc_cipher);
exit(1);
}
......
......@@ -72,9 +72,9 @@ int dorelocs = 1;
int metaoptimize = 0;
int filemode = 0;
int do_encrypt = 0;
char *cipherarg = NULL;
int cipher = ENC_NONE;
int do_checksum = 0;
char *sighasharg = NULL;
int csumalg = CSUM_NONE;
off_t datawritten;
partmap_t ignore, forceraw;
static int got_imageid;
......@@ -492,14 +492,17 @@ main(int argc, char *argv[])
case 'a':
#ifdef WITH_CRYPTO
/* Authentication (checksum) hash algorithm */
sighasharg = optarg;
if (strcmp(sighasharg, "SHA1") != 0) {
fprintf(stderr,
"Only know \"SHA1\"\n");
if (strcmp(optarg, "SHA1") == 0) {
csumalg = CSUM_SHA1;
}
else {
fprintf(stderr, "Only know \"SHA1\"\n");
usage();
}
do_checksum++;
#ifndef SIGN_CHECKSUM
#ifdef SIGN_CHECKSUM
csumalg |= CSUM_SIGNED;
#else
fprintf(stderr, "WARNING: checksum is not signed\n");
#endif
#else
......@@ -511,8 +514,10 @@ main(int argc, char *argv[])
case 'e':
#ifdef WITH_CRYPTO
/* Encryption cipher */
cipherarg = optarg;
if (strcmp(cipherarg, "bf_cbc") != 0) {
if (strcmp(optarg, "bf_cbc") == 0) {
cipher = ENC_BLOWFISH_CBC;
}
else {
fprintf(stderr,
"Only know \"bf_cbc\" (blowfish CBC)\n");
usage();
......@@ -530,6 +535,9 @@ main(int argc, char *argv[])
if (enc_key == NULL ||
!encrypt_readkey(optarg, enc_key, ENC_MAX_KEYLEN))
usage();
/* XXX can you intuit the cipher from the key? */
if (cipher == ENC_NONE)
cipher = ENC_BLOWFISH_CBC;
#else
fprintf(stderr, "'k' option not supported\n");
usage();
......@@ -1809,7 +1817,7 @@ static off_t compress_chunk(off_t, off_t, int *, uint32_t *);
static int compress_finish(uint32_t *subblksize);
static void compress_status(int sig);
#ifdef WITH_CRYPTO
static void checksum_start(blockhdr_t *hdr);
static void checksum_start(blockhdr_t *hdr, int alg);
static void checksum_chunk(uint8_t *buf, off_t size);
static void checksum_finish(blockhdr_t *hdr);
static void encrypt_start(blockhdr_t *hdr);
......@@ -2062,7 +2070,7 @@ compress_image(void)
*/
if (do_checksum) {
assert(!compat);
checksum_start(blkhdr);
checksum_start(blkhdr, csumalg);
checksum_chunk(output_buffer,
blkhdr->size + blkhdr->regionsize);
checksum_finish(blkhdr);
......@@ -2190,7 +2198,7 @@ compress_image(void)
*/
if (do_checksum) {
assert(!compat);
checksum_start(blkhdr);
checksum_start(blkhdr, csumalg);
checksum_chunk(output_buffer,
blkhdr->size + blkhdr->regionsize);
checksum_finish(blkhdr);
......@@ -2532,7 +2540,7 @@ compress_finish(uint32_t *subblksize)
*/
SHA_CTX sha_ctx;
void
checksum_start(blockhdr_t *hdr)
checksum_start(blockhdr_t *hdr, int alg)
{
/*
* Start with the checksum zeroed out - this way, we can put the
......@@ -2542,10 +2550,7 @@ checksum_start(blockhdr_t *hdr)
memset(hdr->checksum, 0, sizeof(hdr->checksum));
/* type is part of the checksum */
hdr->csum_type = CSUM_SHA1;
#ifdef SIGN_CHECKSUM
hdr->csum_type |= CSUM_SIGNED;
#endif
hdr->csum_type = alg;
SHA1_Init(&sha_ctx);
}
......@@ -2706,7 +2711,7 @@ checksum_finish(blockhdr_t *hdr)
* Encryption functions
*/
static EVP_CIPHER_CTX cipher_ctx;
static const EVP_CIPHER *cipher;
static const EVP_CIPHER *ecipher;
/* XXX: the size of the IV may have to change with different ciphers */
static uint8_t iv[ENC_MAX_KEYLEN];
......@@ -2726,7 +2731,7 @@ encrypt_start(blockhdr_t *hdr)
* Pick our cipher - currently, only Blowfish in CBC mode is supported
*/
EVP_CIPHER_CTX_init(&cipher_ctx);
cipher = EVP_bf_cbc();
ecipher = EVP_bf_cbc();
/*
* If this is the first chunk, generate a new IV. Otherwise, we use
......@@ -2767,7 +2772,7 @@ encrypt_start(blockhdr_t *hdr)
/*
* Set the cipher and IV
*/
EVP_EncryptInit(&cipher_ctx, cipher, NULL, iv);
EVP_EncryptInit(&cipher_ctx, ecipher, NULL, iv);
/*
* Bump up the key length and set the key
......@@ -2815,7 +2820,7 @@ encrypt_finish(blockhdr_t *hdr, uint8_t *outbuf, uint32_t *out_size)
assert(encrypted_bytes <= CHUNKMAX);
memcpy(outbuf, encryption_buffer, encrypted_bytes);
hdr->enc_cipher = ENC_BLOWFISH_CBC;
hdr->enc_cipher = cipher;
*out_size = encrypted_bytes;
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment