system/dd: align nshlib/cmd_dd

cmd_dd:support dd can do verify

    After writing the file, compare the contents of the two files again

    Signed-off-by: anjiahao <anjiahao@xiaomi.com>

Signed-off-by: dongjiuzhu1 <dongjiuzhu1@xiaomi.com>
This commit is contained in:
dongjiuzhu1 2025-04-12 18:57:15 +08:00 • committed by Lup Yuen Lee
parent b608dd0e3f
commit 721d79fb73

View file

@ -31,6 +31,7 @@
#include <sys/types.h>
#include <sys/stat.h>
#include <debug.h>
#include <inttypes.h>
#include <stdint.h>
#include <stdbool.h>
@ -203,6 +204,75 @@ static inline int dd_outfopen(FAR const char *name, FAR struct dd_s *dd)
return OK;
}
static int dd_verify(FAR struct dd_s *dd)
{
FAR uint8_t *buffer;
unsigned sector = 0;
int ret = OK;
ret = lseek(dd->infd, dd->skip ? dd->skip * dd->sectsize : 0, SEEK_SET);
if (ret < 0)
{
fprintf(stderr, "%s: failed to infd lseek: %s\n",
g_dd, strerror(errno));
return ret;
}
dd->eof = 0;
ret = lseek(dd->outfd, 0, SEEK_SET);
if (ret < 0)
{
fprintf(stderr, "%s: failed to outfd lseek: %s\n",
g_dd, strerror(errno));
return ret;
}
buffer = malloc(dd->sectsize);
if (buffer == NULL)
{
return ERROR;
}
while (!dd->eof && sector < dd->nsectors)
{
ret = dd_read(dd);
if (ret < 0)
{
break;
}
ret = read(dd->outfd, buffer, dd->nbytes);
if (ret != dd->nbytes)
{
fprintf(stderr, "%s: failed to outfd read: %d\n",
g_dd, ret < 0 ? errno : ret);
break;
}
if (memcmp(dd->buffer, buffer, dd->nbytes) != 0)
{
char msg[32];
snprintf(msg, sizeof(msg), "infile sector %d", sector);
lib_dumpbuffer(msg, dd->buffer, dd->nbytes);
snprintf(msg, sizeof(msg), "\noutfile sector %d", sector);
lib_dumpbuffer(msg, buffer, dd->nbytes);
ret = ERROR;
break;
}
sector++;
}
if (ret < 0)
{
fprintf(stderr, "%s: failed to dd verify: %d\n",
g_dd, ret);
}
free(buffer);
return ret;
}
/****************************************************************************
* Name: print_usage
****************************************************************************/
@ -211,7 +281,7 @@ static void print_usage(void)
{
fprintf(stderr, "usage:\n");
fprintf(stderr, " %s [if=<infile>] [of=<outfile>] [bs=<sectsize>] "
"[count=<sectors>] [skip=<sectors>] [seek=<sectors>] "
"[count=<sectors>] [skip=<sectors>] [seek=<sectors>] [verify] "
"[conv=<nocreat,notrunc>]\n", g_dd);
}
@ -267,6 +337,10 @@ int main(int argc, FAR char **argv)
{
dd.seek = atoi(&argv[i][5]);
}
else if (strncmp(argv[i], "verify", 6) == 0)
{
dd.oflags |= O_RDONLY;
}
else if (strncmp(argv[i], "conv=", 5) == 0)
{
const char *cur = &argv[i][5];
@ -304,6 +378,16 @@ int main(int argc, FAR char **argv)
}
}
/* If verify enabled, infile and outfile are mandatory */
if ((dd.oflags & O_RDONLY) && (infile == NULL || outfile == NULL))
{
fprintf(stderr, "%s: invalid parameters: %s\n", g_dd,
strerror(EINVAL));
print_usage();
goto errout_with_paths;
}
/* Allocate the I/O buffer */
dd.buffer = malloc(dd.sectsize);
@ -400,6 +484,11 @@ int main(int argc, FAR char **argv)
(unsigned int)(((double)total / 1024)
/ ((double)elapsed / USEC_PER_SEC)));
if (ret == 0 && (dd.oflags & O_RDONLY) != 0)
{
ret = dd_verify(&dd);
}
errout_with_outf:
close(dd.outfd);