static int print_ptable(int fd) { struct efi_entry *entry; int n, gpt_size; unsigned char *buf = NULL; /* Alloc EFI sectors: 34 sectors */ gpt_size = (1 + 1 + 32)*512; buf = malloc(gpt_size); if (!buf) goto fail; if (lseek(fd, 0, SEEK_SET) < 0) { printf("\n seek error \n"); goto fail; } n = read(fd, buf, gpt_size); if (memcmp(buf + 512, "EFI PART", 8)) { printf("efi partition table not found\n"); goto fail; } entry = (struct efi_entry *)(buf + 512 + 512); printf("\n EFI table is:\n"); for (n = 0; n < 128; n++) { print_efi_partition(entry + n); } fail: free(buf); return 0; }
/* * Print a partition map */ void print_map(struct partition_info *map) { int i; int want_header; struct dk_gpt *vtoc64; if (cur_label == L_TYPE_EFI) { vtoc64 = map->etoc; want_header = 1; for (i = 0; i < vtoc64->efi_nparts; i++) { /* * we want to print partitions above 7 in expert mode only * or if the partition is reserved */ if (i >= 7 && !expert_mode && ((int)vtoc64->efi_parts[i].p_tag != V_RESERVED)) { continue; } print_efi_partition(vtoc64, i, want_header); want_header = 0; } fmt_print("\n"); return; } /* * Loop through each partition, printing the header * the first time. */ want_header = 1; for (i = 0; i < NDKMAP; i++) { if (i > 9) { break; } print_partition(map, i, want_header); want_header = 0; } fmt_print("\n"); }
/* * This routine allows the user to change the boundaries of the given * partition in the current partition map. */ void change_partition(int num) { uint_t i; uint64_t i64, j64; uint_t j; int deflt; part_deflt_t p_deflt; u_ioparam_t ioparam; int tag; int flag; char msg[256]; blkaddr32_t cyl_offset = 0; efi_deflt_t efi_deflt; /* * check if there exists a partition table for the disk. */ if (cur_parts == NULL) { err_print("Current Disk has no partition table.\n"); return; } if (cur_label == L_TYPE_EFI) { if (num > cur_parts->etoc->efi_nparts - 1) { err_print("Invalid partition for EFI label\n"); return; } print_efi_partition(cur_parts->etoc, num, 1); fmt_print("\n"); /* * Prompt for p_tag and p_flag values for this partition */ deflt = cur_parts->etoc->efi_parts[num].p_tag; if (deflt == V_UNASSIGNED) { deflt = V_USR; } (void) sprintf(msg, "Enter partition id tag"); ioparam.io_slist = ptag_choices; tag = input(FIO_SLIST, msg, ':', &ioparam, &deflt, DATA_INPUT); deflt = cur_parts->etoc->efi_parts[num].p_flag; (void) sprintf(msg, "Enter partition permission flags"); ioparam.io_slist = pflag_choices; flag = input(FIO_SLIST, msg, ':', &ioparam, &deflt, DATA_INPUT); ioparam.io_bounds.lower = 34; ioparam.io_bounds.upper = cur_parts->etoc->efi_last_u_lba; efi_deflt.start_sector = maxofN(cur_parts->etoc); if ((cur_parts->etoc->efi_parts[num].p_start != 0) && (cur_parts->etoc->efi_parts[num].p_size != 0)) { efi_deflt.start_sector = cur_parts->etoc->efi_parts[num].p_start; } efi_deflt.end_sector = ioparam.io_bounds.upper - efi_deflt.start_sector; i64 = input(FIO_INT64, "Enter new starting Sector", ':', &ioparam, (int *)&efi_deflt, DATA_INPUT); ioparam.io_bounds.lower = 0; ioparam.io_bounds.upper = cur_parts->etoc->efi_last_u_lba; efi_deflt.end_sector = cur_parts->etoc->efi_parts[num].p_size; efi_deflt.start_sector = i64; j64 = input(FIO_EFI, "Enter partition size", ':', &ioparam, (int *)&efi_deflt, DATA_INPUT); if (j64 == 0) { tag = V_UNASSIGNED; i64 = 0; } else if ((j64 != 0) && (tag == V_UNASSIGNED)) { tag = V_USR; } if (cur_parts->pinfo_name != NULL) make_partition(); cur_parts->etoc->efi_parts[num].p_tag = tag; cur_parts->etoc->efi_parts[num].p_flag = flag; cur_parts->etoc->efi_parts[num].p_start = i64; cur_parts->etoc->efi_parts[num].p_size = j64; /* * We are now done with EFI part, so return now */ return; } /* * Print out the given partition so the user knows what he/she's * getting into. */ print_partition(cur_parts, num, 1); fmt_print("\n"); /* * Prompt for p_tag and p_flag values for this partition. */ assert(cur_parts->vtoc.v_version == V_VERSION); deflt = cur_parts->vtoc.v_part[num].p_tag; (void) sprintf(msg, "Enter partition id tag"); ioparam.io_slist = ptag_choices; tag = input(FIO_SLIST, msg, ':', &ioparam, &deflt, DATA_INPUT); deflt = cur_parts->vtoc.v_part[num].p_flag; (void) sprintf(msg, "Enter partition permission flags"); ioparam.io_slist = pflag_choices; flag = input(FIO_SLIST, msg, ':', &ioparam, &deflt, DATA_INPUT); /* * Ask for the new values. The old values are the defaults, and * strict bounds checking is done on the values given. */ #if defined(i386) if (tag != V_UNASSIGNED && tag != V_BACKUP && tag != V_BOOT) { /* * Determine cyl offset for boot and alternate partitions. * Assuming that the alternate sectors partition (slice) * physical location immediately follows the boot * partition and partition sizes are expressed in multiples * of cylinder size. */ cyl_offset = cur_parts->pinfo_map[I_PARTITION].dkl_cylno + 1; if (tag != V_ALTSCTR) { if (cur_parts->pinfo_map[J_PARTITION].dkl_nblk != 0) { cyl_offset = cur_parts->pinfo_map[J_PARTITION].dkl_cylno + ((cur_parts->pinfo_map[J_PARTITION].dkl_nblk + (spc()-1)) / spc()); } } } #endif /* defined(i386) */ ioparam.io_bounds.lower = 0; ioparam.io_bounds.upper = ncyl - 1; deflt = max(cur_parts->pinfo_map[num].dkl_cylno, cyl_offset); i = (uint_t)input(FIO_INT, "Enter new starting cyl", ':', &ioparam, &deflt, DATA_INPUT); ioparam.io_bounds.lower = 0; ioparam.io_bounds.upper = (ncyl - i) * spc(); /* fill in defaults for the current partition */ p_deflt.start_cyl = i; p_deflt.deflt_size = min(cur_parts->pinfo_map[num].dkl_nblk, ioparam.io_bounds.upper); /* call input, passing p_deflt's address, typecast to (int *) */ j = (uint_t)input(FIO_ECYL, "Enter partition size", ':', &ioparam, (int *)&p_deflt, DATA_INPUT); /* * If the current partition has a size of zero change the * tag to Unassigned and the starting cylinder to zero */ if (j == 0) { tag = V_UNASSIGNED; i = 0; } #if defined(i386) if (i < cyl_offset && tag != V_UNASSIGNED && tag != V_BACKUP && tag != V_BOOT) { /* * This slice overlaps boot and/or alternates slice * Check if it's the boot or alternates slice and warn * accordingly */ if (i < cur_parts->pinfo_map[I_PARTITION].dkl_cylno + 1) { fmt_print("\nWarning: Partition overlaps boot "); fmt_print("partition. Specify different start cyl.\n"); return; } /* * Cyl offset for alternates partition was calculated before */ if (i < cyl_offset) { fmt_print("\nWarning: Partition overlaps alternates "); fmt_print("partition. Specify different start cyl.\n"); return; } } #endif /* defined(i386) */ /* * If user has entered a V_BACKUP tag then the partition * size should specify full disk capacity else * return an Error. */ if (tag == V_BACKUP) { uint_t fullsz; fullsz = ncyl * nhead * nsect; if (fullsz != j) { /* * V_BACKUP Tag Partition != full disk capacity. * print useful messages. */ fmt_print("\nWarning: Partition with V_BACKUP tag should "); fmt_print("specify full disk capacity. \n"); return; } } /* * If the current partition is named, we can't change it. * We create a new current partition map instead. */ if (cur_parts->pinfo_name != NULL) make_partition(); /* * Change the values. */ cur_parts->pinfo_map[num].dkl_cylno = i; cur_parts->pinfo_map[num].dkl_nblk = j; #if defined(_SUNOS_VTOC_16) cur_parts->vtoc.v_part[num].p_start = (daddr_t)(i * (nhead * nsect)); cur_parts->vtoc.v_part[num].p_size = (long)j; #endif /* defined(_SUNOS_VTOC_16) */ /* * Install the p_tag and p_flag values for this partition */ assert(cur_parts->vtoc.v_version == V_VERSION); cur_parts->vtoc.v_part[num].p_tag = (ushort_t)tag; cur_parts->vtoc.v_part[num].p_flag = (ushort_t)flag; }