diff --git a/libisoburn/trunk/xorriso/xorriso.1 b/libisoburn/trunk/xorriso/xorriso.1 index c355ca30..d33939c5 100644 --- a/libisoburn/trunk/xorriso/xorriso.1 +++ b/libisoburn/trunk/xorriso/xorriso.1 @@ -9,7 +9,7 @@ .\" First parameter, NAME, should be all caps .\" Second parameter, SECTION, should be 1-8, maybe w/ subsection .\" other parameters are allowed: see man(7), man(1) -.TH XORRISO 1 "Apr 20, 2010" +.TH XORRISO 1 "Apr 26, 2010" .\" Please adjust this date whenever revising the manpage. .\" .\" Some roff macros, for reference: @@ -368,8 +368,8 @@ demands a file name length of up to 255 characters and paths of up to 1024 characters. Rock Ridge fulfills this demand. .PP An \fBEl Torito\fR -boot record connects a boot image, which is a binary program plus some -other files stored in the ISO image, with the bootstrapping facility of +boot record connects one or more boot images, which are binary program files +stored in the ISO image, with the bootstrapping facility of contemporary computers. The content of the boot image files is not in the scope of El Torito. .br @@ -2146,7 +2146,7 @@ For images which will never get to a CD it is safe to use -padding 0 . .B El Torito bootable ISO images: .PP Contrary to published specifications many BIOSes will load an El Torito -object from the first session on media and not from the last one, which +record from the first session on media and not from the last one, which gets mounted by default. This makes no problems with overwriteable media, because they appear to inadverted readers as one single session. .br @@ -2163,45 +2163,49 @@ can assume overwriteable media. .TP \fB\-boot_image\fR "any"|"isolinux"|"grub" .br - "discard"|"keep"|"patch"|"show_status"|bootspec + "discard"|"keep"|"patch"|"show_status"|bootspec|"next" .br -Define the handling of an eventual El Torito boot image object which has -been read from an existing ISO image or define how to make a prepared +Define the handling of an eventual set of El Torito boot images which +has been read from an existing ISO image or define how to make a prepared boot image file set bootable. Such file sets get produced by ISOLINUX or GRUB. .br Each -boot_image command has two arguments: type and setting. More than one --boot_image command may be used to define the handling. Sequence matters. +-boot_image command may be used to define the handling of one or more boot +images. Sequence matters. .br Types "isolinux" and "grub" care for known peculiarities. Type "any" makes -no assumptions about the origin of the boot image. +no assumptions about the origin of the boot images. .br El Torito boot images of any type can be newly inserted, or discarded, or patched, or kept unaltered. -The latter is only safe if the format of the boot image is -relocatable without content changes. +Whether to patch or to keep depends on whether +the boot images contain boot info tables. .br -Some boot images contain a boot info table, which needs to be patched when -the boot image gets newly introduced into the ISO image or if an existing -image gets relocated. This is automatically done if type "isolinux" or "grub" +A boot info table needs to be patched when the boot image gets newly +introduced into the ISO image or if an existing image gets relocated. +This is automatically done if type "isolinux" or "grub" is given, but not with "any". .br "show_status" will print what is known about the loaded image and its designated fate. .br -CAUTION: -This is an expert option. -xorriso cannot recognize the inner form of boot images. +"next" ends the definition of a boot image and starts a new one. +Any following -bootimage bootspecs will affect the new image. +The first "next" discards eventually loaded boot images and their +catalog. +.br +CAUTION: xorriso cannot recognize the inner form of boot images. So the user has already to know about the particular needs of the -boot image which is present on the input media. +boot images which are present on the input media. .br Most safe is the default: -boot_image "any" "discard". .br A bootspec is a word of the form name=value and is used to describe the -activation of a boot image by an El Torito record and eventually a MBR. -The names "dir" and "bin_path" lead to El Torito boot image activation. -Name "system_area" activates the given file as MBR. +parameters of a boot image by an El Torito record and eventually a MBR. +The names "dir", "bin_path", "efi_path" lead to El Torito bootable images. +Name "system_area" activates a given file as MBR. .br On all media types this is possible within the first session. In further sessions an existing boot image can get replaced by a new one, but depending @@ -2225,13 +2229,19 @@ which bundles these individual settings: .br -boot_image any boot_info_table=on .br -"bin_path=" depicts the binary program which is to be started by the BIOS at -boot time. +"bin_path=" depicts the boot image file, a binary program which is to be +started by the hardware boot facility (e.g. the BIOS) at boot time. +.br +"efi_path=" depicts a boot image file that is ready for EFI booting. +Its load_size is determined automatically, no boot info table gets +written, platform_id is 0xef. .br An El Torito boot catalog file gets inserted into the ISO image with address "cat_path=" at -commit time. It is subject to normal -overwrite and -reassure processing if there is already a file with the same name. +The catalog lists the boot images and is read by the boot facility to choose +one of the boot images. .br "load_size=" is a value which depends on the boot image. Default 2048 should be overridden only if a better value is known. @@ -2239,12 +2249,25 @@ be overridden only if a better value is known. "boot_info_table=on" may be used to apply patching to a boot image which is given by "any" "bin_path=". "boot_info_table=off" disables patching. .br -"discard" gives up an existing boot image. +"platform_id=" defines by two hex digits the Platform ID of the boot image. +"00" is 80x86 PC-BIOS, "01" is PowerPC, "02" is Mac, "ef" is EFI. .br -"keep" keeps or copies an existing boot image unaltered. +"id_string="text|56_hexdigits defines the ID string of the boot catalog +section where the boot image will be listed. If the value consists of 56 +characters [0-9A-Fa-f] then it is converted into 28 bytes, else the first +28 characters become the ID string. +The ID string of the first boot image becomes the overall catalog ID. +It is limited to 24 characters. Other id_strings become section IDs. .br -"patch" applies boot info table patching if an existing boot image gets copied -to a new location. +"sel_crit="hexdigits defines the Selection Criteria of the boot image. +Up to 20 bytes get read from the given characters [0-9A-Fa-f]. +They get attributed to the boot image entry in the catalog. +.br +"discard" gives up an existing boot catalog and its boot images. +.br +"keep" keeps or copies boot images unaltered and writes a new catalog. +.br +"patch" applies boot info table patching of existing boot images. .br "system_area="disk_path copies at most 32768 bytes from the given disk file to the very start of the ISO image. @@ -2260,8 +2283,9 @@ to the ISO image. 446 to 511 of the System Area. .br With type "isolinux" it shows a partition that begins at byte 0 and it causes -the boot image LBA to be written into the MBR. For the first session this -works only if also "system_area=" and "bin_path=" or "dir=" is given. +the LBA of the first boot image to be written into the MBR. For the first +session this works only if also "system_area=" and "bin_path=" or "dir=" +is given. .br With types "any" and "grub" it shows a single partiton which starts at byte 512 and ends where the ISO image ends. diff --git a/libisoburn/trunk/xorriso/xorriso.c b/libisoburn/trunk/xorriso/xorriso.c index 558b0425..d9296c6b 100644 --- a/libisoburn/trunk/xorriso/xorriso.c +++ b/libisoburn/trunk/xorriso/xorriso.c @@ -137,7 +137,7 @@ or #endif /* ! Xorriso_with_old_readlinE */ #endif /* Xorriso_with_readlinE */ -#define TSOB_FELD(typ,anz) (typ *) malloc((anz)*sizeof(typ)); +#define TSOB_FELD(typ,anz) (typ *) calloc(1, (anz)*sizeof(typ)); /* Diet facility: exclude help texts from binaries */ @@ -2040,6 +2040,41 @@ overflow:; } +int Hex_to_bin(char *hex, + int bin_size, int *bin_count, unsigned char *bin_data, int flag) +{ + int i, l, acc; + + l= strlen(hex); + if(l % 2 || l == 0) + return(-1); /* malformed */ + *bin_count= 0; + for(i= 0; i < l; i+= 2) { + if(hex[i] >= '0' && hex[i] <= '9') + acc= (hex[i] - '0') << 4; + else if(hex[i] >= 'A' && hex[i] <= 'F') + acc= (hex[i] - 'A' + 10) << 4; + else if(hex[i] >= 'a' && hex[i] <= 'f') + acc= (hex[i] - 'a' + 10) << 4; + else + return(-1); + if(hex[i + 1] >= '0' && hex[i + 1] <= '9') + acc|= (hex[i + 1] - '0'); + else if(hex[i + 1] >= 'A' && hex[i + 1] <= 'F') + acc|= (hex[i + 1] - 'A' + 10); + else if(hex[i + 1] >= 'a' && hex[i + 1] <= 'f') + acc|= (hex[i + 1] - 'a' + 10); + else + return(-1); + if(*bin_count >= bin_size) + return(0); /* overflow */ + bin_data[*bin_count]= acc; + (*bin_count)++; + } + return(1); +} + + #ifndef Xorriso_fileliste_externaL /* ??? ts A71006 : Is this compatible with mkisofs pathspecs ? @@ -2892,6 +2927,8 @@ int Findjob_destroy(struct FindjoB **o, int flag) return(0); if(m->test_tree != NULL) Exprnode_destroy(&(m->test_tree), 0); + if(m->start_path != NULL) + free(m->start_path); free((char *) *o); *o= NULL; return(1); @@ -4885,14 +4922,17 @@ int Xorriso_new(struct XorrisO ** xorriso,char *progname, int flag) m->do_stream_recording= 0; m->dvd_obs= 0; m->stdio_sync= 0; - m->boot_platform_id= 0x00; /* El Torito Boot Catalog Platform ID: 0 = 80x86 */ m->keep_boot_image= 0; + m->boot_image_cat_path[0]= 0; + m->boot_count= 0; + m->boot_platform_id= 0x00; /* El Torito Boot Catalog Platform ID: 0 = 80x86 */ m->patch_isolinux_image= 0; m->boot_image_bin_path[0]= 0; m->boot_image_bin_form[0]= 0; m->boot_image_emul= 0; - m->boot_image_cat_path[0]= 0; m->boot_image_load_size= 4 * 512; /* hearsay out of libisofs/demo/iso.c */ + memset(m->boot_id_string, 0, sizeof(m->boot_id_string)); + memset(m->boot_selection_crit, 0, sizeof(m->boot_selection_crit)); #ifdef Xorriso_with_isohybriD m->boot_image_isohybrid= 1; @@ -4900,7 +4940,12 @@ int Xorriso_new(struct XorrisO ** xorriso,char *progname, int flag) m->boot_image_isohybrid= 0; #endif + m->boot_efi_default= 0; + +#ifndef Xorriso_multi_booT m->boot_image_efi_path[0]= 0; +#endif + m->system_area_disk_path[0]= 0; m->system_area_options= 0; m->patch_system_area= 0; @@ -6745,10 +6790,10 @@ int Xorriso_status(struct XorrisO *xorriso, char *filter, FILE *fp, int flag) -options_from_file:${resume_state_file}_pos */ { - int is_default, no_defaults, i, ret, adr_mode, bin_path_in_use= 0, do_single; - int show_indev= 1, show_outdev= 1, show_dev= 0, patch_is_implicit= 0; - int part_table_implicit= 0, efi_path_in_use= 0; - char *line, sfe[5 * SfileadrL + 80], mode[80], *form, *treatment, *bin_form; + int is_default, no_defaults, i, ret, adr_mode, do_single; + int show_indev= 1, show_outdev= 1, show_dev= 0; + int part_table_implicit= 0; + char *line, sfe[5 * SfileadrL + 80], mode[80], *form, *treatment; char *in_pt, *out_pt, *nl_charset, *local_charset, *mode_pt; char *dev_filter= NULL; static char channel_prefixes[4][4]= {".","R","I","M"}; @@ -6756,6 +6801,11 @@ int Xorriso_status(struct XorrisO *xorriso, char *filter, FILE *fp, int flag) static int max_load_mode= 4; struct Xorriso_lsT *paths, *leafs, *s; +#ifndef Xorriso_multi_booT + char *bin_form; + int patch_is_implicit= 0, efi_path_in_use= 0, bin_path_in_use= 0; +#endif + no_defaults= flag&1; line= xorriso->result_line; @@ -6932,6 +6982,12 @@ int Xorriso_status(struct XorrisO *xorriso, char *filter, FILE *fp, int flag) if(!(is_default && no_defaults)) Xorriso_status_result(xorriso,filter,fp,flag&2); +#ifdef Xorriso_multi_booT + + Xorriso_boot_image_status(xorriso, filter, fp, flag & 3); + +#else /* Xorriso_multi_booT */ + is_default= (xorriso->keep_boot_image == 0 && xorriso->patch_isolinux_image == 0 && xorriso->boot_image_bin_path[0] == 0); @@ -6970,12 +7026,14 @@ bin_path:; treatment= sfe; bin_path_in_use= 1; } + } else if(xorriso->boot_image_efi_path[0]) { form= "grub"; strcpy(sfe, "efi_path="); Text_shellsafe(xorriso->boot_image_efi_path, sfe + strlen(sfe), 0); treatment= sfe; efi_path_in_use= 1; + } else if(xorriso->patch_isolinux_image) { treatment= "patch"; if(xorriso->patch_system_area & 1) @@ -7010,6 +7068,7 @@ bin_path:; if(!(is_default && no_defaults)) Xorriso_status_result(xorriso,filter,fp,flag&2); } + if(xorriso->boot_image_efi_path[0] && xorriso->boot_image_bin_path[0]) { strcpy(line,"-boot_image grub efi_path="); Text_shellsafe(xorriso->boot_image_efi_path, line + strlen(line), 0); @@ -7017,6 +7076,7 @@ bin_path:; Xorriso_status_result(xorriso,filter,fp,flag&2); efi_path_in_use= 1; } + if(xorriso->boot_image_cat_path[0] && (bin_path_in_use || efi_path_in_use)) { is_default= 0; sprintf(line,"-boot_image %s cat_path=%s\n", @@ -7024,6 +7084,9 @@ bin_path:; if(!(is_default && no_defaults)) Xorriso_status_result(xorriso,filter,fp,flag&2); } + +#endif /* Xorriso_multi_booT */ + is_default= (xorriso->system_area_disk_path[0] == 0); sprintf(line,"-boot_image %s system_area=%s\n", xorriso->system_area_disk_path[0] && (xorriso->system_area_options & 2) @@ -11176,6 +11239,28 @@ no_volunteer:; } +int Xorriso_genisofs_add_boot(struct XorrisO *xorriso, char *whom, + int *option_b, int *no_emul_boot, int flag) +{ + int ret; + + if(*option_b && !*no_emul_boot) { + xorriso->boot_image_bin_path[0]= 0; + sprintf(xorriso->info_text, + "-as %s: Option -b is supported only if option -no-emul-boot is given", + whom); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + return(0); + } + ret= Xorriso_attach_boot_image(xorriso, 0); + if(ret <= 0) + xorriso->boot_image_bin_path[0]= 0; + *option_b= 0; + *no_emul_boot= 1; + return(ret); +} + + int Xorriso_genisofs_help(struct XorrisO *xorriso, int flag) { static char helptext[][160]= { @@ -11262,6 +11347,7 @@ int Xorriso_genisofs(struct XorrisO *xorriso, char *whom, int do_print_size= 0, fd, idx, iso_level= 0, no_emul_boot= 0; int option_b= 0, was_failure= 0, fret, lower_r= 0, zero= 0; int *weight_list= NULL, weight_count= 0; + int *boot_opt_list= NULL, boot_opt_count= 0; char sfe[5*SfileadrL], adr[SfileadrL+8], ra_text[80], pathspec[2*SfileadrL]; char *ept, *add_pt, eff_path[SfileadrL], indev[SfileadrL+8], msc[80], *cpt; char *boot_path; @@ -11275,6 +11361,11 @@ int Xorriso_genisofs(struct XorrisO *xorriso, char *whom, Xorriso_no_malloc_memory(xorriso, NULL, 0); return(-1); } + boot_opt_list= TSOB_FELD(int, argc + 1); + if(boot_opt_list == NULL) { + Xorriso_no_malloc_memory(xorriso, (char **) &weight_list, 0); + return(-1); + } adr[0]= indev[0]= msc[0]= 0; for(i= 0; ifile_size_limit= 0; + +#ifndef Xorriso_multi_booT + } else if(strcmp(argv[i], "-no-emul-boot")==0) { no_emul_boot= 1; } else if(strcmp(argv[i], "-boot-info-table")==0) { @@ -11360,11 +11454,13 @@ int Xorriso_genisofs(struct XorrisO *xorriso, char *whom, Several boot images shall be kept in a list. One is the Default. They can have type BIOS or EFI. */ - if(strcmp(argv[i - 1], "--efi-boot") == 0) + if(strcmp(argv[i - 1], "--efi-boot") == 0) { boot_path= xorriso->boot_image_efi_path; - else { + xorriso->boot_efi_default= 1; + } else { boot_path= xorriso->boot_image_bin_path; xorriso->boot_platform_id= 0x00; + xorriso->boot_efi_default= 0; option_b= 1; } boot_path[0]= 0; @@ -11398,6 +11494,9 @@ int Xorriso_genisofs(struct XorrisO *xorriso, char *whom, ret= Xorriso_option_boot_image(xorriso, "isolinux", sfe, 0); if(ret <= 0) goto problem_handler_1; + +#endif /* ! Xorriso_multi_booT */ + } else if(strcmp(argv[i], "-input-charset")==0) { if(i+1>=argc) goto not_enough_args; @@ -11479,6 +11578,9 @@ problem_handler_1:; if(ret<=0) goto ex; } + +#ifndef Xorriso_multi_booT + if(option_b && !no_emul_boot) { xorriso->boot_image_bin_path[0]= 0; sprintf(xorriso->info_text, @@ -11487,6 +11589,9 @@ problem_handler_1:; Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); ret= 0; goto ex; } + +#endif /* ! Xorriso_multi_booT */ + if(was_other_option && xorriso->out_drive_handle==NULL) { ret= Xorriso_option_dev(xorriso, "-", 2|4); /* set outdev to stdout */ if(ret<=0) @@ -11652,6 +11757,33 @@ not_enough_args:; } else if(strcmp(argv[i], "-iso-level")==0) { i++; /* was already handled in first argument scan */; + +#ifdef Xorriso_multi_booT + + } else if(strcmp(argv[i], "-no-emul-boot")==0 || + strcmp(argv[i], "-boot-info-table")==0 || + strncmp(argv[i], "isolinux_mbr=", 13)==0 || + strncmp(argv[i], "isolinux_mbr=", 13)==0 || + strcmp(argv[i], "-eltorito-alt-boot")==0 || + strcmp(argv[i], "--protective-msdos-label")==0) { + boot_opt_list[boot_opt_count++]= i; + } else if(strcmp(argv[i], "-b") == 0 || + strcmp(argv[i], "-eltorito-boot") == 0 || + strcmp(argv[i], "--efi-boot") == 0 || + strcmp(argv[i], "-c") == 0 || + strcmp(argv[i], "-eltorito-catalog") == 0 || + strcmp(argv[i], "-boot-load-size") == 0 || + strcmp(argv[i], "--embedded-boot")==0 || + strcmp(argv[i], "-generic-boot")==0 || + strcmp(argv[i], "-G") == 0 || + strcmp(argv[i], "-isohybrid-mbr")==0) { + if(i+1>=argc) + goto not_enough_args; + boot_opt_list[boot_opt_count++]= i; + i++; + +#else /* Xorriso_multi_booT */ + } else if(strcmp(argv[i], "-no-emul-boot")==0) { /* was already handled in first argument scan */; } else if(strcmp(argv[i], "-b") == 0 || @@ -11676,17 +11808,21 @@ not_enough_args:; goto ex; if(strcmp(argv[i - 1], "-isohybrid-mbr")==0) xorriso->system_area_options= (xorriso->system_area_options & ~3) | 2; - } else if(strcmp(argv[i], "--protective-msdos-label")==0) { - xorriso->system_area_options= (xorriso->system_area_options & ~3) | 1; - } else if(strncmp(argv[i], "--modification-date=", 20)==0) { - ret= Xorriso_option_volume_date(xorriso, "uuid", argv[i] + 20, 0); - if(ret <= 0) - goto problem_handler_1; } else if(strcmp(argv[i], "-boot-load-size") == 0) { i++; /* was already handled in first argument scan */; } else if(strcmp(argv[i], "-boot-info-table")==0) { ; + } else if(strcmp(argv[i], "--protective-msdos-label")==0) { + xorriso->system_area_options= (xorriso->system_area_options & ~3) | 1; + +#endif /* ! Xorriso_multi_booT */ + + } else if(strncmp(argv[i], "--modification-date=", 20)==0) { + ret= Xorriso_option_volume_date(xorriso, "uuid", argv[i] + 20, 0); + if(ret <= 0) + goto problem_handler_1; + } else if(strcmp(argv[i], "-input-charset")==0) { i++; /* was already handled in first argument scan */; @@ -11778,10 +11914,118 @@ problem_handler_2:; sort_weight_args[0]= argv[i + 2]; sort_weight_args[3]= argv[i + 1]; ret= Xorriso_option_find(xorriso, 4, sort_weight_args, &zero, 2); - if(ret<=0) + if(ret > 0) + continue; + /* Problem handler */ + was_failure= 1; + fret= Xorriso_eval_problem_status(xorriso, ret, 1|2); + if(fret>=0) + continue; + goto ex; + } + +#ifdef Xorriso_multi_booT + + /* After all pathspecs are added: perform boot related options */ + for(j= 0; j < boot_opt_count; j++) { + i= boot_opt_list[j]; + if(strcmp(argv[i], "-no-emul-boot")==0) { + no_emul_boot= 1; + } else if(strcmp(argv[i], "-boot-info-table")==0) { + xorriso->patch_isolinux_image= 1; + } else if(strcmp(argv[i], "-b") == 0 || + strcmp(argv[i], "-eltorito-boot") == 0 || + strcmp(argv[i], "--efi-boot") == 0) { + i++; + if(strcmp(argv[i - 1], "--efi-boot") == 0) { + if(xorriso->boot_image_bin_path[0]) { + ret= Xorriso_genisofs_add_boot(xorriso, whom, + &option_b, &no_emul_boot, 0); + if(ret <= 0) + goto problem_handler_boot; + } + boot_path= xorriso->boot_image_bin_path; + xorriso->boot_efi_default= 1; + } else { + boot_path= xorriso->boot_image_bin_path; + xorriso->boot_platform_id= 0x00; + xorriso->boot_efi_default= 0; + option_b= 1; + } + boot_path[0]= 0; + if(argv[i][0] != '/') + strcat(boot_path, "/"); + ret= Sfile_str(boot_path + strlen(boot_path), argv[i], 0); + if(ret <= 0) + goto ex; + if(xorriso->boot_efi_default && xorriso->boot_image_bin_path[0]) { + option_b= 0; + ret= Xorriso_genisofs_add_boot(xorriso, whom, + &option_b, &no_emul_boot, 0); + if(ret <= 0) + goto problem_handler_boot; + } + xorriso->keep_boot_image= 0; + } else if(strcmp(argv[i], "-c") == 0 || + strcmp(argv[i], "-eltorito-catalog") == 0) { + if(i+1>=argc) + goto not_enough_args; + i++; + xorriso->boot_image_cat_path[0]= 0; + if(argv[i][0] != '/') + strcat(xorriso->boot_image_cat_path, "/"); + ret= Sfile_str(xorriso->boot_image_cat_path + + strlen(xorriso->boot_image_cat_path), argv[i], 0); + if(ret <= 0) + goto ex; + } else if(strcmp(argv[i], "-boot-load-size") == 0) { + if(i+1>=argc) + goto not_enough_args; + i++; + sscanf(argv[i], "%d", &ret); + xorriso->boot_image_load_size= ret * 512; + } else if(strncmp(argv[i], "isolinux_mbr=", 13)==0) { + sprintf(sfe, "isohybrid=%s", argv[i] + 13); + ret= Xorriso_option_boot_image(xorriso, "isolinux", sfe, 0); + if(ret <= 0) + goto problem_handler_boot; + } else if(strcmp(argv[i], "-eltorito-alt-boot")==0) { + ret= Xorriso_genisofs_add_boot(xorriso, whom, + &option_b, &no_emul_boot, 0); + if(ret <= 0) + goto problem_handler_boot; + } else if(strcmp(argv[i], "--embedded-boot")==0 || + strcmp(argv[i], "-generic-boot")==0 || + strcmp(argv[i], "-G") == 0 || + strcmp(argv[i], "-isohybrid-mbr")==0) { + if(i+1>=argc) + goto not_enough_args; + i++; + ret= Xorriso_set_system_area_path(xorriso, argv[i], 0); + if(ret <= 0) + goto problem_handler_boot; + if(strcmp(argv[i - 1], "-isohybrid-mbr")==0) + xorriso->system_area_options= (xorriso->system_area_options & ~3) | 2; + } else if(strcmp(argv[i], "--protective-msdos-label")==0) { + xorriso->system_area_options= (xorriso->system_area_options & ~3) | 1; + } + continue; /* regular bottom of loop */ +problem_handler_boot:; + /* Problem handler */ + was_failure= 1; + fret= Xorriso_eval_problem_status(xorriso, ret, 1|2); + if(fret>=0) + continue; + goto ex; + } + if(xorriso->boot_image_bin_path[0]) { + ret= Xorriso_genisofs_add_boot(xorriso, whom, &option_b, &no_emul_boot, 0); + if(ret <= 0) goto ex; } +#endif /* Xorriso_multi_booT */ + ret= !was_failure; ex:; if(was_path && !do_print_size) @@ -11791,6 +12035,8 @@ ex:; Xorriso_option_rollback(xorriso, 0); if(weight_list != NULL) free(weight_list); + if(boot_opt_list != NULL) + free(boot_opt_list); return(ret); } @@ -13816,7 +14062,7 @@ unusable_size:; int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, char *treatment, int flag) { - int was_ok= 1, ret, isolinux_grub= 0; + int was_ok= 1, ret, isolinux_grub= 0, count; unsigned int u; char *formpt, *treatpt; double num; @@ -13831,12 +14077,21 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, if(strcmp(formpt, "isolinux")==0 || strcmp(formpt, "grub") == 0) isolinux_grub= 1; if(strcmp(treatpt, "keep")==0) { + if(xorriso->boot_count > 0) { +cannot_keep_or_patch:; + sprintf(xorriso->info_text, + "Loaded boot image has already been replaced. Cannot keep or patch it."); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + return(0); + } xorriso->keep_boot_image= 1; xorriso->patch_isolinux_image= !!isolinux_grub; xorriso->boot_image_bin_path[0]= 0; xorriso->patch_system_area= 0; } else if(strcmp(treatpt, "patch")==0) { + if(xorriso->boot_count > 0) + goto cannot_keep_or_patch; xorriso->keep_boot_image= 0; xorriso->patch_isolinux_image= 1; xorriso->boot_image_bin_path[0]= 0; @@ -13852,6 +14107,16 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, xorriso->patch_isolinux_image= 0; xorriso->boot_image_bin_path[0]= 0; xorriso->patch_system_area= 0; + if(xorriso->boot_count > 0) { + ret= Xorriso_attach_boot_image(xorriso, 2); /* dispose boot images */ + if(ret <= 0) + return(ret); + } + + } else if(strcmp(treatpt, "next") == 0) { + ret= Xorriso_attach_boot_image(xorriso, 0); + if(ret <= 0) + return(ret); } else if(strcmp(treatpt, "show_status")==0) { sprintf(xorriso->result_line, "------------------------------------\n"); @@ -13871,6 +14136,14 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, sprintf(xorriso->result_line, "------------------------------------\n"); Xorriso_result(xorriso, 0); + } else if(strcmp(treatpt, "cat_path=") == 0) { + xorriso->boot_image_cat_path[0] = 0; + } else if(strncmp(treatpt, "cat_path=", 9) == 0) { + ret= Xorriso_normalize_img_path(xorriso, xorriso->wdi, treatpt + 9, + xorriso->boot_image_cat_path, 2); + if(ret <= 0) + return(ret); + } else if(strncmp(treatpt, "dir=", 4) == 0) { if(strcmp(formpt, "isolinux")==0) { /* ISOLINUX */ @@ -13916,6 +14189,7 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, } else if(strcmp(treatpt, "bin_path=") == 0) { xorriso->boot_image_bin_path[0] = 0; + xorriso->boot_efi_default= 0; } else if(strncmp(treatpt, "bin_path=", 9) == 0) { ret= Xorriso_normalize_img_path(xorriso, xorriso->wdi, treatpt + 9, xorriso->boot_image_bin_path, 2); @@ -13929,15 +14203,31 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, strcpy(xorriso->boot_image_bin_form, formpt); } else strcpy(xorriso->boot_image_bin_form, "any"); + xorriso->boot_efi_default= 0; + +#ifdef Xorriso_multi_booT + + } else if(strcmp(treatpt, "efi_path=") == 0) { + xorriso->boot_image_bin_path[0] = 0; + xorriso->boot_efi_default= 0; + } else if(strncmp(treatpt, "efi_path=", 9) == 0) { + ret= Xorriso_normalize_img_path(xorriso, xorriso->wdi, treatpt + 9, + xorriso->boot_image_bin_path, 2); + +#else } else if(strcmp(treatpt, "efi_path=") == 0) { xorriso->boot_image_efi_path[0] = 0; } else if(strncmp(treatpt, "efi_path=", 9) == 0) { ret= Xorriso_normalize_img_path(xorriso, xorriso->wdi, treatpt + 9, xorriso->boot_image_efi_path, 2); + +#endif /* ! Xorriso_multi_booT */ + if(ret <= 0) return(ret); xorriso->keep_boot_image= 0; + xorriso->boot_efi_default= 1; } else if(strncmp(treatpt, "boot_info_table=", 16)==0) { if(strcmp(treatpt + 16, "off") == 0) @@ -13947,14 +14237,6 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, else was_ok= 0; - } else if(strcmp(treatpt, "cat_path=") == 0) { - xorriso->boot_image_cat_path[0] = 0; - } else if(strncmp(treatpt, "cat_path=", 9) == 0) { - ret= Xorriso_normalize_img_path(xorriso, xorriso->wdi, treatpt + 9, - xorriso->boot_image_cat_path, 2); - if(ret <= 0) - return(ret); - } else if(strncmp(treatpt, "load_size=", 10) == 0) { num= Scanf_io_size(treatpt + 10, 0); if(num < 512 && isolinux_grub) { @@ -13966,6 +14248,27 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, } xorriso->boot_image_load_size= num; + } else if(strncmp(treatpt, "id_string=", 10) == 0) { + memset(xorriso->boot_id_string, 0, 29); + if(strlen(treatpt + 10) == 56) { + ret= Hex_to_bin(treatpt + 10, 28, &count, xorriso->boot_id_string, 0); + } else + ret= 0; + if(ret <= 0) + strncpy((char *) xorriso->boot_id_string, treatpt + 10, 28); + + } else if(strncmp(treatpt, "sel_crit=", 9) == 0) { + memset(xorriso->boot_selection_crit, 0, 21); + count= 0; + ret= Hex_to_bin(treatpt + 9, 20, &count, xorriso->boot_selection_crit, 0); + if(ret <= 0) { + sprintf(xorriso->info_text, + "-boot_image %s sel_crit= : Wrong form. Need even number of hex digits.", + formpt); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + return(0); + } + } else if(strncmp(treatpt, "system_area=", 12) == 0) { ret= Xorriso_set_system_area_path(xorriso, treatpt + 12, 0); if(ret <= 0) @@ -14043,11 +14346,6 @@ int Xorriso_option_boot_image(struct XorrisO *xorriso, char *form, } else was_ok= 0; - /* >>> BOOT : check whether directories and/or files exist: - bin_path , dirname(cat_path), - isolinux.cfg in / , /isolinux , or /boot/isolinux - */ - if(!was_ok) { sprintf(xorriso->info_text, "Unrecognized options with -boot_image: %s %s", form, treatment); diff --git a/libisoburn/trunk/xorriso/xorriso.info b/libisoburn/trunk/xorriso/xorriso.info index b0ea897e..b9659228 100644 --- a/libisoburn/trunk/xorriso/xorriso.info +++ b/libisoburn/trunk/xorriso/xorriso.info @@ -329,8 +329,8 @@ characters of filename length. It is the X/Open System Interface standard XSI which demands a file name length of up to 255 characters and paths of up to 1024 characters. Rock Ridge fulfills this demand. - An *El Torito* boot record connects a boot image, which is a binary -program plus some other files stored in the ISO image, with the + An *El Torito* boot record connects one or more boot images, which +are binary program files stored in the ISO image, with the bootstrapping facility of contemporary computers. The content of the boot image files is not in the scope of El Torito. Most bootable GNU/Linux CDs are equipped with ISOLINUX or GRUB boot @@ -1927,7 +1927,7 @@ File: xorriso.info, Node: Bootable, Next: Charset, Prev: SetWrite, Up: Optio ================================== Contrary to published specifications many BIOSes will load an El Torito -object from the first session on media and not from the last one, which +record from the first session on media and not from the last one, which gets mounted by default. This makes no problems with overwriteable media, because they appear to inadverted readers as one single session. But with multi-session media CD-R[W], DVD-R[W], DVD+R, it implies that @@ -1940,40 +1940,41 @@ But one should not rely on the capability to influence the bootability of the existing sessions, unless one can assume overwriteable media. -boot_image "any"|"isolinux"|"grub" - "discard"|"keep"|"patch"|"show_status"|bootspec + "discard"|"keep"|"patch"|"show_status"|bootspec|"next" - Define the handling of an eventual El Torito boot image object + Define the handling of an eventual set of El Torito boot images which has been read from an existing ISO image or define how to make a prepared boot image file set bootable. Such file sets get produced by ISOLINUX or GRUB. Each -boot_image command has two arguments: type and setting. More - than one -boot_image command may be used to define the handling. - Sequence matters. + than one -boot_image command may be used to define the handling of + one or more boot images. Sequence matters. Types "isolinux" and "grub" care for known peculiarities. Type - "any" makes no assumptions about the origin of the boot image. + "any" makes no assumptions about the origin of the boot images. El Torito boot images of any type can be newly inserted, or - discarded, or patched, or kept unaltered. The latter is only safe - if the format of the boot image is relocatable without content - changes. - Some boot images contain a boot info table, which needs to be - patched when the boot image gets newly introduced into the ISO - image or if an existing image gets relocated. This is - automatically done if type "isolinux" or "grub" is given, but not - with "any". + discarded, or patched, or kept unaltered. Whether to patch or to + keep depends on whether the boot images contain boot info tables. + A boot info table needs to be patched when the boot image gets + newly introduced into the ISO image or if an existing image gets + relocated. This is automatically done if type "isolinux" or "grub" + is given, but not with "any". "show_status" will print what is known about the loaded image and its designated fate. - CAUTION: This is an expert option. xorriso cannot recognize the - inner form of boot images. So the user has already to know about - the particular needs of the boot image which is present on the - input media. + "next" ends the definition of a boot image and starts a new one. + Any following -bootimage bootspecs will affect the new image. The + first "next" discards eventually loaded boot images and their + catalog. + CAUTION: xorriso cannot recognize the inner form of boot images. + So the user has already to know about the particular needs of the + boot images which are present on the input media. Most safe is the default: -boot_image "any" "discard". A bootspec is a word of the form name=value and is used to - describe the activation of a boot image by an El Torito record and - eventually a MBR. The names "dir" and "bin_path" lead to El - Torito boot image activation. Name "system_area" activates the - given file as MBR. + describe the parameters of a boot image by an El Torito record and + eventually a MBR. The names "dir", "bin_path", "efi_path" lead to + El Torito bootable images. Name "system_area" activates a given + file as MBR. On all media types this is possible within the first session. In further sessions an existing boot image can get replaced by a new one, but depending on the media type this may have few effect at @@ -1990,21 +1991,39 @@ of the existing sessions, unless one can assume overwriteable media. -boot_image isolinux cat_path=/boot/isolinux/boot.cat -boot_image isolinux load_size=2048 -boot_image any boot_info_table=on - "bin_path=" depicts the binary program which is to be started by - the BIOS at boot time. + "bin_path=" depicts the boot image file, a binary program which is + to be started by the hardware boot facility (e.g. the BIOS) at + boot time. + "efi_path=" depicts a boot image file that is ready for EFI + booting. Its load_size is determined automatically, no boot info + table gets written, platform_id is 0xef. An El Torito boot catalog file gets inserted into the ISO image with address "cat_path=" at -commit time. It is subject to normal -overwrite and -reassure processing if there is already a file - with the same name. + with the same name. The catalog lists the boot images and is read + by the boot facility to choose one of the boot images. "load_size=" is a value which depends on the boot image. Default 2048 should be overridden only if a better value is known. "boot_info_table=on" may be used to apply patching to a boot image which is given by "any" "bin_path=". "boot_info_table=off" disables patching. - "discard" gives up an existing boot image. - "keep" keeps or copies an existing boot image unaltered. - "patch" applies boot info table patching if an existing boot image - gets copied to a new location. + "platform_id=" defines by two hex digits the Platform ID of the + boot image. "00" is 80x86 PC-BIOS, "01" is PowerPC, "02" is Mac, + "ef" is EFI. + "id_string="text|56_hexdigits defines the ID string of the boot + catalog section where the boot image will be listed. If the value + consists of 56 characters [0-9A-Fa-f] then it is converted into 28 + bytes, else the first 28 characters become the ID string. The ID + string of the first boot image becomes the overall catalog ID. It + is limited to 24 characters. Other id_strings become section IDs. + "sel_crit="hexdigits defines the Selection Criteria of the boot + image. Up to 20 bytes get read from the given characters + [0-9A-Fa-f]. They get attributed to the boot image entry in the + catalog. + "discard" gives up an existing boot catalog and its boot images. + "keep" keeps or copies boot images unaltered and writes a new + catalog. + "patch" applies boot info table patching of existing boot images. "system_area="disk_path copies at most 32768 bytes from the given disk file to the very start of the ISO image. This System Area is reserved for system dependent boot software, e.g. an MBR which can @@ -2015,9 +2034,9 @@ of the existing sessions, unless one can assume overwriteable media. "partition_table=on" causes a simple partition table to be written into bytes 446 to 511 of the System Area. With type "isolinux" it shows a partition that begins at byte 0 - and it causes the boot image LBA to be written into the MBR. For - the first session this works only if also "system_area=" and - "bin_path=" or "dir=" is given. + and it causes the LBA of the first boot image to be written into + the MBR. For the first session this works only if also + "system_area=" and "bin_path=" or "dir=" is given. With types "any" and "grub" it shows a single partiton which starts at byte 512 and ends where the ISO image ends. This works with or without system_area= or boot image. @@ -3902,7 +3921,7 @@ File: xorriso.info, Node: ConceptIdx, Prev: CommandIdx, Up: Top * iso_rr_path, _definition: Insert. (line 7) * List delimiter, _definiton: Processing. (line 8) * MBR, _definiton: Extras. (line 26) -* MBR, set, -boot_image system_area=: Bootable. (line 85) +* MBR, set, -boot_image system_area=: Bootable. (line 104) * MD5, control handling, -md5: Loading. (line 141) * Media, erase, -blank: Writing. (line 45) * Media, format, -format: Writing. (line 69) @@ -3932,7 +3951,7 @@ File: xorriso.info, Node: ConceptIdx, Prev: CommandIdx, Up: Top * Ownership, global in ISO image, -uid: SetWrite. (line 125) * Ownership, in ISO image, -chown: Manip. (line 42) * Ownership, in ISO image, -chown_r: Manip. (line 47) -* Partition table, _definiton: Bootable. (line 92) +* Partition table, _definiton: Bootable. (line 111) * Pathspec, _definition: SetInsert. (line 120) * Pattern expansion, _definition: Processing. (line 22) * Pattern expansion, for disk paths, -disk_pattern: Insert. (line 31) @@ -3983,7 +4002,7 @@ File: xorriso.info, Node: ConceptIdx, Prev: CommandIdx, Up: Top * Session, mount command line, -mount_cmd: Inquiry. (line 31) * Session, mount parameters, -mount_opts: Inquiry. (line 47) * Session, select as input, -load: Loading. (line 11) -* System area, _definiton: Bootable. (line 85) +* System area, _definiton: Bootable. (line 104) * Table-of-content, search sessions, -rom_toc_scan: Loading. (line 189) * Table-of-content, show, -toc: Inquiry. (line 18) * Timestamps, set in ISO image, -alter_date: Manip. (line 146) @@ -4031,50 +4050,50 @@ Node: Media6089 Node: Methods8519 Node: Drives11066 Node: Extras14332 -Node: Processing17736 -Node: Dialog21232 -Node: Options22889 -Node: AqDrive24457 -Node: Loading27363 -Node: Insert39798 -Node: SetInsert48155 -Node: Manip56722 -Node: CmdFind64598 -Node: Filter73943 -Node: Writing78292 -Node: SetWrite84581 -Node: Bootable94713 -Node: Charset100824 -Node: Exception103578 -Node: DialogCtl108093 -Node: Inquiry110438 -Node: Navigate114578 -Node: Verify121932 -Node: Restore130352 -Node: Emulation137008 -Node: Scripting143695 -Node: Frontend149257 -Node: Examples150458 -Node: ExDevices151627 -Node: ExCreate152109 -Node: ExDialog153383 -Node: ExGrowing154645 -Node: ExModifying155447 -Node: ExBootable155948 -Node: ExCharset156495 -Node: ExPseudo157323 -Node: ExCdrecord158217 -Node: ExMkisofs158532 -Node: ExGrowisofs159535 -Node: ExException160659 -Node: ExTime161113 -Node: ExIncBackup161572 -Node: ExRestore165044 -Node: ExRecovery166013 -Node: Files166579 -Node: Seealso167617 -Node: Legal168141 -Node: CommandIdx169063 -Node: ConceptIdx182364 +Node: Processing17730 +Node: Dialog21226 +Node: Options22883 +Node: AqDrive24451 +Node: Loading27357 +Node: Insert39792 +Node: SetInsert48149 +Node: Manip56716 +Node: CmdFind64592 +Node: Filter73937 +Node: Writing78286 +Node: SetWrite84575 +Node: Bootable94707 +Node: Charset102163 +Node: Exception104917 +Node: DialogCtl109432 +Node: Inquiry111777 +Node: Navigate115917 +Node: Verify123271 +Node: Restore131691 +Node: Emulation138347 +Node: Scripting145034 +Node: Frontend150596 +Node: Examples151797 +Node: ExDevices152966 +Node: ExCreate153448 +Node: ExDialog154722 +Node: ExGrowing155984 +Node: ExModifying156786 +Node: ExBootable157287 +Node: ExCharset157834 +Node: ExPseudo158662 +Node: ExCdrecord159556 +Node: ExMkisofs159871 +Node: ExGrowisofs160874 +Node: ExException161998 +Node: ExTime162452 +Node: ExIncBackup162911 +Node: ExRestore166383 +Node: ExRecovery167352 +Node: Files167918 +Node: Seealso168956 +Node: Legal169480 +Node: CommandIdx170402 +Node: ConceptIdx183703  End Tag Table diff --git a/libisoburn/trunk/xorriso/xorriso.texi b/libisoburn/trunk/xorriso/xorriso.texi index 51d66c95..6ff49759 100644 --- a/libisoburn/trunk/xorriso/xorriso.texi +++ b/libisoburn/trunk/xorriso/xorriso.texi @@ -44,7 +44,7 @@ @c man .\" First parameter, NAME, should be all caps @c man .\" Second parameter, SECTION, should be 1-8, maybe w/ subsection @c man .\" other parameters are allowed: see man(7), man(1) -@c man .TH XORRISO 1 "Apr 20, 2010" +@c man .TH XORRISO 1 "Apr 26, 2010" @c man .\" Please adjust this date whenever revising the manpage. @c man .\" @c man .\" Some roff macros, for reference: @@ -496,8 +496,8 @@ characters. Rock Ridge fulfills this demand. @sp 1 @cindex El Torito, _definiton An @strong{El Torito} -boot record connects a boot image, which is a binary program plus some -other files stored in the ISO image, with the bootstrapping facility of +boot record connects one or more boot images, which are binary program files +stored in the ISO image, with the bootstrapping facility of contemporary computers. The content of the boot image files is not in the scope of El Torito. @* @@ -2588,7 +2588,7 @@ For images which will never get to a CD it is safe to use -padding 0 . @section El Torito bootable ISO images @c man .PP Contrary to published specifications many BIOSes will load an El Torito -object from the first session on media and not from the last one, which +record from the first session on media and not from the last one, which gets mounted by default. This makes no problems with overwriteable media, because they appear to inadverted readers as one single session. @* @@ -2610,48 +2610,52 @@ can assume overwriteable media. @cindex Write, bootability, -boot_image @cindex Bootability, control, -boot_image @* - "discard"|"keep"|"patch"|"show_status"|bootspec + "discard"|"keep"|"patch"|"show_status"|bootspec|"next" @* @sp 1 -Define the handling of an eventual El Torito boot image object which has -been read from an existing ISO image or define how to make a prepared +Define the handling of an eventual set of El Torito boot images which +has been read from an existing ISO image or define how to make a prepared boot image file set bootable. Such file sets get produced by ISOLINUX or GRUB. @* Each -boot_image command has two arguments: type and setting. More than one --boot_image command may be used to define the handling. Sequence matters. +-boot_image command may be used to define the handling of one or more boot +images. Sequence matters. @* Types "isolinux" and "grub" care for known peculiarities. Type "any" makes -no assumptions about the origin of the boot image. +no assumptions about the origin of the boot images. @* @sp 1 El Torito boot images of any type can be newly inserted, or discarded, or patched, or kept unaltered. -The latter is only safe if the format of the boot image is -relocatable without content changes. +Whether to patch or to keep depends on whether +the boot images contain boot info tables. @* -Some boot images contain a boot info table, which needs to be patched when -the boot image gets newly introduced into the ISO image or if an existing -image gets relocated. This is automatically done if type "isolinux" or "grub" +A boot info table needs to be patched when the boot image gets newly +introduced into the ISO image or if an existing image gets relocated. +This is automatically done if type "isolinux" or "grub" is given, but not with "any". @* "show_status" will print what is known about the loaded image and its designated fate. @* -CAUTION: -This is an expert option. -xorriso cannot recognize the inner form of boot images. +"next" ends the definition of a boot image and starts a new one. +Any following -bootimage bootspecs will affect the new image. +The first "next" discards eventually loaded boot images and their +catalog. +@* +CAUTION: xorriso cannot recognize the inner form of boot images. So the user has already to know about the particular needs of the -boot image which is present on the input media. +boot images which are present on the input media. @* Most safe is the default: -boot_image "any" "discard". @* @sp 1 A bootspec is a word of the form name=value and is used to describe the -activation of a boot image by an El Torito record and eventually a MBR. -The names "dir" and "bin_path" lead to El Torito boot image activation. -Name "system_area" activates the given file as MBR. +parameters of a boot image by an El Torito record and eventually a MBR. +The names "dir", "bin_path", "efi_path" lead to El Torito bootable images. +Name "system_area" activates a given file as MBR. @* On all media types this is possible within the first session. In further sessions an existing boot image can get replaced by a new one, but depending @@ -2675,13 +2679,19 @@ which bundles these individual settings: @* -boot_image any boot_info_table=on @* -"bin_path=" depicts the binary program which is to be started by the BIOS at -boot time. +"bin_path=" depicts the boot image file, a binary program which is to be +started by the hardware boot facility (e.g. the BIOS) at boot time. +@* +"efi_path=" depicts a boot image file that is ready for EFI booting. +Its load_size is determined automatically, no boot info table gets +written, platform_id is 0xef. @* An El Torito boot catalog file gets inserted into the ISO image with address "cat_path=" at -commit time. It is subject to normal -overwrite and -reassure processing if there is already a file with the same name. +The catalog lists the boot images and is read by the boot facility to choose +one of the boot images. @* "load_size=" is a value which depends on the boot image. Default 2048 should be overridden only if a better value is known. @@ -2689,12 +2699,25 @@ be overridden only if a better value is known. "boot_info_table=on" may be used to apply patching to a boot image which is given by "any" "bin_path=". "boot_info_table=off" disables patching. @* -"discard" gives up an existing boot image. +"platform_id=" defines by two hex digits the Platform ID of the boot image. +"00" is 80x86 PC-BIOS, "01" is PowerPC, "02" is Mac, "ef" is EFI. @* -"keep" keeps or copies an existing boot image unaltered. +"id_string="text|56_hexdigits defines the ID string of the boot catalog +section where the boot image will be listed. If the value consists of 56 +characters [0-9A-Fa-f] then it is converted into 28 bytes, else the first +28 characters become the ID string. +The ID string of the first boot image becomes the overall catalog ID. +It is limited to 24 characters. Other id_strings become section IDs. @* -"patch" applies boot info table patching if an existing boot image gets copied -to a new location. +"sel_crit="hexdigits defines the Selection Criteria of the boot image. +Up to 20 bytes get read from the given characters [0-9A-Fa-f]. +They get attributed to the boot image entry in the catalog. +@* +"discard" gives up an existing boot catalog and its boot images. +@* +"keep" keeps or copies boot images unaltered and writes a new catalog. +@* +"patch" applies boot info table patching to existing boot images. @* @cindex System area, _definiton @cindex MBR, set, -boot_image system_area= @@ -2713,8 +2736,9 @@ to the ISO image. 446 to 511 of the System Area. @* With type "isolinux" it shows a partition that begins at byte 0 and it causes -the boot image LBA to be written into the MBR. For the first session this -works only if also "system_area=" and "bin_path=" or "dir=" is given. +the LBA of the first boot image to be written into the MBR. For the first +session this works only if also "system_area=" and "bin_path=" or "dir=" +is given. @* With types "any" and "grub" it shows a single partiton which starts at byte 512 and ends where the ISO image ends. diff --git a/libisoburn/trunk/xorriso/xorriso_private.h b/libisoburn/trunk/xorriso/xorriso_private.h index e0dcaf68..f0701868 100644 --- a/libisoburn/trunk/xorriso/xorriso_private.h +++ b/libisoburn/trunk/xorriso/xorriso_private.h @@ -18,6 +18,11 @@ #ifndef Xorriso_private_includeD #define Xorriso_private_includeD yes + +/* >>> transition to new boot image management */ +#define Xorriso_multi_booT 1 + + /** The source code release timestamp */ #include "xorriso_timestamp.h" #ifndef Xorriso_timestamP @@ -258,19 +263,33 @@ struct XorrisO { /* the global context of xorriso */ int dvd_obs; /* DVD write chunk size: 0, 32k or 64k */ int stdio_sync; /* stdio fsync interval: -1, 0, >=32 */ - int boot_platform_id; int keep_boot_image; - int patch_isolinux_image; + char boot_image_cat_path[SfileadrL]; + int boot_count; /* number of already attached boot images */ + char boot_image_bin_path[SfileadrL]; char boot_image_bin_form[16]; + int boot_platform_id; + int patch_isolinux_image; int boot_image_emul; /* 0=no emulation (1=emulation as hard disk) (2=emulation as floppy) */ - char boot_image_cat_path[SfileadrL]; off_t boot_image_load_size; - int boot_image_isohybrid; /* 0=off , 1=auto , 2=on , 3=force */ + unsigned char boot_id_string[29]; + unsigned char boot_selection_crit[21]; + + int boot_image_isohybrid; /* 0=off , deprecated: 1=auto , 2=on , 3=force */ + + int boot_efi_default; /* 0= no effect , + 1= appy --efi-boot parameters when attaching to img */ + +#ifndef Xorriso_multi_booT + /* <<< BOOT replace by attaching previous boot image to IsoImage by + -boot_image any next */ char boot_image_efi_path[SfileadrL]; +#endif /* ! Xorriso_multi_booT */ + char system_area_disk_path[SfileadrL]; int system_area_options; /* bit0= "GRUB protective msdos label" (a simple partition table) diff --git a/libisoburn/trunk/xorriso/xorriso_timestamp.h b/libisoburn/trunk/xorriso/xorriso_timestamp.h index a73effb9..db1fa665 100644 --- a/libisoburn/trunk/xorriso/xorriso_timestamp.h +++ b/libisoburn/trunk/xorriso/xorriso_timestamp.h @@ -1 +1 @@ -#define Xorriso_timestamP "2010.04.22.160615" +#define Xorriso_timestamP "2010.04.26.121051" diff --git a/libisoburn/trunk/xorriso/xorrisoburn.c b/libisoburn/trunk/xorriso/xorrisoburn.c index 0e5d8591..aa43c520 100644 --- a/libisoburn/trunk/xorriso/xorrisoburn.c +++ b/libisoburn/trunk/xorriso/xorrisoburn.c @@ -1422,6 +1422,7 @@ int Xorriso_give_up_drive(struct XorrisO *xorriso, int flag) xorriso->no_volset_present= 0; xorriso->loaded_boot_bin_lba= 0; xorriso->loaded_boot_cat_path[0]= 0; + xorriso->boot_count= 0; in_is_out_too= 0; } if((flag&2) && xorriso->out_drive_handle!=NULL) { @@ -1610,27 +1611,35 @@ int Xorriso_is_isohybrid(struct XorrisO *xorriso, IsoFile *bootimg_node, int Xorriso_set_isolinux_options(struct XorrisO *xorriso, IsoImage *image, int flag) { - int make_isohybrid_mbr= 0, ret, patch_table= 0; - ElToritoBootImage *bootimg; - IsoFile *bootimg_node; + int make_isohybrid_mbr= 0, ret, patch_table= 0, num_boots; + ElToritoBootImage *bootimg, **boots = NULL; + IsoFile *bootimg_node, **bootnodes = NULL; ret= iso_image_get_boot_image(image, &bootimg, &bootimg_node, NULL); + Xorriso_process_msg_queues(xorriso,0); if(ret != 1) { sprintf(xorriso->info_text, "Programming error: No boot image available in Xorriso_set_isolinux_options()"); Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0); - return(-1); + ret= -1; goto ex; + } + ret= iso_image_get_all_boot_imgs(image, &num_boots, &boots, &bootnodes, 0); + Xorriso_process_msg_queues(xorriso,0); + if(ret != 1) { + Xorriso_report_iso_error(xorriso, "", ret, "Cannot inquire boot images", 0, + "FATAL", 1); + ret= -1; goto ex; } patch_table = !!xorriso->patch_isolinux_image; - if(xorriso->boot_image_isohybrid == 0) { - ret= el_torito_set_isolinux_options(bootimg, patch_table, 0); - return(ret == 1); + if(xorriso->boot_image_isohybrid == 0 || num_boots > 1) { + ret= el_torito_set_isolinux_options(boots[num_boots - 1], patch_table, 0); + ret= (ret == 1); goto ex; } if(xorriso->boot_image_isohybrid == 3) { make_isohybrid_mbr= 1; } else { ret= Xorriso_is_isohybrid(xorriso, bootimg_node, 0); if(ret < 0) - return(0); + {ret= 0; goto ex;} if(ret > 0) make_isohybrid_mbr= 1; } @@ -1639,7 +1648,7 @@ int Xorriso_set_isolinux_options(struct XorrisO *xorriso, sprintf(xorriso->info_text, "Isohybrid signature is demanded but not found in boot image file."); Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); - return(0); + {ret= 0; goto ex;} } if(make_isohybrid_mbr) { sprintf(xorriso->info_text, "Will write isohybrid MBR."); @@ -1649,7 +1658,14 @@ int Xorriso_set_isolinux_options(struct XorrisO *xorriso, ret= el_torito_set_isolinux_options(bootimg, patch_table | (make_isohybrid_mbr << 1),0); - return(ret == 1); + ret= (ret == 1); +ex: + Xorriso_process_msg_queues(xorriso,0); + if(boots != NULL) + free(boots); + if(bootnodes != NULL) + free(bootnodes); + return(ret); } @@ -1806,6 +1822,423 @@ ex:; } +/* + bit0= do only report non-default settings + bit1= do only report to fp + bit2= is_default + bit3= append -boot_image any next + bit4= eventually concentrate boot options +*/ +int Xorriso_boot_item_status(struct XorrisO *xorriso, char *cat_path, + char *bin_path, int platform_id, + int patch_isolinux, int emul, off_t load_size, + unsigned char *id_string, + unsigned char *selection_crit, char *form, + char *filter, FILE *fp, int flag) +{ + int is_default, no_defaults, i, is_default_id= 0, ret; + char *line, bspec[SfileadrL + 80], zeros[28]; + off_t file_size; + struct stat stbuf; + + no_defaults= flag & 1; + line= xorriso->result_line; + + if(flag & 16) { + /* >>> BOOT: allow to concentrate boot options. */ + memset(zeros, 0, 28); + if(memcmp(id_string, zeros, 28) == 0 && + memcmp(selection_crit, zeros, 20) == 0) + is_default_id= 1; + + /* -boot_image isolinux dir= ... */ + bspec[0]= 0; + if(strcmp(form, "isolinux") != 0 && strcmp(form, "any") != 0) + ; + else if(strcmp(bin_path, "/isolinux.bin") == 0 && + strcmp(cat_path, "/boot.cat") == 0) + strcpy(bspec, "dir=/"); + else if(strcmp(bin_path, "/isolinux/isolinux.bin") == 0 && + strcmp(cat_path, "/isolinux/boot.cat") == 0) + strcpy(bspec, "dir=/isolinux"); + else if(strcmp(xorriso->boot_image_bin_path, + "/boot/isolinux/isolinux.bin") == 0 + && strcmp(xorriso->boot_image_cat_path, + "/boot/isolinux/boot.cat") == 0) + strcpy(bspec, "dir=/boot/isolinux"); + memset(zeros, 0, 28); + if(bspec[0] && platform_id == 0 && patch_isolinux && + load_size == 2048 && is_default_id) { + sprintf(line, "-boot_image isolinux %s\n", bspec); + Xorriso_status_result(xorriso,filter,fp,flag&2); + return(1); + } + + file_size= 0; + ret= Xorriso_iso_lstat(xorriso, bin_path, &stbuf, 2 | 4); + if(ret == 0) + file_size= ((stbuf.st_size / (off_t) 512) + + !!(stbuf.st_size % (off_t) 512)) * 512; + if(platform_id == 0xef && !patch_isolinux && + load_size == file_size && is_default_id) { + sprintf(line, "-boot_image any efi_path="); + Text_shellsafe(bin_path, line, 1); + strcat(line, "\n"); + Xorriso_status_result(xorriso,filter,fp,flag&2); + return(1); + } + } + + is_default= (bin_path[0] == 0) || (flag & 4); + sprintf(line, "-boot_image %s bin_path=", form); + Text_shellsafe(bin_path, line, 1); + strcat(line, "\n"); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + + is_default= (platform_id == 0 || (flag & 4)); + sprintf(line, "-boot_image %s platform_id=0x%-2.2x\n", form, platform_id); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + + is_default= (patch_isolinux == 0 || bin_path[0] == 0 || (flag & 4)); + sprintf(line, "-boot_image %s boot_info_table=%s\n", + form, patch_isolinux ? "on" : "off"); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + + is_default= (load_size == 2048 || (flag & 4)); + sprintf(line, "-boot_image %s load_size=%lu\n", + form, (unsigned long) load_size); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + + is_default= 1; + if(!(flag & 4)) + for(i= 0; i < 20; i++) + if(selection_crit[i]) + is_default= 0; + sprintf(line, "-boot_image %s sel_crit=", form); + for(i= 0; i < 20; i++) + sprintf(line + strlen(line), "%-2.2X", (unsigned int) selection_crit[i]); + strcat(line, "\n"); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + + is_default= 1; + if(!(flag & 4)) + for(i= 0; i < 28; i++) + if(id_string[i]) + is_default= 0; + sprintf(line, "-boot_image %s id_string=", form); + for(i= 0; i < 28; i++) + sprintf(line + strlen(line), "%-2.2X", (unsigned int) id_string[i]); + strcat(line, "\n"); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + + return(1); +} + + +/* + bit0= do only report non-default settings + bit1= do only report to fp +*/ +int Xorriso_boot_image_status(struct XorrisO *xorriso, char *filter, FILE *fp, + int flag) +{ + int ret, i, num_boots, hflag; + int bin_path_in_use= 0, is_default, no_defaults; + char sfe[5*SfileadrL], path[SfileadrL], *form= "any", *line; + struct burn_drive_info *dinfo; + struct burn_drive *drive; + IsoImage *image= NULL; + ElToritoBootImage **boots = NULL; + IsoFile **bootnodes = NULL; + int platform_id, patch, load_size; + enum eltorito_boot_media_type media_type; + unsigned char id_string[29], sel_crit[21]; + + line= xorriso->result_line; + no_defaults= flag & 1; + + if(xorriso->boot_count == 0 && xorriso->boot_image_bin_path[0] == 0) { + if(xorriso->patch_isolinux_image) { + sprintf(line, "-boot_image %s patch\n", form); + is_default= 0; + } else if(xorriso->keep_boot_image) { + sprintf(line, "-boot_image %s keep\n", form); + is_default= 0; + } else { + sprintf(line, "-boot_image %s discard\n", form); + is_default= 1; + } + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + ret= 1; goto ex; + } + + ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive, + "on attempt to print boot info", 16); + if(ret<=0) + {ret= 0; goto ex;} + image= isoburn_get_attached_image(drive); + Xorriso_process_msg_queues(xorriso,0); + if(image == NULL) + {ret= 0; goto ex;} + + if(xorriso->boot_image_bin_path[0] || xorriso->boot_count > 0) + bin_path_in_use= 1; + if(xorriso->boot_image_cat_path[0] && bin_path_in_use) { + is_default= 0; + sprintf(line,"-boot_image %s cat_path=%s\n", + form, Text_shellsafe(xorriso->boot_image_cat_path, sfe, 0)); + if(!(is_default && no_defaults)) + Xorriso_status_result(xorriso,filter,fp,flag&2); + } + + if(xorriso->boot_count > 0) { + + /* show attached boot image info */; + + ret= iso_image_get_all_boot_imgs(image, &num_boots, &boots, &bootnodes, 0); + Xorriso_process_msg_queues(xorriso,0); + if(ret == 1 && num_boots > 0) { + for(i= 0; i < num_boots; i++) { + ret= Xorriso_path_from_node(xorriso, (IsoNode *) bootnodes[i], path, 0); + if(ret <= 0) + continue; + platform_id= el_torito_get_boot_platform_id(boots[i]); + patch= el_torito_get_isolinux_options(boots[i], 0); + el_torito_get_boot_media_type(boots[i], &media_type); + load_size= el_torito_get_load_size(boots[i]) * 512; + el_torito_get_id_string(boots[i], id_string); + el_torito_get_selection_crit(boots[i], sel_crit); + ret= Xorriso_boot_item_status(xorriso, xorriso->boot_image_cat_path, + path, platform_id, patch & 1, media_type, + load_size, id_string, sel_crit, "any", + filter, fp, 16 | (flag & 3)); + if(ret <= 0) + continue; + sprintf(line,"-boot_image %s next\n", form); + Xorriso_status_result(xorriso,filter,fp,flag&2); + } + } + } + + /* Show pending boot image info */ + if(strcmp(xorriso->boot_image_bin_form, "isolinux") == 0 || + strcmp(xorriso->boot_image_bin_form, "grub") == 0) + form= xorriso->boot_image_bin_form; + + if(xorriso->boot_count > 0 && + xorriso->boot_platform_id == 0 && + xorriso->patch_isolinux_image == 0 && + xorriso->boot_image_bin_path[0] == 0 && + xorriso->boot_image_emul == 0 && + xorriso->boot_image_load_size == 4 * 512) { + for(i= 0; i < 20; i++) + if(xorriso->boot_selection_crit[i]) + break; + if(i >= 20) + for(i= 0; i < 28; i++) + if(xorriso->boot_id_string[i]) + break; + if(i >= 28) + {ret= 1; goto ex;} /* Images registered, pending is still default */ + } + + hflag= 16; + if(xorriso->boot_platform_id == 0xef && !xorriso->boot_efi_default) + hflag= 0; + ret= Xorriso_boot_item_status(xorriso, xorriso->boot_image_cat_path, + xorriso->boot_image_bin_path, xorriso->boot_platform_id, + xorriso->patch_isolinux_image, xorriso->boot_image_emul, + xorriso->boot_image_load_size, xorriso->boot_id_string, + xorriso->boot_selection_crit, form, + filter, fp, hflag | (flag & 3)); + if(ret <= 0) + goto ex; + + ret= 1; +ex: + if(boots != NULL) + free(boots); + if(bootnodes != NULL) + free(bootnodes); + return(ret); +} + + +/* @param flag bit0= do not increment boot_count + and do not reset boot parameters + bit1= dispose attached boot images +*/ +int Xorriso_attach_boot_image(struct XorrisO *xorriso, int flag) +{ + int ret; + char sfe[5*SfileadrL], *cpt; + struct burn_drive_info *source_dinfo; + struct burn_drive *source_drive; + IsoImage *image= NULL; + IsoNode *node; + ElToritoBootImage *bootimg; + enum eltorito_boot_media_type emul_type= ELTORITO_NO_EMUL; + char *bin_path; + int emul, platform_id; + off_t load_size; + struct stat stbuf; + int hflag= 0; + + if(xorriso->boot_image_bin_path[0] == 0 && !(flag & 2)) { + + /* >>> no boot image path given : no op */; + + ret= 2; goto ex; + } + + if(xorriso->in_drive_handle == NULL) + hflag= 2; + ret= Xorriso_get_drive_handles(xorriso, &source_dinfo, &source_drive, + "on attempt to attach boot image", hflag); + if(ret<=0) + goto ex; + image= isoburn_get_attached_image(source_drive); + if(image == NULL) { + /* (should not happen) */ + sprintf(xorriso->info_text, + "No ISO image present on attempt to attach boot image"); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + ret= 0; goto ex; + } + if(flag & 2) { + iso_image_remove_boot_image(image); + xorriso->boot_count= 0; + ret= 1; goto ex; + } + + bin_path= xorriso->boot_image_bin_path; + emul= xorriso->boot_image_emul; + platform_id= xorriso->boot_platform_id; + load_size= xorriso->boot_image_load_size; + + if(xorriso->boot_efi_default) { + emul= 0; + platform_id= 0xef; + xorriso->patch_isolinux_image= 0; + } + if(platform_id == 0xef || load_size < 0) { + ret= Xorriso_iso_lstat(xorriso, bin_path, &stbuf, 2 | 4); + if(ret != 0) + {ret= 0; goto ex;} + load_size= ((stbuf.st_size / (off_t) 512) + + !!(stbuf.st_size % (off_t) 512)) * 512; + } + sprintf(xorriso->info_text, "Adding boot image %s", + Text_shellsafe(bin_path, sfe, 0)); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "DEBUG", 0); + + if(emul == 0) + emul_type= ELTORITO_NO_EMUL; + else if(emul == 1) + emul_type= ELTORITO_HARD_DISC_EMUL; + else if(emul == 2) + emul_type= ELTORITO_FLOPPY_EMUL; + + ret= Xorriso_node_from_path(xorriso, image, bin_path, &node, 1); + if(ret <= 0) { + sprintf(xorriso->info_text, + "Cannot find in ISO image: -boot_image ... bin_path=%s", + Text_shellsafe(bin_path, sfe, 0)); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + {ret= 0; goto ex;} + } + + if(xorriso->boot_count == 0) { + if(xorriso->boot_image_cat_path[0] == 0) { + strcpy(xorriso->boot_image_cat_path, bin_path); + cpt= strrchr(xorriso->boot_image_cat_path, '/'); + if(cpt == NULL) + cpt= xorriso->boot_image_cat_path; + else + cpt++; + strcpy(cpt, "boot.cat"); + } + ret= Xorriso_node_from_path(xorriso, image, xorriso->boot_image_cat_path, + &node, 1); + if(ret > 0) { + if(!xorriso->do_overwrite) { + sprintf(xorriso->info_text, + "May not overwite existing -boot_image ... cat_path=%s", + Text_shellsafe(xorriso->boot_image_cat_path, sfe, 0)); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + {ret= 0; goto ex;} + } + ret= Xorriso_rmi(xorriso, NULL, (off_t) 0, xorriso->boot_image_cat_path, + 8 | (xorriso->do_overwrite == 1)); + if(ret != 1) { + sprintf(xorriso->info_text, + "Could not remove existing -boot_image cat_path=%s", + Text_shellsafe(xorriso->boot_image_cat_path, sfe, 0)); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + {ret= 0; goto ex;} + } + } + + /* Discard old boot image, set new one */ + ret= iso_image_get_boot_image(image, &bootimg, NULL, NULL); + if(ret == 1) + iso_image_remove_boot_image(image); + ret= iso_image_set_boot_image(image, bin_path, emul_type, + xorriso->boot_image_cat_path, &bootimg); + if(ret > 0) + iso_image_set_boot_catalog_weight(image, 1000000000); + } else { + ret= iso_image_add_boot_image(image, bin_path, emul_type, 0, &bootimg); + } + if(ret < 0) { + Xorriso_process_msg_queues(xorriso,0); + Xorriso_report_iso_error(xorriso, "", ret, + "Error when attaching El-Torito boot image to ISO 9660 image", + 0, "FAILURE", 1); + sprintf(xorriso->info_text, + "Could not attach El-Torito boot image to ISO 9660 image"); + Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); + {ret= 0; goto ex;} + } + el_torito_set_boot_platform_id(bootimg, (uint8_t) platform_id); + el_torito_set_load_size(bootimg, load_size / 512); + el_torito_set_id_string(bootimg, xorriso->boot_id_string); + el_torito_set_selection_crit(bootimg, xorriso->boot_selection_crit); + ret= Xorriso_set_isolinux_options(xorriso, image, 0); + if(!(flag & 1)) { + /* Register attachment and reset even in case of error return */ + xorriso->boot_count++; + xorriso->boot_platform_id= 0; + xorriso->patch_isolinux_image&= ~1; + xorriso->boot_image_bin_path[0]= 0; + xorriso->boot_image_bin_form[0]= 0; + xorriso->boot_image_emul= 0; + xorriso->boot_image_load_size= 4 * 512; + memset(xorriso->boot_id_string, 0, sizeof(xorriso->boot_id_string)); + memset(xorriso->boot_selection_crit, 0, + sizeof(xorriso->boot_selection_crit)); + xorriso->boot_efi_default= 0; + } + if(ret <= 0) + goto ex; + + ret= 1; +ex:; + if(image != NULL) + iso_image_unref(image); + return(ret); +} + + +/* #define Xorriso_boot_dummY 1 */ + /* @param flag bit0= do not write but only prepare and return size in sectors */ @@ -1813,7 +2246,7 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) { int ret, relax= 0, i, pacifier_speed= 0, data_lba, ext; int major, minor, micro; - char xorriso_id[256], *img_id, sfe[5*SfileadrL], *cpt, *out_cs; + char xorriso_id[256], *img_id, sfe[5*SfileadrL], *out_cs; struct isoburn_imgen_opts *sopts= NULL; struct burn_drive_info *dinfo, *source_dinfo; struct burn_drive *drive, *source_drive; @@ -1825,14 +2258,23 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) struct burn_track **tracks; enum burn_disc_status s; IsoImage *image= NULL; - IsoNode *node, *root_node; - ElToritoBootImage *bootimg, *efi_bootimg; - enum eltorito_boot_media_type emul_type= ELTORITO_NO_EMUL; + IsoNode *root_node; int profile_number; - char profile_name[80], *boot_image_bin_path; + char profile_name[80]; + +#ifdef Xorriso_multi_booT + IsoBoot *bootcat_node; +#else + char *cpt; + IsoNode *node; + ElToritoBootImage *bootimg; + ElToritoBootImage *efi_bootimg; + enum eltorito_boot_media_type emul_type= ELTORITO_NO_EMUL; int boot_image_emul, boot_platform_id; off_t boot_image_load_size; struct stat stbuf; + char *boot_image_bin_path; +#endif /* ! Xorriso_multi_booT */ ret= Xorriso_finish_hl_update(xorriso, 0); if(ret <= 0) @@ -1884,7 +2326,7 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) ret= isoburn_igopt_new(&sopts, 0); if(ret<=0) { Xorriso_process_msg_queues(xorriso, 0); - return(ret); + goto ex; } relax= xorriso->relax_compliance; @@ -1913,6 +2355,31 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) goto ex; /* Activate, adjust or discard boot image */ + +#ifdef Xorriso_multi_booT + + if(image!=NULL && !(flag&1)) { + if(xorriso->boot_image_bin_path[0]) { + ret= Xorriso_attach_boot_image(xorriso, xorriso->boot_count == 0); + if(ret <= 0) + goto ex; + + /* Eventually rename boot catalog node to changed boot_image_cat_path */ + ret= iso_image_get_boot_image(image, NULL, NULL, &bootcat_node); + if(ret > 0) { + ret= Xorriso_path_from_node(xorriso, (IsoNode *) bootcat_node, sfe, 0); + if(ret > 0) { + if(strcmp(sfe, xorriso->boot_image_cat_path) != 0) { + ret= Xorriso_rename(xorriso, NULL, sfe, + xorriso->boot_image_cat_path, 0); + if(ret <= 0) + goto ex; + } + } + } + +#else /* Xorriso_multi_booT */ + boot_image_bin_path= xorriso->boot_image_bin_path; boot_image_emul= xorriso->boot_image_emul; boot_platform_id= xorriso->boot_platform_id; @@ -2005,6 +2472,17 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); {ret= 0; goto ex;} } + +#ifdef Xorriso_boot_dummY +/* <<< for testing only */ + if(xorriso->boot_image_bin_path[0] == 0) + el_torito_set_id_string(bootimg, + (unsigned char *) "xorriso EFI 3456789012345678"); + else + el_torito_set_id_string(bootimg, + (unsigned char *) "xorriso 80x86 BIOS 012345678"); +#endif /* Xorriso_boot_dummY */ + el_torito_set_boot_platform_id(bootimg, (uint8_t) boot_platform_id); iso_image_set_boot_catalog_weight(image, 1000000000); el_torito_set_load_size(bootimg, boot_image_load_size / 512); @@ -2025,6 +2503,15 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) "Error when adding EFI boot image", 0, "FAILURE", 1); goto ex; } + +#ifdef Xorriso_boot_dummY +/* <<< for testing only */ + el_torito_set_id_string(efi_bootimg, + (unsigned char *) "xorriso EFI 3456789012345678"); + el_torito_set_selection_crit(efi_bootimg, + (unsigned char *) "@selection criteria@"); +#endif /* Xorriso_boot_dummY */ + el_torito_set_boot_platform_id(efi_bootimg, (uint8_t) 0xef); ret= Xorriso_iso_lstat(xorriso, xorriso->boot_image_efi_path, &stbuf, 2 | 4); @@ -2033,7 +2520,45 @@ int Xorriso_write_session(struct XorrisO *xorriso, int flag) boot_image_load_size= ((stbuf.st_size / (off_t) 512) + !!(stbuf.st_size % (off_t) 512)); el_torito_set_load_size(efi_bootimg, boot_image_load_size); + +#ifdef Xorriso_boot_dummY +/* <<< for testing only */ + ret= iso_image_add_boot_image(image, "/xxx", + ELTORITO_NO_EMUL, 0, &efi_bootimg); + if(ret < 0) { + Xorriso_process_msg_queues(xorriso,0); + Xorriso_report_iso_error(xorriso, "", ret, + "Error when adding EFI boot image 2", 0, "FAILURE", 1); + goto ex; + } + el_torito_set_id_string(efi_bootimg, + (unsigned char *) "xorriso EFI 3456789012345678"); + el_torito_set_selection_crit(efi_bootimg, + (unsigned char *) "@selection crit 2 @"); + el_torito_set_boot_platform_id(efi_bootimg, (uint8_t) 0xef); + el_torito_set_load_size(efi_bootimg, boot_image_load_size); + + ret= iso_image_add_boot_image(image, "/xxxx", + ELTORITO_NO_EMUL, 0, &efi_bootimg); + if(ret < 0) { + Xorriso_process_msg_queues(xorriso,0); + Xorriso_report_iso_error(xorriso, "", ret, + "Error when adding BIOS boot image 2", 0, "FAILURE", 1); + goto ex; + } + el_torito_set_id_string(efi_bootimg, + (unsigned char *) "xorriso BIOS2 abcdefghijklmn"); + el_torito_set_selection_crit(efi_bootimg, + (unsigned char *) "@selection crit 3 @"); + el_torito_set_boot_platform_id(efi_bootimg, (uint8_t) 0); + el_torito_set_load_size(efi_bootimg, (uint8_t) 4); + +#endif /* Xorriso_boot_dummY */ + } + +#endif /* ! Xorriso_multi_booT */ + } else if(xorriso->patch_isolinux_image) { if(ret==1) { relax|= isoburn_igopt_allow_full_ascii; @@ -5356,10 +5881,10 @@ int Xorriso_toc_line(struct XorrisO *xorriso, int flag) */ int Xorriso_show_boot_info(struct XorrisO *xorriso, int flag) { - int ret, bin_path_valid= 0,has_isolinux_mbr= 0, i, num_boots, bin_is_efi= 0; - unsigned int mbr_lba= 0; + int ret, bin_path_valid= 0,has_isolinux_mbr= 0, i, num_boots; + unsigned int mbr_lba= 0, platform_id; off_t lb0_count; - char *respt, sfe[5*SfileadrL], path[SfileadrL], *path_cmd= "bin_path"; + char *respt, sfe[5*SfileadrL], path[SfileadrL], path_cmd[16]; unsigned char lb0[2048]; struct burn_drive_info *dinfo; struct burn_drive *drive; @@ -5369,6 +5894,15 @@ int Xorriso_show_boot_info(struct XorrisO *xorriso, int flag) IsoBoot *bootcat_node; respt= xorriso->result_line; + + if(xorriso->boot_count > 0) { + if(!(flag & 1)) { + sprintf(respt, "Boot record : overridden by -boot_image any next\n"); + Xorriso_toc_line(xorriso, flag & 8); + } + ret= 1; goto ex; + } + ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive, "on attempt to print boot info", 16); if(ret<=0) @@ -5388,7 +5922,7 @@ no_boot:; ret= iso_image_get_boot_image(image, &bootimg, &bootimg_node, &bootcat_node); if(ret != 1) goto no_boot; - bin_is_efi= (el_torito_get_boot_platform_id(bootimg) == 0xef); + ret= Xorriso_path_from_lba(xorriso, NULL, xorriso->loaded_boot_bin_lba, path, 1); if(ret > 0) @@ -5432,8 +5966,18 @@ no_boot:; Xorriso_toc_line(xorriso, flag & 8); if(flag & 2) {ret= 1; goto ex;} - if(bin_is_efi) - path_cmd= "efi_path"; + + if(xorriso->loaded_boot_cat_path[0]) + sprintf(respt, "Boot cat_path: %s\n", + Text_shellsafe(xorriso->loaded_boot_cat_path, sfe, 0)); + else + sprintf(respt, "Boot cat_path: -not-found-at-load-time-\n"); + Xorriso_toc_line(xorriso, flag & 8); + + platform_id= el_torito_get_boot_platform_id(bootimg); + strcpy(path_cmd, "bin_path"); + if(platform_id != 0) + sprintf(path_cmd, " 0x%-2.2X ", (unsigned int) platform_id); if(bin_path_valid) sprintf(respt, "Boot %s: %s\n", path_cmd, Text_shellsafe(path, sfe, 0)); else if(xorriso->loaded_boot_bin_lba <= 0) @@ -5447,23 +5991,16 @@ no_boot:; Xorriso_process_msg_queues(xorriso,0); if(ret == 1 && num_boots > 1) { for(i= 1; i < num_boots; i++) { - ret= el_torito_get_boot_platform_id(boots[i]); - if(ret == 0xef) { - ret= Xorriso_path_from_node(xorriso, (IsoNode *) bootnodes[i], path, 0); - if(ret > 0) { - sprintf(respt, "Boot efi_path: %s\n", Text_shellsafe(path, sfe, 0)); - Xorriso_toc_line(xorriso, flag & 8); - break; - } - } + platform_id= el_torito_get_boot_platform_id(boots[i]); + sprintf(path_cmd, "platf %-2.2X", (unsigned int) platform_id); + ret= Xorriso_path_from_node(xorriso, (IsoNode *) bootnodes[i], path, 0); + if(ret > 0) + sprintf(respt, "Boot %s: %s\n", path_cmd, Text_shellsafe(path, sfe, 0)); + else + sprintf(respt, "Boot %s: -not-found-any-more-\n", path_cmd); + Xorriso_toc_line(xorriso, flag & 8); } } - if(xorriso->loaded_boot_cat_path[0]) - sprintf(respt, "Boot cat_path: %s\n", - Text_shellsafe(xorriso->loaded_boot_cat_path, sfe, 0)); - else - sprintf(respt, "Boot cat_path: -not-found-at-load-time-\n"); - Xorriso_toc_line(xorriso, flag & 8); ret= 1; ex:; if(boots != NULL) diff --git a/libisoburn/trunk/xorriso/xorrisoburn.h b/libisoburn/trunk/xorriso/xorrisoburn.h index 1e160af8..92cb2036 100644 --- a/libisoburn/trunk/xorriso/xorrisoburn.h +++ b/libisoburn/trunk/xorriso/xorrisoburn.h @@ -491,7 +491,17 @@ int Xorriso_set_change_pending(struct XorrisO *xorriso, int flag); /* @param flag bit0= enable SCSI command logging to stderr */ int Xorriso_scsi_log(struct XorrisO *xorriso, int flag); +/* flag bit0= do not increment boot_count and do not reset boot parameters + bit1= dispose attached boot images +*/ +int Xorriso_attach_boot_image(struct XorrisO *xorriso, int flag); +/* + bit0= do only report non-default settings + bit1= do only report to fp +*/ +int Xorriso_boot_image_status(struct XorrisO *xorriso, char *filter, FILE *fp, + int flag); /* A pseudo file type for El-Torito bootsectors as in man 2 stat : For now take the highest possible value.