Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(574)

Side by Side Diff: cgpt/cmd_add.c

Issue 2719008: Nearly complete rewrite of cgpt tool. (Closed) Base URL: ssh://git@chromiumos-git//vboot_reference.git
Patch Set: Created 10 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « cgpt/cgpt_common.c ('k') | cgpt/cmd_boot.c » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "cgpt.h"
6
7 #include <getopt.h>
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <string.h>
11 #include <uuid/uuid.h>
12
13 #include "cgptlib_internal.h"
14
15 static void Usage(void)
16 {
17 printf("\nUsage: %s add [OPTIONS] DRIVE\n\n"
18 "Add, edit, or remove a partition entry.\n\n"
19 "Options:\n"
20 " -i NUM Specify partition (default is next available)\n"
21 " -b NUM Beginning sector\n"
22 " -s NUM Size in sectors\n"
23 " -t GUID Partition Type GUID\n"
24 " -u GUID Partition Unique ID\n"
25 " -l LABEL Label\n"
26 " -S NUM set Successful flag (0|1)\n"
27 " -T NUM set Tries flag (0-15)\n"
28 " -P NUM set Priority flag (0-15)\n"
29 " -A NUM set raw 64-bit attribute value\n"
30 "\n"
31 "Use the -i option to modify an existing partition.\n"
32 "The -b, -s, and -t options must be given for new partitions.\n"
33 "\n", progname);
34 PrintTypes();
35 }
36
37 int cmd_add(int argc, char *argv[]) {
38 struct drive drive;
39 int partition = 0;
40 uint64_t begin = 0;
41 uint64_t size = 0;
42 Guid type_guid;
43 Guid unique_guid;
44 char *label = 0;
45 int successful = 0;
46 int tries = 0;
47 int priority = 0;
48 uint64_t raw_value = 0;
49 int set_begin = 0;
50 int set_size = 0;
51 int set_type = 0;
52 int set_unique = 0;
53 int set_successful = 0;
54 int set_tries = 0;
55 int set_priority = 0;
56 int set_raw = 0;
57
58 int gpt_retval;
59 GptEntry *entry;
60 int index;
61
62 int c;
63 int errorcnt = 0;
64 char *e = 0;
65
66 opterr = 0; // quiet, you
67 while ((c=getopt(argc, argv, ":hi:b:s:t:u:l:S:T:P:A:")) != -1)
68 {
69 switch (c)
70 {
71 case 'i':
72 partition = (uint32_t)strtoul(optarg, &e, 0);
73 if (!*optarg || (e && *e))
74 {
75 Error("invalid argument to -%c: \"%s\"\n", c, optarg);
76 errorcnt++;
77 }
78 break;
79 case 'b':
80 set_begin = 1;
81 begin = strtoull(optarg, &e, 0);
82 if (!*optarg || (e && *e))
83 {
84 Error("invalid argument to -%c: \"%s\"\n", c, optarg);
85 errorcnt++;
86 }
87 break;
88 case 's':
89 set_size = 1;
90 size = strtoull(optarg, &e, 0);
91 if (!*optarg || (e && *e))
92 {
93 Error("invalid argument to -%c: \"%s\"\n", c, optarg);
94 errorcnt++;
95 }
96 break;
97 case 't':
98 set_type = 1;
99 if (CGPT_OK != SupportedType(optarg, &type_guid) &&
100 CGPT_OK != StrToGuid(optarg, &type_guid)) {
101 Error("invalid argument to -%c: %s\n", c, optarg);
102 errorcnt++;
103 }
104 break;
105 case 'u':
106 set_unique = 1;
107 if (CGPT_OK != StrToGuid(optarg, &unique_guid)) {
108 Error("invalid argument to -%c: %s\n", c, optarg);
109 errorcnt++;
110 }
111 break;
112 case 'l':
113 label = optarg;
114 break;
115 case 'S':
116 set_successful = 1;
117 successful = (uint32_t)strtoul(optarg, &e, 0);
118 if (!*optarg || (e && *e))
119 {
120 Error("invalid argument to -%c: \"%s\"\n", c, optarg);
121 errorcnt++;
122 }
123 if (successful < 0 || successful > 1) {
124 Error("value for -%c must be between 0 and 1", c);
125 errorcnt++;
126 }
127 break;
128 case 'T':
129 set_tries = 1;
130 tries = (uint32_t)strtoul(optarg, &e, 0);
131 if (!*optarg || (e && *e))
132 {
133 fprintf(stderr, "%s: invalid argument to -%c: \"%s\"\n",
134 progname, c, optarg);
135 errorcnt++;
136 }
137 if (tries < 0 || tries > 15) {
138 Error("value for -%c must be between 0 and 15", c);
139 errorcnt++;
140 }
141 break;
142 case 'P':
143 set_priority = 1;
144 priority = (uint32_t)strtoul(optarg, &e, 0);
145 if (!*optarg || (e && *e))
146 {
147 Error("invalid argument to -%c: \"%s\"\n", c, optarg);
148 errorcnt++;
149 }
150 if (priority < 0 || priority > 15) {
151 Error("value for -%c must be between 0 and 15", c);
152 errorcnt++;
153 }
154 break;
155 case 'A':
156 set_raw = 1;
157 raw_value = strtoull(optarg, &e, 0);
158 if (!*optarg || (e && *e))
159 {
160 Error("invalid argument to -%c: \"%s\"\n", c, optarg);
161 errorcnt++;
162 }
163 break;
164
165 case 'h':
166 Usage();
167 return CGPT_OK;
168 case '?':
169 Error("unrecognized option: -%c\n", optopt);
170 errorcnt++;
171 break;
172 case ':':
173 Error("missing argument to -%c\n", optopt);
174 errorcnt++;
175 break;
176 default:
177 errorcnt++;
178 break;
179 }
180 }
181 if (errorcnt)
182 {
183 Usage();
184 return CGPT_FAILED;
185 }
186
187 if (optind >= argc) {
188 Error("missing drive argument\n");
189 return CGPT_FAILED;
190 }
191
192 if (CGPT_OK != DriveOpen(argv[optind], &drive))
193 return CGPT_FAILED;
194
195 if (GPT_SUCCESS != (gpt_retval = GptSanityCheck(&drive.gpt))) {
196 Error("GptSanityCheck() returned %d: %s\n",
197 gpt_retval, GptError(gpt_retval));
198 return CGPT_FAILED;
199 }
200
201 int max_part = GetNumberOfEntries(&drive.gpt);
202 if (partition) {
203 if (partition > max_part) {
204 Error("invalid partition number: %d\n", partition);
205 goto bad;
206 }
207 index = partition - 1;
208 entry = GetEntry(&drive.gpt, PRIMARY, index);
209 } else {
210 // find next empty partition
211 for (index = 0; index < max_part; index++) {
212 entry = GetEntry(&drive.gpt, PRIMARY, index);
213 if (IsZero(&entry->type)) {
214 partition = index + 1;
215 break;
216 }
217 }
218 if (index >= max_part) {
219 Error("no unused partitions available\n");
220 goto bad;
221 }
222 }
223
224 // New partitions must specify type, begin, and size.
225 if (IsZero(&entry->type)) {
226 if (!set_begin || !set_size || !set_type) {
227 Error("-t, -b, and -s options are required for new partitions\n");
228 goto bad;
229 }
230 if (IsZero(&type_guid)) {
231 Error("New partitions must have a type other than \"unused\"\n");
232 goto bad;
233 }
234 if (!set_unique)
235 uuid_generate((uint8_t *)&entry->unique);
236 }
237
238 if (set_begin)
239 entry->starting_lba = begin;
240 if (set_size)
241 entry->ending_lba = begin + size - 1;
242 if (set_type)
243 memcpy(&entry->type, &type_guid, sizeof(Guid));
244 if (set_unique)
245 memcpy(&entry->unique, &unique_guid, sizeof(Guid));
246 if (label) {
247 uint16_t buf[128];
248 UTF8ToUTF16((uint8_t *)label, buf);
249 memcpy(entry->name, buf, sizeof(entry->name));
250 }
251 if (set_raw) {
252 entry->attributes = raw_value;
253 } else {
254 if (set_successful)
255 SetSuccessful(&drive.gpt, PRIMARY, index, successful);
256 if (set_tries)
257 SetTries(&drive.gpt, PRIMARY, index, tries);
258 if (set_priority)
259 SetPriority(&drive.gpt, PRIMARY, index, priority);
260 }
261
262 RepairEntries(&drive.gpt, MASK_PRIMARY);
263 RepairHeader(&drive.gpt, MASK_PRIMARY);
264
265 drive.gpt.modified |= (GPT_MODIFIED_HEADER1 | GPT_MODIFIED_ENTRIES1 |
266 GPT_MODIFIED_HEADER2 | GPT_MODIFIED_ENTRIES2);
267 UpdateCrc(&drive.gpt);
268
269
270 // Write it all out
271 return DriveClose(&drive, 1);
272
273 bad:
274 (void) DriveClose(&drive, 0);
275 return CGPT_FAILED;
276 }
OLDNEW
« no previous file with comments | « cgpt/cgpt_common.c ('k') | cgpt/cmd_boot.c » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698