aboutsummaryrefslogtreecommitdiff
path: root/util-linux/fdisk.c
diff options
context:
space:
mode:
Diffstat (limited to 'util-linux/fdisk.c')
-rw-r--r--util-linux/fdisk.c309
1 files changed, 149 insertions, 160 deletions
diff --git a/util-linux/fdisk.c b/util-linux/fdisk.c
index cc6dfa57a..f15b9af91 100644
--- a/util-linux/fdisk.c
+++ b/util-linux/fdisk.c
@@ -202,7 +202,7 @@ static int get_boot(enum action what);
202 }) 202 })
203 203
204 204
205#define LINE_LENGTH 800 205#define LINE_LENGTH 80
206#define pt_offset(b, n) ((struct partition *)((b) + 0x1be + \ 206#define pt_offset(b, n) ((struct partition *)((b) + 0x1be + \
207 (n) * sizeof(struct partition))) 207 (n) * sizeof(struct partition)))
208#define sector(s) ((s) & 0x3f) 208#define sector(s) ((s) & 0x3f)
@@ -291,16 +291,20 @@ write_part_table_flag(char *b)
291static char line_buffer[LINE_LENGTH]; 291static char line_buffer[LINE_LENGTH];
292static char *line_ptr; 292static char *line_ptr;
293 293
294/* read line; return 0 or first char */ 294/* read line; return 0 or first printable char */
295static int 295static int
296read_line(void) 296read_line(const char *prompt)
297{ 297{
298 fflush(stdout); /* requested by niles@scyld.com */ 298 int sz;
299
300 sz = read_line_input(prompt, line_buffer, LINE_LENGTH, NULL);
301 if (sz <= 0)
302 exit(0); /* Ctrl-D or Ctrl-C */
303
304 if (line_buffer[sz-1] == '\n')
305 line_buffer[--sz] = '\0';
306
299 line_ptr = line_buffer; 307 line_ptr = line_buffer;
300 if (!fgets(line_buffer, LINE_LENGTH, stdin)) {
301 /* error or eof */
302 bb_error_msg_and_die("\ngot EOF, exiting");
303 }
304 while (*line_ptr && !isgraph(*line_ptr)) 308 while (*line_ptr && !isgraph(*line_ptr))
305 line_ptr++; 309 line_ptr++;
306 return *line_ptr; 310 return *line_ptr;
@@ -309,22 +313,19 @@ read_line(void)
309static char 313static char
310read_nonempty(const char *mesg) 314read_nonempty(const char *mesg)
311{ 315{
312 do { 316 while (!read_line(mesg)) /* repeat */;
313 fputs(mesg, stdout);
314 } while (!read_line());
315 return *line_ptr; 317 return *line_ptr;
316} 318}
317 319
318static char 320static char
319read_maybe_empty(const char *mesg) 321read_maybe_empty(const char *mesg)
320{ 322{
321 fputs(mesg, stdout); 323 if (!read_line(mesg)) {
322 if (!read_line()) {
323 line_ptr = line_buffer; 324 line_ptr = line_buffer;
324 *line_ptr = '\n'; 325 line_ptr[0] = '\n';
325 line_ptr[1] = 0; 326 line_ptr[1] = '\0';
326 } 327 }
327 return *line_ptr; 328 return line_ptr[0];
328} 329}
329 330
330static int 331static int
@@ -469,9 +470,9 @@ static const struct systypes i386_sys_types[] = {
469 { "\x16" "Hidden FAT16" }, 470 { "\x16" "Hidden FAT16" },
470 { "\x17" "Hidden HPFS/NTFS" }, 471 { "\x17" "Hidden HPFS/NTFS" },
471 { "\x1b" "Hidden Win95 FAT32" }, 472 { "\x1b" "Hidden Win95 FAT32" },
472 { "\x1c" "Hidden Win95 FAT32 (LBA)" }, 473 { "\x1c" "Hidden W95 FAT32 (LBA)" },
473 { "\x1e" "Hidden Win95 FAT16 (LBA)" }, 474 { "\x1e" "Hidden W95 FAT16 (LBA)" },
474 { "\x3c" "PartitionMagic recovery" }, 475 { "\x3c" "Part.Magic recovery" },
475 { "\x41" "PPC PReP Boot" }, 476 { "\x41" "PPC PReP Boot" },
476 { "\x42" "SFS" }, 477 { "\x42" "SFS" },
477 { "\x63" "GNU HURD or SysV" }, /* GNU HURD or Mach or Sys V/386 (such as ISC UNIX) */ 478 { "\x63" "GNU HURD or SysV" }, /* GNU HURD or Mach or Sys V/386 (such as ISC UNIX) */
@@ -485,7 +486,7 @@ static const struct systypes i386_sys_types[] = {
485 { "\x87" "NTFS volume set" }, 486 { "\x87" "NTFS volume set" },
486 { "\x8e" "Linux LVM" }, 487 { "\x8e" "Linux LVM" },
487 { "\x9f" "BSD/OS" }, /* BSDI */ 488 { "\x9f" "BSD/OS" }, /* BSDI */
488 { "\xa0" "IBM Thinkpad hibernation" }, 489 { "\xa0" "Thinkpad hibernation" },
489 { "\xa5" "FreeBSD" }, /* various BSD flavours */ 490 { "\xa5" "FreeBSD" }, /* various BSD flavours */
490 { "\xa6" "OpenBSD" }, 491 { "\xa6" "OpenBSD" },
491 { "\xa8" "Darwin UFS" }, 492 { "\xa8" "Darwin UFS" },
@@ -718,71 +719,61 @@ is_dos_partition(int t)
718static void 719static void
719menu(void) 720menu(void)
720{ 721{
722 puts(_("Command Action"));
721 if (LABEL_IS_SUN) { 723 if (LABEL_IS_SUN) {
722 puts(_("Command action")); 724 puts(_("a\ttoggle a read only flag")); /* sun */
723 puts(_("\ta\ttoggle a read only flag")); /* sun */ 725 puts(_("b\tedit bsd disklabel"));
724 puts(_("\tb\tedit bsd disklabel")); 726 puts(_("c\ttoggle the mountable flag")); /* sun */
725 puts(_("\tc\ttoggle the mountable flag")); /* sun */ 727 puts(_("d\tdelete a partition"));
726 puts(_("\td\tdelete a partition")); 728 puts(_("l\tlist known partition types"));
727 puts(_("\tl\tlist known partition types")); 729 puts(_("n\tadd a new partition"));
728 puts(_("\tm\tprint this menu")); 730 puts(_("o\tcreate a new empty DOS partition table"));
729 puts(_("\tn\tadd a new partition")); 731 puts(_("p\tprint the partition table"));
730 puts(_("\to\tcreate a new empty DOS partition table")); 732 puts(_("q\tquit without saving changes"));
731 puts(_("\tp\tprint the partition table")); 733 puts(_("s\tcreate a new empty Sun disklabel")); /* sun */
732 puts(_("\tq\tquit without saving changes")); 734 puts(_("t\tchange a partition's system id"));
733 puts(_("\ts\tcreate a new empty Sun disklabel")); /* sun */ 735 puts(_("u\tchange display/entry units"));
734 puts(_("\tt\tchange a partition's system id")); 736 puts(_("v\tverify the partition table"));
735 puts(_("\tu\tchange display/entry units")); 737 puts(_("w\twrite table to disk and exit"));
736 puts(_("\tv\tverify the partition table"));
737 puts(_("\tw\twrite table to disk and exit"));
738#if ENABLE_FEATURE_FDISK_ADVANCED 738#if ENABLE_FEATURE_FDISK_ADVANCED
739 puts(_("\tx\textra functionality (experts only)")); 739 puts(_("x\textra functionality (experts only)"));
740#endif 740#endif
741 } else 741 } else if (LABEL_IS_SGI) {
742 if (LABEL_IS_SGI) { 742 puts(_("a\tselect bootable partition")); /* sgi flavour */
743 puts(_("Command action")); 743 puts(_("b\tedit bootfile entry")); /* sgi */
744 puts(_("\ta\tselect bootable partition")); /* sgi flavour */ 744 puts(_("c\tselect sgi swap partition")); /* sgi flavour */
745 puts(_("\tb\tedit bootfile entry")); /* sgi */ 745 puts(_("d\tdelete a partition"));
746 puts(_("\tc\tselect sgi swap partition")); /* sgi flavour */ 746 puts(_("l\tlist known partition types"));
747 puts(_("\td\tdelete a partition")); 747 puts(_("n\tadd a new partition"));
748 puts(_("\tl\tlist known partition types")); 748 puts(_("o\tcreate a new empty DOS partition table"));
749 puts(_("\tm\tprint this menu")); 749 puts(_("p\tprint the partition table"));
750 puts(_("\tn\tadd a new partition")); 750 puts(_("q\tquit without saving changes"));
751 puts(_("\to\tcreate a new empty DOS partition table")); 751 puts(_("s\tcreate a new empty Sun disklabel")); /* sun */
752 puts(_("\tp\tprint the partition table")); 752 puts(_("t\tchange a partition's system id"));
753 puts(_("\tq\tquit without saving changes")); 753 puts(_("u\tchange display/entry units"));
754 puts(_("\ts\tcreate a new empty Sun disklabel")); /* sun */ 754 puts(_("v\tverify the partition table"));
755 puts(_("\tt\tchange a partition's system id")); 755 puts(_("w\twrite table to disk and exit"));
756 puts(_("\tu\tchange display/entry units")); 756 } else if (LABEL_IS_AIX) {
757 puts(_("\tv\tverify the partition table")); 757 puts(_("o\tcreate a new empty DOS partition table"));
758 puts(_("\tw\twrite table to disk and exit")); 758 puts(_("q\tquit without saving changes"));
759 } else 759 puts(_("s\tcreate a new empty Sun disklabel")); /* sun */
760 if (LABEL_IS_AIX) { 760 } else {
761 puts(_("Command action")); 761 puts(_("a\ttoggle a bootable flag"));
762 puts(_("\tm\tprint this menu")); 762 puts(_("b\tedit bsd disklabel"));
763 puts(_("\to\tcreate a new empty DOS partition table")); 763 puts(_("c\ttoggle the dos compatibility flag"));
764 puts(_("\tq\tquit without saving changes")); 764 puts(_("d\tdelete a partition"));
765 puts(_("\ts\tcreate a new empty Sun disklabel")); /* sun */ 765 puts(_("l\tlist known partition types"));
766 } else 766 puts(_("n\tadd a new partition"));
767 { 767 puts(_("o\tcreate a new empty DOS partition table"));
768 puts(_("Command action")); 768 puts(_("p\tprint the partition table"));
769 puts(_("\ta\ttoggle a bootable flag")); 769 puts(_("q\tquit without saving changes"));
770 puts(_("\tb\tedit bsd disklabel")); 770 puts(_("s\tcreate a new empty Sun disklabel")); /* sun */
771 puts(_("\tc\ttoggle the dos compatibility flag")); 771 puts(_("t\tchange a partition's system id"));
772 puts(_("\td\tdelete a partition")); 772 puts(_("u\tchange display/entry units"));
773 puts(_("\tl\tlist known partition types")); 773 puts(_("v\tverify the partition table"));
774 puts(_("\tm\tprint this menu")); 774 puts(_("w\twrite table to disk and exit"));
775 puts(_("\tn\tadd a new partition"));
776 puts(_("\to\tcreate a new empty DOS partition table"));
777 puts(_("\tp\tprint the partition table"));
778 puts(_("\tq\tquit without saving changes"));
779 puts(_("\ts\tcreate a new empty Sun disklabel")); /* sun */
780 puts(_("\tt\tchange a partition's system id"));
781 puts(_("\tu\tchange display/entry units"));
782 puts(_("\tv\tverify the partition table"));
783 puts(_("\tw\twrite table to disk and exit"));
784#if ENABLE_FEATURE_FDISK_ADVANCED 775#if ENABLE_FEATURE_FDISK_ADVANCED
785 puts(_("\tx\textra functionality (experts only)")); 776 puts(_("x\textra functionality (experts only)"));
786#endif 777#endif
787 } 778 }
788} 779}
@@ -793,73 +784,64 @@ menu(void)
793static void 784static void
794xmenu(void) 785xmenu(void)
795{ 786{
787 puts(_("Command Action"));
796 if (LABEL_IS_SUN) { 788 if (LABEL_IS_SUN) {
797 puts(_("Command action")); 789 puts(_("a\tchange number of alternate cylinders")); /*sun*/
798 puts(_("\ta\tchange number of alternate cylinders")); /*sun*/ 790 puts(_("c\tchange number of cylinders"));
799 puts(_("\tc\tchange number of cylinders")); 791 puts(_("d\tprint the raw data in the partition table"));
800 puts(_("\td\tprint the raw data in the partition table")); 792 puts(_("e\tchange number of extra sectors per cylinder"));/*sun*/
801 puts(_("\te\tchange number of extra sectors per cylinder"));/*sun*/ 793 puts(_("h\tchange number of heads"));
802 puts(_("\th\tchange number of heads")); 794 puts(_("i\tchange interleave factor")); /*sun*/
803 puts(_("\ti\tchange interleave factor")); /*sun*/ 795 puts(_("o\tchange rotation speed (rpm)")); /*sun*/
804 puts(_("\to\tchange rotation speed (rpm)")); /*sun*/ 796 puts(_("p\tprint the partition table"));
805 puts(_("\tm\tprint this menu")); 797 puts(_("q\tquit without saving changes"));
806 puts(_("\tp\tprint the partition table")); 798 puts(_("r\treturn to main menu"));
807 puts(_("\tq\tquit without saving changes")); 799 puts(_("s\tchange number of sectors/track"));
808 puts(_("\tr\treturn to main menu")); 800 puts(_("v\tverify the partition table"));
809 puts(_("\ts\tchange number of sectors/track")); 801 puts(_("w\twrite table to disk and exit"));
810 puts(_("\tv\tverify the partition table")); 802 puts(_("y\tchange number of physical cylinders")); /*sun*/
811 puts(_("\tw\twrite table to disk and exit")); 803 } else if (LABEL_IS_SGI) {
812 puts(_("\ty\tchange number of physical cylinders")); /*sun*/ 804 puts(_("b\tmove beginning of data in a partition")); /* !sun */
813 } else 805 puts(_("c\tchange number of cylinders"));
814 if (LABEL_IS_SGI) { 806 puts(_("d\tprint the raw data in the partition table"));
815 puts(_("Command action")); 807 puts(_("e\tlist extended partitions")); /* !sun */
816 puts(_("\tb\tmove beginning of data in a partition")); /* !sun */ 808 puts(_("g\tcreate an IRIX (SGI) partition table"));/* sgi */
817 puts(_("\tc\tchange number of cylinders")); 809 puts(_("h\tchange number of heads"));
818 puts(_("\td\tprint the raw data in the partition table")); 810 puts(_("p\tprint the partition table"));
819 puts(_("\te\tlist extended partitions")); /* !sun */ 811 puts(_("q\tquit without saving changes"));
820 puts(_("\tg\tcreate an IRIX (SGI) partition table"));/* sgi */ 812 puts(_("r\treturn to main menu"));
821 puts(_("\th\tchange number of heads")); 813 puts(_("s\tchange number of sectors/track"));
822 puts(_("\tm\tprint this menu")); 814 puts(_("v\tverify the partition table"));
823 puts(_("\tp\tprint the partition table")); 815 puts(_("w\twrite table to disk and exit"));
824 puts(_("\tq\tquit without saving changes")); 816 } else if (LABEL_IS_AIX) {
825 puts(_("\tr\treturn to main menu")); 817 puts(_("b\tmove beginning of data in a partition")); /* !sun */
826 puts(_("\ts\tchange number of sectors/track")); 818 puts(_("c\tchange number of cylinders"));
827 puts(_("\tv\tverify the partition table")); 819 puts(_("d\tprint the raw data in the partition table"));
828 puts(_("\tw\twrite table to disk and exit")); 820 puts(_("e\tlist extended partitions")); /* !sun */
829 } else 821 puts(_("g\tcreate an IRIX (SGI) partition table"));/* sgi */
830 if (LABEL_IS_AIX) { 822 puts(_("h\tchange number of heads"));
831 puts(_("Command action")); 823 puts(_("p\tprint the partition table"));
832 puts(_("\tb\tmove beginning of data in a partition")); /* !sun */ 824 puts(_("q\tquit without saving changes"));
833 puts(_("\tc\tchange number of cylinders")); 825 puts(_("r\treturn to main menu"));
834 puts(_("\td\tprint the raw data in the partition table")); 826 puts(_("s\tchange number of sectors/track"));
835 puts(_("\te\tlist extended partitions")); /* !sun */ 827 puts(_("v\tverify the partition table"));
836 puts(_("\tg\tcreate an IRIX (SGI) partition table"));/* sgi */ 828 puts(_("w\twrite table to disk and exit"));
837 puts(_("\th\tchange number of heads")); 829 } else {
838 puts(_("\tm\tprint this menu")); 830 puts(_("b\tmove beginning of data in a partition")); /* !sun */
839 puts(_("\tp\tprint the partition table")); 831 puts(_("c\tchange number of cylinders"));
840 puts(_("\tq\tquit without saving changes")); 832 puts(_("d\tprint the raw data in the partition table"));
841 puts(_("\tr\treturn to main menu")); 833 puts(_("e\tlist extended partitions")); /* !sun */
842 puts(_("\ts\tchange number of sectors/track")); 834 puts(_("f\tfix partition order")); /* !sun, !aix, !sgi */
843 puts(_("\tv\tverify the partition table"));
844 puts(_("\tw\twrite table to disk and exit"));
845 } else {
846 puts(_("Command action"));
847 puts(_("\tb\tmove beginning of data in a partition")); /* !sun */
848 puts(_("\tc\tchange number of cylinders"));
849 puts(_("\td\tprint the raw data in the partition table"));
850 puts(_("\te\tlist extended partitions")); /* !sun */
851 puts(_("\tf\tfix partition order")); /* !sun, !aix, !sgi */
852#if ENABLE_FEATURE_SGI_LABEL 835#if ENABLE_FEATURE_SGI_LABEL
853 puts(_("\tg\tcreate an IRIX (SGI) partition table"));/* sgi */ 836 puts(_("g\tcreate an IRIX (SGI) partition table"));/* sgi */
854#endif 837#endif
855 puts(_("\th\tchange number of heads")); 838 puts(_("h\tchange number of heads"));
856 puts(_("\tm\tprint this menu")); 839 puts(_("p\tprint the partition table"));
857 puts(_("\tp\tprint the partition table")); 840 puts(_("q\tquit without saving changes"));
858 puts(_("\tq\tquit without saving changes")); 841 puts(_("r\treturn to main menu"));
859 puts(_("\tr\treturn to main menu")); 842 puts(_("s\tchange number of sectors/track"));
860 puts(_("\ts\tchange number of sectors/track")); 843 puts(_("v\tverify the partition table"));
861 puts(_("\tv\tverify the partition table")); 844 puts(_("w\twrite table to disk and exit"));
862 puts(_("\tw\twrite table to disk and exit"));
863 } 845 }
864} 846}
865#endif /* ADVANCED mode */ 847#endif /* ADVANCED mode */
@@ -883,7 +865,7 @@ static const char *partition_type(unsigned char type)
883 const struct systypes *types = get_sys_types(); 865 const struct systypes *types = get_sys_types();
884 866
885 for (i = 0; types[i].name; i++) 867 for (i = 0; types[i].name; i++)
886 if ((unsigned char )types[i].name[0] == type) 868 if ((unsigned char)types[i].name[0] == type)
887 return types[i].name + 1; 869 return types[i].name + 1;
888 870
889 return _("Unknown"); 871 return _("Unknown");
@@ -899,24 +881,29 @@ get_sysid(int i)
899 ptes[i].part_table->sys_ind); 881 ptes[i].part_table->sys_ind);
900} 882}
901 883
902void list_types(const struct systypes *sys) 884static void list_types(const struct systypes *sys)
903{ 885{
904 unsigned last[4], done = 0, next = 0, size; 886 enum { COLS = 3 };
887
888 unsigned last[COLS];
889 unsigned done, next, size;
905 int i; 890 int i;
906 891
907 for (i = 0; sys[i].name; i++); 892 for (size = 0; sys[size].name; size++) /* */;
908 size = i;
909 893
910 for (i = 3; i >= 0; i--) 894 done = 0;
911 last[3 - i] = done += (size + i - done) / (i + 1); 895 for (i = COLS-1; i >= 0; i--) {
912 i = done = 0; 896 done += (size + i - done) / (i + 1);
897 last[COLS-1 - i] = done;
898 }
913 899
900 i = done = next = 0;
914 do { 901 do {
915 printf("%c%2x %-15.15s", i ? ' ' : '\n', 902 printf("%c%2x %-22.22s", i ? ' ' : '\n',
916 (unsigned char)sys[next].name[0], 903 (unsigned char)sys[next].name[0],
917 partition_type((unsigned char)sys[next].name[0])); 904 sys[next].name + 1);
918 next = last[i++] + done; 905 next = last[i++] + done;
919 if (i > 3 || next >= last[i]) { 906 if (i >= COLS || next >= last[i]) {
920 i = 0; 907 i = 0;
921 next = ++done; 908 next = ++done;
922 } 909 }
@@ -2415,10 +2402,12 @@ new_partition(void)
2415 "an extended partition first\n")); 2402 "an extended partition first\n"));
2416 } else { 2403 } else {
2417 char c, line[LINE_LENGTH]; 2404 char c, line[LINE_LENGTH];
2418 snprintf(line, sizeof(line), "%s\n %s\n p primary " 2405 snprintf(line, sizeof(line),
2419 "partition (1-4)\n", 2406 "Command action\n"
2420 "Command action", (extended_offset ? 2407 " %s\n"
2421 "l logical (5 or over)" : "e extended")); 2408 " p primary partition (1-4)\n",
2409 (extended_offset ?
2410 "l logical (5 or over)" : "e extended"));
2422 while (1) { 2411 while (1) {
2423 c = read_nonempty(line); 2412 c = read_nonempty(line);
2424 if (c == 'p' || c == 'P') { 2413 if (c == 'p' || c == 'P') {