2007/10/3, Kazuo TAKADA <[EMAIL PROTECTED]>:
>
> Hi,
>
> If the dd command fails in a sequence of copying, it always returns
> EXIT_SUCCESS. So, I can't judge whether the command had succeeded or
> failed.
>
> Its behavior doesn't conform to POSIX.
>
> POSIX 1003.1:
> http://www.opengroup.org/onlinepubs/009695399/utilities/dd.html
> | EXIT STATUS
> | The following exit values shall be returned:
> |
> | 0
> | The input file was copied successfully.
> | >0
> | An error occurred.
>
> For example, copy some data to a small size device repeatly.
>
> --------------------------------------------------
> (with a root account)
> # ./busybox dd if=/dev/zero of=/dev/ram
> dd: writing '/dev/ram': No space left on device
> 32769+0 records in
> 32768+0 records out
> # echo $?
> 0 <= should be failed!!
>
> # ./busybox dd if=/dev/zero of=/dev/ram count=1
> 1+0 records in
> 1+0 records out
> # echo $?
> 0
>
> # /bin/dd if=/dev/zero of=/dev/ram <= GNU's one
> dd: writing to `/dev/ram': No space left on device
> 32769+0 records in
> 32768+0 records out
> # echo $?
> 1
> --------------------------------------------------
>
> The old busybox-1.2.2.1 returns EXIT_FAILURE. It is the version that
> dd had not reconstructed yet.
>
> Can you accept the patch below?
> write_and_stats() is the function which returns a bool value.
>
> ----------------------------------------------------------------------
> --- coreutils/dd.c.orig 2007-09-03 20:48:39.000000000 +0900
> +++ coreutils/dd.c 2007-10-03 10:31:50.000000000 +0900
> @@ -106,7 +106,7 @@
> #endif
> };
> size_t ibs = 512, obs = 512;
> - ssize_t n, w;
> + ssize_t n, w = 0;
> char *ibuf, *obuf;
> /* And these are all zeroed at once! */
> struct {
> @@ -303,13 +303,17 @@
> tmp += d;
> oc += d;
> if (oc == obs) {
> - if (write_and_stats(ofd, obuf,
> obs, obs, outfile))
> + if (write_and_stats(ofd, obuf,
> obs, obs, outfile)) {
> + w = -1;
> goto out_status;
> + }
> oc = 0;
> }
> }
> - } else if (write_and_stats(ofd, ibuf, n, obs, outfile))
> + } else if (write_and_stats(ofd, ibuf, n, obs, outfile)) {
> + w = -1;
> goto out_status;
> + }
> }
>
> if (ENABLE_FEATURE_DD_IBS_OBS && oc) {
> @@ -330,5 +334,5 @@
> out_status:
> dd_output_status(0);
>
> - return EXIT_SUCCESS;
> + return (w >= 0 ? EXIT_SUCCESS : EXIT_FAILURE);
> }
> ----------------------------------------------------------------------
It may be faster to do
if ((w = write_and_stats(...)))
goto out_status;
and
return w;
because write_and_stats returns 1 on failure. You can even tweak
it to return either EXIT_SUCCESS or EXIT_FAILURE and change the
if to:
if ((w = write_and_stats(...)) == EXIT_SUCCESS)
goto out_status;
(which is the same but symbolically different).
Loïc
_______________________________________________
busybox mailing list
[email protected]
http://busybox.net/cgi-bin/mailman/listinfo/busybox