Page MenuHomeFreeBSD

D21441.id61892.diff
No OneTemporary

D21441.id61892.diff

Index: bin/dd/args.c
===================================================================
--- bin/dd/args.c
+++ bin/dd/args.c
@@ -57,6 +57,7 @@
static int c_arg(const void *, const void *);
static int c_conv(const void *, const void *);
+static int c_iflag(const void *, const void *);
static int c_oflag(const void *, const void *);
static void f_bs(char *);
static void f_cbs(char *);
@@ -66,6 +67,7 @@
static void f_fillchar(char *);
static void f_ibs(char *);
static void f_if(char *);
+static void f_iflag(char *);
static void f_obs(char *);
static void f_of(char *);
static void f_oflag(char *);
@@ -89,6 +91,7 @@
{ "fillchar", f_fillchar, C_FILL, C_FILL },
{ "ibs", f_ibs, C_IBS, C_BS|C_IBS },
{ "if", f_if, C_IF, C_IF },
+ { "iflag", f_iflag, 0, 0 },
{ "iseek", f_skip, C_SKIP, C_SKIP },
{ "obs", f_obs, C_OBS, C_BS|C_OBS },
{ "of", f_of, C_OF, C_OF },
@@ -259,6 +262,38 @@
in.name = arg;
}
+static const struct iflag {
+ const char *name;
+ uint64_t set, noset;
+} ilist[] = {
+ { "fullblock", C_IFULLBLOCK, C_SYNC },
+};
+
+static void
+f_iflag(char *arg)
+{
+ struct iflag *ip, tmp;
+
+ while (arg != NULL) {
+ tmp.name = strsep(&arg, ",");
+ ip = bsearch(&tmp, ilist, nitems(ilist), sizeof(struct iflag),
+ c_iflag);
+ if (ip == NULL)
+ errx(1, "unknown iflag %s", tmp.name);
+ if (ddflags & ip->noset)
+ errx(1, "%s: illegal conversion combination", tmp.name);
+ ddflags |= ip->set;
+ }
+}
+
+static int
+c_iflag(const void *a, const void *b)
+{
+
+ return (strcmp(((const struct iflag *)a)->name,
+ ((const struct iflag *)b)->name));
+}
+
static void
f_obs(char *arg)
{
@@ -339,7 +374,7 @@
{ "parset", C_PARSET, C_PARODD|C_PAREVEN|C_PARNONE, NULL},
{ "sparse", C_SPARSE, 0, NULL },
{ "swab", C_SWAB, 0, NULL },
- { "sync", C_SYNC, 0, NULL },
+ { "sync", C_SYNC, C_IFULLBLOCK, NULL },
{ "ucase", C_UCASE, C_LCASE, NULL },
{ "unblock", C_UNBLOCK, C_BLOCK, NULL },
};
Index: bin/dd/dd.h
===================================================================
--- bin/dd/dd.h
+++ bin/dd/dd.h
@@ -104,6 +104,7 @@
#define C_FSYNC 0x0000000080000000ULL
#define C_FDATASYNC 0x0000000100000000ULL
#define C_OFSYNC 0x0000000200000000ULL
+#define C_IFULLBLOCK 0x0000000400000000ULL
#define C_PARITY (C_PAREVEN | C_PARODD | C_PARNONE | C_PARSET)
Index: bin/dd/dd.1
===================================================================
--- bin/dd/dd.1
+++ bin/dd/dd.1
@@ -102,6 +102,21 @@
Read input from
.Ar file
instead of the standard input.
+.It Cm iflag Ns = Ns Ar value Ns Op , Ns Ar value ...
+Where
+.Cm value
+is one of the symbols from the following list.
+.Bl -tag -width "fullblock"
+.It Cm fullblock
+Reading from the input file may not obtain a full block. When a read returns
+short, continue reading to fill the block. Without this flag,
+.Cm count
+limits the number of times
+.Xr read 2
+is called on the input rather than the number of blocks copied in full.
+May not be combined with
+.Cm conv=sync .
+.El
.It Cm iseek Ns = Ns Ar n
Seek on the input file
.Ar n
Index: bin/dd/dd.c
===================================================================
--- bin/dd/dd.c
+++ bin/dd/dd.c
@@ -408,13 +408,15 @@
memset(in.dbp, 0, in.dbsz);
}
- n = read(in.fd, in.dbp, in.dbsz);
- if (n == 0) {
- in.dbrcnt = 0;
+ in.dbrcnt = 0;
+fill:
+ n = read(in.fd, in.dbp + in.dbrcnt, in.dbsz - in.dbrcnt);
+
+ /* EOF */
+ if (n == 0 && in.dbrcnt == 0)
return;
- }
- /* Read error. */
+ /* Read error */
if (n == -1) {
/*
* If noerror not specified, die. POSIX requires that
@@ -440,23 +442,26 @@
continue;
/* Read errors count as full blocks. */
- in.dbcnt += in.dbrcnt = in.dbsz;
- ++st.in_full;
+ n = in.dbsz;
+ }
- /* Handle full input blocks. */
- } else if ((size_t)n == (size_t)in.dbsz) {
- in.dbcnt += in.dbrcnt = n;
- ++st.in_full;
+ /* If conv=sync, use the entire block. */
+ if (ddflags & C_SYNC)
+ n = in.dbsz;
- /* Handle partial input blocks. */
- } else {
- /* If sync, use the entire block. */
- if (ddflags & C_SYNC)
- in.dbcnt += in.dbrcnt = in.dbsz;
- else
- in.dbcnt += in.dbrcnt = n;
+ /* Count the bytes read for this block. */
+ in.dbrcnt += n;
+
+ /* Count the number of full and partial blocks. */
+ if (in.dbrcnt == in.dbsz)
+ ++st.in_full;
+ else if (ddflags & C_IFULLBLOCK && n != 0)
+ goto fill; /* these don't count */
+ else
++st.in_part;
- }
+
+ /* Count the total bytes read for this file. */
+ in.dbcnt += in.dbrcnt;
/*
* POSIX states that if bs is set and no other conversions
@@ -478,6 +483,7 @@
swapbytes(in.dbp, (size_t)n);
}
+ /* Advance to the next block. */
in.dbp += in.dbrcnt;
(*cfunc)();
if (need_summary)

File Metadata

Mime Type
text/plain
Expires
Wed, Mar 18, 9:16 PM (11 h, 18 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
29926849
Default Alt Text
D21441.id61892.diff (4 KB)

Event Timeline