2 * Copyright (C) 2017 Karel Zak <kzak@redhat.com>
4 * This file may be redistributed under the terms of the
5 * GNU Lesser General Public License.
11 #include <sys/types.h>
23 static int ask_callback(struct fdisk_context
*cxt
__attribute__((__unused__
)),
24 struct fdisk_ask
*ask
,
27 switch(fdisk_ask_get_type(ask
)) {
28 case FDISK_ASKTYPE_INFO
:
29 fputs(fdisk_ask_print_get_mesg(ask
), stdout
);
32 case FDISK_ASKTYPE_WARNX
:
34 fputs(fdisk_ask_print_get_mesg(ask
), stderr
);
37 case FDISK_ASKTYPE_WARN
:
39 fputs(fdisk_ask_print_get_mesg(ask
), stderr
);
40 errno
= fdisk_ask_print_get_errno(ask
);
41 fprintf(stderr
, ": %m\n");
49 int main(int argc
, char *argv
[])
51 struct fdisk_context
*cxt
;
52 struct fdisk_partition
*pa
;
53 const char *label
= NULL
, *device
= NULL
;
55 unsigned int sectorsize
;
57 static const struct option longopts
[] = {
58 { "label", required_argument
, NULL
, 'x' },
59 { "device", required_argument
, NULL
, 'd' },
60 { "help", no_argument
, NULL
, 'h' },
64 setlocale(LC_ALL
, ""); /* just to have enable UTF8 chars */
68 while((c
= getopt_long(argc
, argv
, "x:d:h", longopts
, NULL
)) != -1) {
77 printf("%s [options] <size> ...", program_invocation_short_name
);
78 fputs(USAGE_SEPARATOR
, stdout
);
79 fputs("Make disklabel and partitions.\n", stdout
);
80 fputs(USAGE_OPTIONS
, stdout
);
81 fputs(" -x, --label <dos,gpt,...> disk label type\n", stdout
);
82 fputs(" -d, --device <path> block device\n", stdout
);
83 fputs(" -h, --help this help\n", stdout
);
84 fputs(USAGE_SEPARATOR
, stdout
);
90 errx(EXIT_FAILURE
, "no device specified");
94 cxt
= fdisk_new_context();
97 fdisk_set_ask(cxt
, ask_callback
, NULL
);
99 pa
= fdisk_new_partition();
103 if (fdisk_assign_device(cxt
, device
, 0))
104 err(EXIT_FAILURE
, "failed to assign device");
105 if (fdisk_create_disklabel(cxt
, "dos"))
106 err(EXIT_FAILURE
, "failed to create disk label");
108 sectorsize
= fdisk_get_sector_size(cxt
);
110 while (optind
< argc
) {
113 const char *str
= argv
[optind
];
116 fdisk_partition_start_follow_default(pa
, 1);
117 fdisk_partition_end_follow_default(pa
, 1);
121 size
= strtosize_or_err(argv
[optind
], "failed to parse partition size");
122 fdisk_partition_set_size(pa
, size
/ sectorsize
);
123 fdisk_partition_end_follow_default(pa
, 0);
125 } else if (*str
== '-') {
126 fdisk_partition_end_follow_default(pa
, 1);
129 if (fdisk_is_label(cxt
, DOS
)) {
130 /* For MBR we want to avoid primary/logical dialog.
131 * This is possible by explicitly specified partition
132 * number, <4 means primary, >=4 means logical.
134 fdisk_partition_partno_follow_default(pa
, 0);
135 fdisk_partition_set_partno(pa
, n
);
137 /* Make sure last primary partition is extended if user
138 * wants more than 4 partitions.
140 if (n
== 3 && optind
+ 1 < argc
) {
141 struct fdisk_parttype
*type
=
142 fdisk_label_parse_parttype(
143 fdisk_get_label(cxt
, NULL
), "05");
146 fdisk_partition_set_type(pa
, type
);
147 fdisk_unref_parttype(type
);
150 fdisk_partition_partno_follow_default(pa
, 1);
153 rc
= fdisk_add_partition(cxt
, pa
, NULL
);
156 err(EXIT_FAILURE
, "failed to add #%d partition", n
+ 1);
159 fdisk_reset_partition(pa
);
164 if (fdisk_write_disklabel(cxt
))
165 err(EXIT_FAILURE
, "failed to write disk label");
167 fdisk_deassign_device(cxt
, 1);
168 fdisk_unref_context(cxt
);
169 fdisk_unref_partition(pa
);