Commit 304bdd7d authored by Ondrej Kozina's avatar Ondrej Kozina Committed by Milan Broz

luks2: add json_object_new_uint64 wrapper

json doesn't support 64 bits integers. We workaround it by storing
large numbers as string and validate the value internally.
parent 382d27b4
......@@ -151,8 +151,6 @@ unsigned crypt_cpusonline(void);
int init_crypto(struct crypt_device *ctx);
const char *uint64_to_str(char *buffer, size_t size, const uint64_t *val);
void logger(struct crypt_device *cd, int class, const char *file, int line, const char *format, ...) __attribute__ ((format (printf, 5, 6)));
#define log_dbg(x...) logger(NULL, CRYPT_LOG_DEBUG, __FILE__, __LINE__, x)
#define log_std(c, x...) logger(c, CRYPT_LOG_NORMAL, __FILE__, __LINE__, x)
......
......@@ -55,6 +55,7 @@ void hexprint_base64(struct crypt_device *cd, json_object *jobj,
json_object *parse_json_len(const char *json_area, int length, int *end_offset);
uint64_t json_object_get_uint64(json_object *jobj);
uint32_t json_object_get_uint32(json_object *jobj);
json_object *json_object_new_uint64(uint64_t value);
void JSON_DBG(json_object *jobj, const char *desc);
......
......@@ -190,7 +190,7 @@ int LUKS2_generate_hdr(
offset += alignOffset;
}
json_object_object_add(jobj_segment, "offset", json_object_new_string(uint64_to_str(num, sizeof(num), &offset)));
json_object_object_add(jobj_segment, "offset", json_object_new_uint64(offset));
json_object_object_add(jobj_segment, "iv_tweak", json_object_new_string("0"));
json_object_object_add(jobj_segment, "size", json_object_new_string("dynamic"));
json_object_object_add(jobj_segment, "encryption", json_object_new_string(cipher));
......@@ -208,8 +208,7 @@ int LUKS2_generate_hdr(
json_object_object_add(jobj_segments, num, jobj_segment);
json_size = hdr->hdr_size - LUKS2_HDR_BIN_LEN;
json_object_object_add(jobj_config, "json_size",
json_object_new_string(uint64_to_str(num, sizeof(num), &json_size)));
json_object_object_add(jobj_config, "json_size", json_object_new_uint64(json_size));
/* for detached metadata device compute reasonable keyslot areas size */
// FIXME: this is coupled with FIXME above
......@@ -225,8 +224,7 @@ int LUKS2_generate_hdr(
/* keyslots size has to be 4 KiB aligned */
keyslots_size -= (keyslots_size % 4096);
json_object_object_add(jobj_config, "keyslots_size",
json_object_new_string(uint64_to_str(num, sizeof(num), &keyslots_size)));
json_object_object_add(jobj_config, "keyslots_size", json_object_new_uint64(keyslots_size));
JSON_DBG(hdr->jobj, "Header JSON");
return 0;
......
......@@ -209,6 +209,21 @@ uint64_t json_object_get_uint64(json_object *jobj)
return json_str_to_uint64(jobj, &r) ? r : 0;
}
json_object *json_object_new_uint64(uint64_t value)
{
/* 18446744073709551615 */
char num[21];
int r;
json_object *jobj;
r = snprintf(num, sizeof(num), "%" PRIu64, value);
if (r < 0 || (size_t)r >= sizeof(num))
return NULL;
jobj = json_object_new_string(num);
return jobj;
}
/*
* Validate helpers
*/
......
......@@ -381,7 +381,6 @@ int luks2_keyslot_alloc(struct crypt_device *cd,
{
struct luks2_hdr *hdr;
const struct crypt_pbkdf_type *pbkdf;
char area_offset_string[24], area_length_string[24];
char cipher[2 * MAX_CIPHER_LEN + 1], num[16];
uint64_t area_offset, area_length;
json_object *jobj_keyslots, *jobj_keyslot, *jobj_kdf, *jobj_af, *jobj_area;
......@@ -463,10 +462,8 @@ int luks2_keyslot_alloc(struct crypt_device *cd,
json_object_object_add(jobj_area, "encryption", json_object_new_string(cipher));
json_object_object_add(jobj_area, "key_size", json_object_new_int(keyslot_key_len));
uint64_to_str(area_offset_string, sizeof(area_offset_string), &area_offset);
json_object_object_add(jobj_area, "offset", json_object_new_string(area_offset_string));
uint64_to_str(area_length_string, sizeof(area_length_string), &area_length);
json_object_object_add(jobj_area, "size", json_object_new_string(area_length_string));
json_object_object_add(jobj_area, "offset", json_object_new_uint64(area_offset));
json_object_object_add(jobj_area, "size", json_object_new_uint64(area_length));
json_object_object_add(jobj_keyslot, "area", jobj_area);
snprintf(num, sizeof(num), "%d", keyslot);
......
......@@ -26,7 +26,7 @@
static int json_luks1_keyslot(const struct luks_phdr *hdr_v1, int keyslot, struct json_object **keyslot_object)
{
char *base64_str, cipher[LUKS_CIPHERNAME_L+LUKS_CIPHERMODE_L], num[24];
char *base64_str, cipher[LUKS_CIPHERNAME_L+LUKS_CIPHERMODE_L];
size_t base64_len;
struct json_object *keyslot_obj, *field, *jobj_kdf, *jobj_af, *jobj_area;
uint64_t offset, area_size, offs_a, offs_b, length;
......@@ -83,8 +83,8 @@ static int json_luks1_keyslot(const struct luks_phdr *hdr_v1, int keyslot, struc
}
area_size = offs_b - offs_a;
json_object_object_add(jobj_area, "key_size", json_object_new_int(hdr_v1->keyBytes));
json_object_object_add(jobj_area, "offset", json_object_new_string(uint64_to_str(num, sizeof(num), &offset)));
json_object_object_add(jobj_area, "size", json_object_new_string(uint64_to_str(num, sizeof(num), &area_size)));
json_object_object_add(jobj_area, "offset", json_object_new_uint64(offset));
json_object_object_add(jobj_area, "size", json_object_new_uint64(area_size));
json_object_object_add(keyslot_obj, "area", jobj_area);
*keyslot_object = keyslot_obj;
......@@ -121,7 +121,6 @@ static int json_luks1_segment(const struct luks_phdr *hdr_v1, struct json_object
{
const char *c;
char cipher[LUKS_CIPHERNAME_L+LUKS_CIPHERMODE_L];
char num[24]; /* uint64_t in string */
struct json_object *segment_obj, *field;
uint64_t number;
......@@ -140,7 +139,7 @@ static int json_luks1_segment(const struct luks_phdr *hdr_v1, struct json_object
/* offset field */
number = (uint64_t)hdr_v1->payloadOffset * SECTOR_SIZE;
field = json_object_new_string(uint64_to_str(num, sizeof(num), &number));
field = json_object_new_uint64(number);
if (!field) {
json_object_put(segment_obj);
return -ENOMEM;
......@@ -348,7 +347,6 @@ static int json_luks1_digests(const struct luks_phdr *hdr_v1, struct json_object
static int json_luks1_object(struct luks_phdr *hdr_v1, struct json_object **luks1_object, uint64_t keyslots_size)
{
char num[24];
int r;
struct json_object *luks1_obj, *field;
uint64_t json_size;
......@@ -399,10 +397,8 @@ static int json_luks1_object(struct luks_phdr *hdr_v1, struct json_object **luks
json_object_object_add(luks1_obj, "config", field);
json_size = LUKS2_HDR_16K_LEN - LUKS2_HDR_BIN_LEN;
json_object_object_add(field, "json_size",
json_object_new_string(uint64_to_str(num, sizeof(num), &json_size)));
json_object_object_add(field, "keyslots_size",
json_object_new_string(uint64_to_str(num, sizeof(num), &keyslots_size)));
json_object_object_add(field, "json_size", json_object_new_uint64(json_size));
json_object_object_add(field, "keyslots_size", json_object_new_uint64(keyslots_size));
*luks1_object = luks1_obj;
return 0;
......@@ -410,7 +406,6 @@ static int json_luks1_object(struct luks_phdr *hdr_v1, struct json_object **luks
static void move_keyslot_offset(json_object *jobj, int offset_add)
{
char num[24];
json_object *jobj1, *jobj2, *jobj_area;
uint64_t offset = 0;
......@@ -420,7 +415,7 @@ static void move_keyslot_offset(json_object *jobj, int offset_add)
json_object_object_get_ex(val, "area", &jobj_area);
json_object_object_get_ex(jobj_area, "offset", &jobj2);
offset = json_object_get_uint64(jobj2) + offset_add;
json_object_object_add(jobj_area, "offset", json_object_new_string(uint64_to_str(num, sizeof(num), &offset)));
json_object_object_add(jobj_area, "offset", json_object_new_uint64(offset));
}
}
......
......@@ -45,20 +45,6 @@ unsigned crypt_cpusonline(void)
return r < 0 ? 1 : r;
}
const char *uint64_to_str(char *buffer, size_t size, const uint64_t *val)
{
int r = snprintf(buffer, size, "%" PRIu64, *val);
if (r < 0) {
log_dbg("Failed to convert integer to string.");
*buffer = '\0';
} else if ((size_t)r >= size) {
log_dbg("Not enough space to store '%" PRIu64 "' to a string buffer.", *val);
*buffer = '\0';
}
return buffer;
}
ssize_t read_buffer(int fd, void *buf, size_t count)
{
size_t read_size = 0;
......
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