Improved handling of cylinder alignment if the resulting image size

size is not divisible by 2048. Old behavior was to not align. New is
to pad up by a few blocks of 512 bytes.
This commit is contained in:
2015-05-10 09:34:45 +02:00
parent 5a3d84cbbb
commit c47167058a
5 changed files with 28 additions and 16 deletions

View File

@ -2481,6 +2481,7 @@ int ecma119_image_new(IsoImage *src, IsoWriteOpts *in_opts, Ecma119Image **img)
target->wthread_is_running = 0;
target->post_iso_part_pad = 0;
target->prep_part_size = 0;
target->efi_boot_part_size = 0;
target->efi_boot_part_filesrc = NULL;

View File

@ -798,6 +798,12 @@ struct ecma119_image
struct iso_mbr_partition_request *mbr_req[ISO_MBR_ENTRIES_MAX];
int mbr_req_count;
/* Number of bytes which have to be added after the cylinder aligned end
of the overall ISO partition because clinder size is not a multiple
of 2048
*/
int post_iso_part_pad;
uint32_t prep_part_size;
/* GPT description. To be composed during IsoImageWriter

View File

@ -590,7 +590,8 @@ int make_isolinux_mbr(uint32_t *img_blocks, Ecma119Image *t,
part_offset = 1;
}
hd_img_blocks = ((off_t) *img_blocks) * (off_t) 4;
hd_img_blocks = ((off_t) *img_blocks) * (off_t) 4 -
t->post_iso_part_pad / 512;
boot_lba = t->bootsrc[0]->sections[0].block;
head_count = t->partition_heads_per_cyl;

View File

@ -329,21 +329,24 @@ int make_grub_msdos_label(uint32_t img_blocks, int sph, int hpc,
/* @param flag bit0= zeroize partitions entries 2, 3, 4
bit0= UEFI protective MBR: start LBA = 1
bit1= UEFI protective MBR: start LBA = 1
*/
static
int iso_offset_partition_start(uint32_t img_blocks, uint32_t partition_offset,
int iso_offset_partition_start(uint32_t img_blocks, int post_part_pad,
uint32_t partition_offset,
int sph, int hpc, uint8_t *buf, int flag)
{
uint8_t *wpt;
uint32_t end_lba, end_sec, end_head, end_cyl;
uint32_t start_lba, start_sec, start_head, start_cyl;
uint64_t img_hd_blocks;
int i;
iso_compute_cyl_head_sec((uint64_t) partition_offset, hpc, sph,
&start_lba, &start_sec, &start_head, &start_cyl, 1);
iso_compute_cyl_head_sec((uint64_t) img_blocks, hpc, sph,
&end_lba, &end_sec, &end_head, &end_cyl, 0);
img_hd_blocks = ((uint64_t) img_blocks) * 4 - post_part_pad / 512;
iso_compute_cyl_head_sec(img_hd_blocks, hpc, sph,
&end_lba, &end_sec, &end_head, &end_cyl, 2);
if (flag & 2) {
start_lba = 1;
start_sec = 2;
@ -1863,10 +1866,10 @@ int iso_write_system_area(Ecma119Image *t, uint8_t *buf)
return ret;
} else if (t->opts->partition_offset == 0) {
/* Re-write partion entry 1 : start at 0, type Linux */
ret = write_mbr_partition_entry(1, 0x83,
(uint64_t) 0, (uint64_t) img_blocks,
blk = ((uint64_t) img_blocks) * 4 - t->post_iso_part_pad / 512;
ret = write_mbr_partition_entry(1, 0x83, (uint64_t) 0, blk,
t->partition_secs_per_head, t->partition_heads_per_cyl,
buf, 0);
buf, 2);
if (ret < 0)
return ret;
}
@ -1884,7 +1887,7 @@ int iso_write_system_area(Ecma119Image *t, uint8_t *buf)
} else {
mbrp1_blocks = img_blocks;
}
ret = iso_offset_partition_start(mbrp1_blocks,
ret = iso_offset_partition_start(mbrp1_blocks, t->post_iso_part_pad,
t->opts->partition_offset,
t->partition_secs_per_head,
t->partition_heads_per_cyl, buf,
@ -1936,7 +1939,7 @@ int iso_write_system_area(Ecma119Image *t, uint8_t *buf)
/* Choose *heads_per_cyl so that
- *heads_per_cyl * secs_per_head * 1024 >= imgsize / 512
- *heads_per_cyl * secs_per_head is divisible by 4
- it is as small as possible (to reduce aligment overhead)
- it is as small as possible (to reduce alignment overhead)
- it is <= 255
@return 1= success , 0= cannot achieve goals
*/
@ -2053,14 +2056,15 @@ int iso_align_isohybrid(Ecma119Image *t, int flag)
frac = imgsize - ((off_t) img_blocks) * (off_t) 2048;
if (frac == 0)
{ret = ISO_SUCCESS; goto ex;}
t->post_iso_part_pad = 0;
if (frac % 2048) {
t->post_iso_part_pad = 2048 - frac % 2048;
sprintf(msg,
"Cylinder size %d not divisible by 2048. Cannot align partition.",
(int) cylsize);
"Cylinder aligned image size is not divisible by 2048. Have to add %d bytes.",
t->post_iso_part_pad);
iso_msgs_submit(0, msg, 0, "WARNING", 0);
} else {
t->opts->tail_blocks += frac / 2048;
}
t->opts->tail_blocks += (frac + 2047) / 2048;
ret = ISO_SUCCESS;
ex:;
LIBISO_FREE_MEM(msg);