Skip to content

Commit 8e638e4

Browse files
committed
Add options for logical start and end disk blocks.
1 parent 9fa7ba3 commit 8e638e4

File tree

1 file changed

+58
-8
lines changed

1 file changed

+58
-8
lines changed

hdrecover.c

Lines changed: 58 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,8 @@
3636
#include <sys/ioctl.h>
3737
#include <linux/fs.h>
3838

39+
const char *program_name;
40+
3941
int badblocks = 0;
4042
int recovered = 0;
4143
int destroyed = 0;
@@ -46,7 +48,6 @@ unsigned int phys_block_size = 0;
4648
char *buf = NULL;
4749

4850
int fd = 0;
49-
int randfd = 0;
5051

5152
int64_t length = 0;
5253

@@ -146,6 +147,13 @@ int correctsector(int64_t sectornum)
146147
return 0;
147148
}
148149

150+
void usage()
151+
{
152+
fprintf(stderr, "Usage: %s [-s <logical start block>] [-e <logical end block>] <block device>\n",
153+
program_name);
154+
exit(EXIT_FAILURE);
155+
}
156+
149157
int main(int argc, char **argv, char **envp)
150158
{
151159
printf(PACKAGE " version " VERSION "\n");
@@ -157,13 +165,31 @@ int main(int argc, char **argv, char **envp)
157165
fprintf(stderr, "Exiting\n");
158166
return 1;
159167
}
160-
if (argc != 2) {
161-
fprintf(stderr, "Usage %s <block device>\n", *argv);
162-
return 1;
168+
169+
program_name = argv[0];
170+
int64_t logical_start_block = 0;
171+
int64_t logical_end_block = 0;
172+
173+
int opt;
174+
while ((opt = getopt(argc, argv, "s:e:")) != -1) {
175+
switch (opt) {
176+
case 's':
177+
logical_start_block = atoll(optarg);
178+
break;
179+
case 'e':
180+
logical_end_block = atoll(optarg);
181+
break;
182+
default:
183+
usage();
184+
}
163185
}
164-
fd = open(argv[1], O_RDWR | O_DIRECT);
186+
187+
if (optind > argc - 1)
188+
usage();
189+
190+
fd = open(argv[optind], O_RDWR | O_DIRECT);
165191
if (fd < 0) {
166-
fprintf(stderr, "Failed to open file '%s': %s\n", argv[1], strerror(errno));
192+
fprintf(stderr, "Failed to open device '%s': %s\n", argv[optind], strerror(errno));
167193
return 1;
168194
}
169195

@@ -190,15 +216,39 @@ int main(int argc, char **argv, char **envp)
190216
}
191217
length /= phys_block_size;
192218

193-
printf("Disk is %ld sectors big\n", length);
219+
unsigned int logical_block_size = 0;
220+
if (ioctl(fd, BLKSSZGET, &logical_block_size) == -1) {
221+
fprintf(stderr, "Failed to get logical block size of device: %s\n", strerror(errno));
222+
return 1;
223+
}
224+
225+
printf("Logical sector size is %u bytes\n", logical_block_size);
226+
printf("Physical sector size is %u bytes\n", phys_block_size);
227+
printf("Disk is %ld physical sectors big\n", length);
194228

195229
time_t starttime;
196230
time(&starttime);
197231

198232
time_t lasttime;
199233
time(&lasttime);
200234

201-
int64_t sectornum = 0;
235+
int64_t sectornum = logical_start_block / (phys_block_size / logical_block_size);
236+
237+
if (logical_end_block) {
238+
int64_t new_length = logical_end_block / (phys_block_size / logical_block_size);
239+
240+
if (new_length > length) {
241+
fprintf(stderr, "Logical end block is out of range!\n");
242+
return 1;
243+
}
244+
else
245+
length = new_length;
246+
}
247+
248+
if (sectornum >= length) {
249+
fprintf(stderr, "Logical start block is out of range!\n");
250+
return 1;
251+
}
202252

203253
int blocksize = phys_block_size * 20;
204254

0 commit comments

Comments
 (0)