You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
94 lines
3.4 KiB
94 lines
3.4 KiB
diff -rupN cryptsetup-2.0.3.old/lib/luks2/luks2_json_metadata.c cryptsetup-2.0.3/lib/luks2/luks2_json_metadata.c |
|
--- cryptsetup-2.0.3.old/lib/luks2/luks2_json_metadata.c 2019-03-27 16:14:49.790420791 +0100 |
|
+++ cryptsetup-2.0.3/lib/luks2/luks2_json_metadata.c 2019-03-27 16:23:50.499187212 +0100 |
|
@@ -363,12 +363,13 @@ static json_bool segment_has_digest(cons |
|
return FALSE; |
|
} |
|
|
|
-static json_bool validate_intervals(int length, const struct interval *ix, uint64_t *data_offset) |
|
+static json_bool validate_intervals(int length, const struct interval *ix, |
|
+ uint64_t metadata_size, uint64_t keyslots_area_end) |
|
{ |
|
int j, i = 0; |
|
|
|
while (i < length) { |
|
- if (ix[i].offset < 2 * LUKS2_HDR_16K_LEN) { |
|
+ if (ix[i].offset < 2 * metadata_size) { |
|
log_dbg("Illegal area offset: %" PRIu64 ".", ix[i].offset); |
|
return FALSE; |
|
} |
|
@@ -378,10 +379,9 @@ static json_bool validate_intervals(int |
|
return FALSE; |
|
} |
|
|
|
- /* first segment at offset 0 means we have detached header. Do not check then. */ |
|
- if (*data_offset && (ix[i].offset + ix[i].length) > *data_offset) { |
|
- log_dbg("Area [%" PRIu64 ", %" PRIu64 "] intersects with segment starting at offset: %" PRIu64, |
|
- ix[i].offset, ix[i].offset + ix[i].length, *data_offset); |
|
+ if ((ix[i].offset + ix[i].length) > keyslots_area_end) { |
|
+ log_dbg("Area [%" PRIu64 ", %" PRIu64 "] overflows binary keyslots area (ends at offset: %" PRIu64 ").", |
|
+ ix[i].offset, ix[i].offset + ix[i].length, keyslots_area_end); |
|
return FALSE; |
|
} |
|
|
|
@@ -596,12 +596,24 @@ static int hdr_validate_segments(json_ob |
|
return 0; |
|
} |
|
|
|
+static uint64_t LUKS2_metadata_size(json_object *jobj) |
|
+{ |
|
+ json_object *jobj1, *jobj2; |
|
+ uint64_t json_size; |
|
+ |
|
+ json_object_object_get_ex(jobj, "config", &jobj1); |
|
+ json_object_object_get_ex(jobj1, "json_size", &jobj2); |
|
+ json_str_to_uint64(jobj2, &json_size); |
|
+ |
|
+ return json_size + LUKS2_HDR_BIN_LEN; |
|
+} |
|
+ |
|
static int hdr_validate_areas(json_object *hdr_jobj) |
|
{ |
|
struct interval *intervals; |
|
json_object *jobj_keyslots, *jobj_offset, *jobj_length, *jobj_segments, *jobj_area; |
|
int length, ret, i = 0; |
|
- uint64_t first_offset, keyslots_size, keyslots_area_sum = 0; |
|
+ uint64_t keyslots_size, metadata_size, keyslots_area_sum = 0; |
|
|
|
if (!json_object_object_get_ex(hdr_jobj, "keyslots", &jobj_keyslots)) |
|
return 1; |
|
@@ -611,6 +623,7 @@ static int hdr_validate_areas(json_objec |
|
|
|
/* config is already validated */ |
|
keyslots_size = LUKS2_keyslots_size(hdr_jobj); |
|
+ metadata_size = LUKS2_metadata_size(hdr_jobj); |
|
|
|
length = json_object_object_length(jobj_keyslots); |
|
|
|
@@ -663,9 +676,7 @@ static int hdr_validate_areas(json_objec |
|
return 1; |
|
} |
|
|
|
- first_offset = get_first_data_offset(jobj_segments, NULL); |
|
- |
|
- ret = validate_intervals(length, intervals, &first_offset) ? 0 : 1; |
|
+ ret = validate_intervals(length, intervals, metadata_size, LUKS2_hdr_and_areas_size(hdr_jobj)) ? 0 : 1; |
|
|
|
free(intervals); |
|
|
|
@@ -918,14 +929,7 @@ uint64_t LUKS2_keyslots_size(json_object |
|
|
|
uint64_t LUKS2_hdr_and_areas_size(json_object *jobj) |
|
{ |
|
- json_object *jobj1, *jobj2; |
|
- uint64_t json_size; |
|
- |
|
- json_object_object_get_ex(jobj, "config", &jobj1); |
|
- json_object_object_get_ex(jobj1, "json_size", &jobj2); |
|
- json_str_to_uint64(jobj2, &json_size); |
|
- |
|
- return 2 * (json_size + LUKS2_HDR_BIN_LEN) + LUKS2_keyslots_size(jobj); |
|
+ return 2 * LUKS2_metadata_size(jobj) + LUKS2_keyslots_size(jobj); |
|
} |
|
|
|
int LUKS2_hdr_backup(struct crypt_device *cd, struct luks2_hdr *hdr,
|
|
|