I just ran across the following bash construct, I understand this is called compound-list and that those three cat commands are executed in a subshell environment, what I do not get is how the pipes fit in there and more generally, how it works. I would really appreciate a step by step explanation.

It is part of a binary image generation script so I kindof know alreayd what it does, what I do not get is how it gets there:

export DD="dd status=noxfer bs=1k iflag=fullblock"
    cat $DIR/file1 /dev/zero | $DD count=128
    cat $DIR/file2 /dev/zero | $DD count=128
    cat $DIR/file3 /dev/zero
) | $DD of=$OUT_FILE count=$SIZE

Some bash guru out there can help me?


migrated from serverfault.com Oct 5 '16 at 19:06

This question came from our site for system and network administrators.


It looks like it is trying to concatenate all three files into one with padding. The first cat gets the file plus /dev/zero, padded to 128 bytes. Same with the second, and the third is just cat'ed directly (with /dev/zero also). Then the pipe takes the output of all three and saves to a file of size $SIZE. This creates a single file with file1 in a 128 byte block, then file2 in another 128 byte block, then file3 filling the rest with padding.

  • This would also be my reading of this. But you were faster than me ;-) – pacey Sep 28 '16 at 12:03
  • They are padded to 128KB. Note the bs=1k parameter. – Eric Sep 29 '16 at 10:48
  • Yes, you are right, I missed that. The other options were in my mind because I specifically looked them up, but because I use that one all the time it kind of slipped. – lsd Sep 29 '16 at 11:58

The command cat concatenates all the files that are given as arguments.

cat $DIR/file1 /dev/zero

concatenates file1 with zero(s) from /dev/zero until the following command is willing to read. The next command (in the pipe |) is $DD count=128, which means that 128 1k blocks (note the bs=1k in the definition of the variable) will be read and written to stdout.

In short: read file1 and pad it with zeros up to 128k.

The next command line is quite similar:

read file2 and pad it with zeros up to 128k.

And the last line just reads the file3 (with no padding).

Then, all that (inside parentheses) concatenated stream is given back to dd to write to $OUT_FILE up to $SIZE kbytes.

In short:

read all from file1 and pad with zeros up to 128k.
read all from file2 and pad with zeros up to 128k.
read all from file3.


Write all that was read to `$OUT_FILE` up to `$SIZE` kBytes.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy