aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2010-04-06 02:31:43 +0200
committerDenys Vlasenko <vda.linux@googlemail.com>2010-04-06 02:31:43 +0200
commit5ea1de2235e75d8fd4f559c7c6cca9a2d0396094 (patch)
tree29c746ef85d67a7c9810f28118b9115e3aa615ae
parent37bc1eb5cdcaec015579241fc1f20fd03bed2d67 (diff)
downloadbusybox-w32-5ea1de2235e75d8fd4f559c7c6cca9a2d0396094.tar.gz
busybox-w32-5ea1de2235e75d8fd4f559c7c6cca9a2d0396094.tar.bz2
busybox-w32-5ea1de2235e75d8fd4f559c7c6cca9a2d0396094.zip
fdisk: code shrink without logic changes
function old new delta create_doslabel 113 110 -3 set_start_sect 8 4 -4 set_nr_sects 8 4 -4 get_start_sect 8 4 -4 get_nr_sects 8 4 -4 store4_little_endian 21 - -21 read4_little_endian 33 - -33 is_cleared_partition 84 21 -63 ------------------------------------------------------------------------------ (add/remove: 0/2 grow/shrink: 0/6 up/down: 0/-136) Total: -136 bytes Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--util-linux/fdisk.c244
1 files changed, 118 insertions, 126 deletions
diff --git a/util-linux/fdisk.c b/util-linux/fdisk.c
index 980568bc8..cb15bd267 100644
--- a/util-linux/fdisk.c
+++ b/util-linux/fdisk.c
@@ -21,6 +21,13 @@
21#endif 21#endif
22#include "libbb.h" 22#include "libbb.h"
23 23
24#if BB_LITTLE_ENDIAN
25# define inline_if_little_endian ALWAYS_INLINE
26#else
27# define inline_if_little_endian /* nothing */
28#endif
29
30
24/* Looks like someone forgot to add this to config system */ 31/* Looks like someone forgot to add this to config system */
25#ifndef ENABLE_FEATURE_FDISK_BLKSIZE 32#ifndef ENABLE_FEATURE_FDISK_BLKSIZE
26# define ENABLE_FEATURE_FDISK_BLKSIZE 0 33# define ENABLE_FEATURE_FDISK_BLKSIZE 0
@@ -181,7 +188,7 @@ struct pte {
181 sector_t offset; /* disk sector number */ 188 sector_t offset; /* disk sector number */
182 char *sectorbuffer; /* disk sector contents */ 189 char *sectorbuffer; /* disk sector contents */
183#if ENABLE_FEATURE_FDISK_WRITABLE 190#if ENABLE_FEATURE_FDISK_WRITABLE
184 char changed; /* boolean */ 191 char changed; /* boolean */
185#endif 192#endif
186}; 193};
187 194
@@ -445,27 +452,6 @@ close_dev_fd(void)
445 xmove_fd(xopen(bb_dev_null, O_RDONLY), dev_fd); 452 xmove_fd(xopen(bb_dev_null, O_RDONLY), dev_fd);
446} 453}
447 454
448#if ENABLE_FEATURE_FDISK_WRITABLE
449/* Read line; return 0 or first printable char */
450static int
451read_line(const char *prompt)
452{
453 int sz;
454
455 sz = read_line_input(prompt, line_buffer, sizeof(line_buffer), NULL);
456 if (sz <= 0)
457 exit(EXIT_SUCCESS); /* Ctrl-D or Ctrl-C */
458
459 if (line_buffer[sz-1] == '\n')
460 line_buffer[--sz] = '\0';
461
462 line_ptr = line_buffer;
463 while (*line_ptr != '\0' && (unsigned char)*line_ptr <= ' ')
464 line_ptr++;
465 return *line_ptr;
466}
467#endif
468
469/* 455/*
470 * Return partition name - uses static storage 456 * Return partition name - uses static storage
471 */ 457 */
@@ -497,30 +483,13 @@ partname(const char *dev, int pno, int lth)
497 483
498 if (lth) { 484 if (lth) {
499 snprintf(bufp, bufsiz, "%*.*s%s%-2u", 485 snprintf(bufp, bufsiz, "%*.*s%s%-2u",
500 lth-wp-2, w, dev, p, pno); 486 lth-wp-2, w, dev, p, pno);
501 } else { 487 } else {
502 snprintf(bufp, bufsiz, "%.*s%s%-2u", w, dev, p, pno); 488 snprintf(bufp, bufsiz, "%.*s%s%-2u", w, dev, p, pno);
503 } 489 }
504 return bufp; 490 return bufp;
505} 491}
506 492
507#if ENABLE_FEATURE_FDISK_WRITABLE
508static void
509set_all_unchanged(void)
510{
511 int i;
512
513 for (i = 0; i < MAXIMUM_PARTS; i++)
514 ptes[i].changed = 0;
515}
516
517static ALWAYS_INLINE void
518set_changed(int i)
519{
520 ptes[i].changed = 1;
521}
522#endif /* FEATURE_FDISK_WRITABLE */
523
524static ALWAYS_INLINE struct partition * 493static ALWAYS_INLINE struct partition *
525get_part_table(int i) 494get_part_table(int i)
526{ 495{
@@ -541,7 +510,67 @@ valid_part_table_flag(const char *mbuffer)
541 return (mbuffer[510] == 0x55 && (uint8_t)mbuffer[511] == 0xaa); 510 return (mbuffer[510] == 0x55 && (uint8_t)mbuffer[511] == 0xaa);
542} 511}
543 512
513static void fdisk_fatal(const char *why)
514{
515 if (listing) {
516 close_dev_fd();
517 longjmp(listingbuf, 1);
518 }
519 bb_error_msg_and_die(why, disk_device);
520}
521
522static void
523seek_sector(sector_t secno)
524{
525#if ENABLE_FDISK_SUPPORT_LARGE_DISKS
526 off64_t off = (off64_t)secno * sector_size;
527 if (lseek64(dev_fd, off, SEEK_SET) == (off64_t) -1)
528 fdisk_fatal(unable_to_seek);
529#else
530 uint64_t off = (uint64_t)secno * sector_size;
531 if (off > MAXINT(off_t)
532 || lseek(dev_fd, (off_t)off, SEEK_SET) == (off_t) -1
533 ) {
534 fdisk_fatal(unable_to_seek);
535 }
536#endif
537}
538
544#if ENABLE_FEATURE_FDISK_WRITABLE 539#if ENABLE_FEATURE_FDISK_WRITABLE
540/* Read line; return 0 or first printable char */
541static int
542read_line(const char *prompt)
543{
544 int sz;
545
546 sz = read_line_input(prompt, line_buffer, sizeof(line_buffer), NULL);
547 if (sz <= 0)
548 exit(EXIT_SUCCESS); /* Ctrl-D or Ctrl-C */
549
550 if (line_buffer[sz-1] == '\n')
551 line_buffer[--sz] = '\0';
552
553 line_ptr = line_buffer;
554 while (*line_ptr != '\0' && (unsigned char)*line_ptr <= ' ')
555 line_ptr++;
556 return *line_ptr;
557}
558
559static void
560set_all_unchanged(void)
561{
562 int i;
563
564 for (i = 0; i < MAXIMUM_PARTS; i++)
565 ptes[i].changed = 0;
566}
567
568static ALWAYS_INLINE void
569set_changed(int i)
570{
571 ptes[i].changed = 1;
572}
573
545static ALWAYS_INLINE void 574static ALWAYS_INLINE void
546write_part_table_flag(char *b) 575write_part_table_flag(char *b)
547{ 576{
@@ -579,48 +608,18 @@ read_hex(const char *const *sys)
579 continue; 608 continue;
580 } 609 }
581 v = bb_strtoul(line_ptr, NULL, 16); 610 v = bb_strtoul(line_ptr, NULL, 16);
582 if (v > 0xff) 611 if (v <= 0xff)
583 /* Bad input also triggers this */ 612 return v;
584 continue;
585 return v;
586 } 613 }
587} 614}
588#endif /* FEATURE_FDISK_WRITABLE */
589
590static void fdisk_fatal(const char *why)
591{
592 if (listing) {
593 close_dev_fd();
594 longjmp(listingbuf, 1);
595 }
596 bb_error_msg_and_die(why, disk_device);
597}
598 615
599static void 616static void
600seek_sector(sector_t secno)
601{
602#if ENABLE_FDISK_SUPPORT_LARGE_DISKS
603 off64_t off = (off64_t)secno * sector_size;
604 if (lseek64(dev_fd, off, SEEK_SET) == (off64_t) -1)
605 fdisk_fatal(unable_to_seek);
606#else
607 uint64_t off = (uint64_t)secno * sector_size;
608 if (off > MAXINT(off_t)
609 || lseek(dev_fd, (off_t)off, SEEK_SET) == (off_t) -1
610 ) {
611 fdisk_fatal(unable_to_seek);
612 }
613#endif
614}
615
616#if ENABLE_FEATURE_FDISK_WRITABLE
617static void
618write_sector(sector_t secno, const void *buf) 617write_sector(sector_t secno, const void *buf)
619{ 618{
620 seek_sector(secno); 619 seek_sector(secno);
621 xwrite(dev_fd, buf, sector_size); 620 xwrite(dev_fd, buf, sector_size);
622} 621}
623#endif 622#endif /* FEATURE_FDISK_WRITABLE */
624 623
625 624
626#include "fdisk_aix.c" 625#include "fdisk_aix.c"
@@ -713,40 +712,42 @@ STATIC_SUN void sun_write_table(void);
713#include "fdisk_sun.c" 712#include "fdisk_sun.c"
714 713
715 714
716#if ENABLE_FEATURE_FDISK_WRITABLE 715static inline_if_little_endian unsigned
717/* start_sect and nr_sects are stored little endian on all machines */ 716read4_little_endian(const unsigned char *cp)
718/* moreover, they are not aligned correctly */
719static void
720store4_little_endian(unsigned char *cp, unsigned val)
721{ 717{
722 cp[0] = val; 718 uint32_t v;
723 cp[1] = val >> 8; 719 move_from_unaligned32(v, cp);
724 cp[2] = val >> 16; 720 return SWAP_LE32(v);
725 cp[3] = val >> 24;
726} 721}
727#endif /* FEATURE_FDISK_WRITABLE */
728 722
729static unsigned 723static sector_t
730read4_little_endian(const unsigned char *cp) 724get_start_sect(const struct partition *p)
725{
726 return read4_little_endian(p->start4);
727}
728
729static sector_t
730get_nr_sects(const struct partition *p)
731{ 731{
732 return cp[0] + (cp[1] << 8) + (cp[2] << 16) + (cp[3] << 24); 732 return read4_little_endian(p->size4);
733} 733}
734 734
735#if ENABLE_FEATURE_FDISK_WRITABLE 735#if ENABLE_FEATURE_FDISK_WRITABLE
736static void 736/* start_sect and nr_sects are stored little endian on all machines */
737set_start_sect(struct partition *p, unsigned start_sect) 737/* moreover, they are not aligned correctly */
738static inline_if_little_endian void
739store4_little_endian(unsigned char *cp, unsigned val)
738{ 740{
739 store4_little_endian(p->start4, start_sect); 741 uint32_t v = SWAP_LE32(val);
742 move_to_unaligned32(cp, v);
740} 743}
741#endif
742 744
743static sector_t 745static void
744get_start_sect(const struct partition *p) 746set_start_sect(struct partition *p, unsigned start_sect)
745{ 747{
746 return read4_little_endian(p->start4); 748 store4_little_endian(p->start4, start_sect);
747} 749}
748 750
749#if ENABLE_FEATURE_FDISK_WRITABLE
750static void 751static void
751set_nr_sects(struct partition *p, unsigned nr_sects) 752set_nr_sects(struct partition *p, unsigned nr_sects)
752{ 753{
@@ -754,12 +755,6 @@ set_nr_sects(struct partition *p, unsigned nr_sects)
754} 755}
755#endif 756#endif
756 757
757static sector_t
758get_nr_sects(const struct partition *p)
759{
760 return read4_little_endian(p->size4);
761}
762
763/* Allocate a buffer and read a partition table sector */ 758/* Allocate a buffer and read a partition table sector */
764static void 759static void
765read_pte(struct pte *pe, sector_t offset) 760read_pte(struct pte *pe, sector_t offset)
@@ -942,7 +937,7 @@ get_sys_types(void)
942} 937}
943#else 938#else
944#define get_sys_types() i386_sys_types 939#define get_sys_types() i386_sys_types
945#endif /* FEATURE_FDISK_WRITABLE */ 940#endif
946 941
947static const char * 942static const char *
948partition_type(unsigned char type) 943partition_type(unsigned char type)
@@ -957,6 +952,24 @@ partition_type(unsigned char type)
957 return "Unknown"; 952 return "Unknown";
958} 953}
959 954
955static int
956is_cleared_partition(const struct partition *p)
957{
958 /* We consider partition "cleared" only if it has only zeros */
959 const char *cp = (const char *)p;
960 int cnt = sizeof(*p);
961 char bits = 0;
962 while (--cnt >= 0)
963 bits |= *cp++;
964 return (bits == 0);
965}
966
967static void
968clear_partition(struct partition *p)
969{
970 if (p)
971 memset(p, 0, sizeof(*p));
972}
960 973
961#if ENABLE_FEATURE_FDISK_WRITABLE 974#if ENABLE_FEATURE_FDISK_WRITABLE
962static int 975static int
@@ -998,26 +1011,8 @@ list_types(const char *const *sys)
998 } while (done < last[0]); 1011 } while (done < last[0]);
999 bb_putchar('\n'); 1012 bb_putchar('\n');
1000} 1013}
1001#endif /* FEATURE_FDISK_WRITABLE */
1002
1003static int
1004is_cleared_partition(const struct partition *p)
1005{
1006 return !(!p || p->boot_ind || p->head || p->sector || p->cyl ||
1007 p->sys_ind || p->end_head || p->end_sector || p->end_cyl ||
1008 get_start_sect(p) || get_nr_sects(p));
1009}
1010 1014
1011static void 1015static void
1012clear_partition(struct partition *p)
1013{
1014 if (!p)
1015 return;
1016 memset(p, 0, sizeof(struct partition));
1017}
1018
1019#if ENABLE_FEATURE_FDISK_WRITABLE
1020static void
1021set_partition(int i, int doext, sector_t start, sector_t stop, int sysid) 1016set_partition(int i, int doext, sector_t start, sector_t stop, int sysid)
1022{ 1017{
1023 struct partition *p; 1018 struct partition *p;
@@ -1189,26 +1184,22 @@ read_extended(int ext)
1189static void 1184static void
1190create_doslabel(void) 1185create_doslabel(void)
1191{ 1186{
1192 int i;
1193
1194 printf(msg_building_new_label, "DOS disklabel"); 1187 printf(msg_building_new_label, "DOS disklabel");
1195 1188
1196 current_label_type = LABEL_DOS; 1189 current_label_type = LABEL_DOS;
1197
1198#if ENABLE_FEATURE_OSF_LABEL 1190#if ENABLE_FEATURE_OSF_LABEL
1199 possibly_osf_label = 0; 1191 possibly_osf_label = 0;
1200#endif 1192#endif
1201 g_partitions = 4; 1193 g_partitions = 4;
1202 1194
1203 for (i = 510-64; i < 510; i++) 1195 memset(&MBRbuffer[510 - 4*16], 0, 4*16);
1204 MBRbuffer[i] = 0;
1205 write_part_table_flag(MBRbuffer); 1196 write_part_table_flag(MBRbuffer);
1206 extended_offset = 0; 1197 extended_offset = 0;
1207 set_all_unchanged(); 1198 set_all_unchanged();
1208 set_changed(0); 1199 set_changed(0);
1209 get_boot(CREATE_EMPTY_DOS); 1200 get_boot(CREATE_EMPTY_DOS);
1210} 1201}
1211#endif /* FEATURE_FDISK_WRITABLE */ 1202#endif
1212 1203
1213static void 1204static void
1214get_sectorsize(void) 1205get_sectorsize(void)
@@ -1721,9 +1712,10 @@ delete_partition(int i)
1721 ptes[i] = ptes[i+1]; 1712 ptes[i] = ptes[i+1];
1722 i++; 1713 i++;
1723 } 1714 }
1724 } else 1715 } else {
1725 /* the only logical: clear only */ 1716 /* the only logical: clear only */
1726 clear_partition(ptes[i].part_table); 1717 clear_partition(ptes[i].part_table);
1718 }
1727 } 1719 }
1728} 1720}
1729 1721