Home / Alt manpages / pamfile(1)

  • pamfile(1)
  • User command
  • linux

Inspect Netpbm Images Reliably with pamfile

pamfile tells you what a PAM or PNM image actually is before a script trusts a file that turns out to be the wrong format or size. You will finish able to print dimensions for a script, count images in a file, and dodge the pipe-reading trap. The examples use pamfile from Netpbm 11.5.2, installed here as Debian package netpbm 2:11.05.02-1.1build1.

Allow about ten minutes. You need a shell and a readable PBM, PGM, PPM or PAM file. These commands only inspect image data: no sudo, no modifying the input, no touching system configuration.

1. Confirm the installed command

Check which binary your shell will run and record the package version. This matters the day a script depends on output introduced by a newer Netpbm release:

$ command -v pamfile
/usr/bin/pamfile
$ pamfile --version
pamfile: Using libnetpbm from Netpbm Version: Netpbm 11.5.2
$ dpkg-query -W -f='${Package} ${Version}\n' netpbm
netpbm 2:11.05.02-1.1build1

The installed manual is the contract for this machine. It permits minimum unique option abbreviations and double hyphens, but full option names read clearer in scripts. If pamfile is missing, install Netpbm through your normal package-management process rather than copying a binary from an unrelated host.

Checkpoint

You should have a path for pamfile, a Netpbm version, and an input file you can read.

2. Read the normal human-oriented description

Run pamfile with the input path as the final argument. This example uses a sample PPM shipped with the installed package:

$ pamfile /usr/share/netpbm/pcxstd.ppm
/usr/share/netpbm/pcxstd.ppm:    PPM plain, 16 by 1  maxval 255

The wording is for people, not parsers: file, format, subformat, width, height and maximum sample value. PAM and PNM are families of formats, so a result like PPM tells you far more than a generic "it's an image".

pamfile normally reads only the first image header. That is fast, but it does not prove that every later image in a multi-image stream is readable.

3. Get dimensions for a script

Use -size when you need exactly two whitespace-separated values, width then height:

$ pamfile -size /usr/share/netpbm/pcxstd.ppm
16 1

This output deliberately drops the file name. Convenient for one input, unsafe for several files or several images, because you cannot map each pair back to its source. Check the exit status as well as the values in a script:

$ dimensions=$(pamfile -size /usr/share/netpbm/pcxstd.ppm) && printf 'dimensions: %s\n' "$dimensions"
dimensions: 16 1

Keep the command substitution separate from any later numeric validation. A successful pamfile command says the inspection completed; it says nothing about whether a 16 by 1 image is fit for the next step.

4. Use machine output when filenames matter

-machine emits one line per image and keeps the filename attached to the metadata: format, subformat, width, height, depth, maxval and tuple type.

$ pamfile -machine /usr/share/netpbm/pcxstd.ppm
/usr/share/netpbm/pcxstd.ppm: PPM PLAIN 16 1 3 255 RGB

For multiple inputs, each line still starts with its source:

$ pamfile -machine /usr/share/netpbm/pcxstd.ppm /usr/share/netpbm/pcxstd.ppm
/usr/share/netpbm/pcxstd.ppm: PPM PLAIN 16 1 3 255 RGB
/usr/share/netpbm/pcxstd.ppm: PPM PLAIN 16 1 3 255 RGB

Do not parse the human-oriented output by guessing where a phrase ends. If a program needs stable fields, use -machine and note the Netpbm version you tested against. Quote filenames from external input, and prefer separate arguments over building a shell string by hand.

5. Count all images without printing their metadata

Use -count when the only question is how many images are present:

$ pamfile -count /usr/share/netpbm/pcxstd.ppm
/usr/share/netpbm/pcxstd.ppm:    1 images

-count reads every image, unlike the default header-only inspection, and can take longer on a large stream. -count, -machine and -size are alternatives: use at most one. Combine them and pamfile rejects the combination outright rather than picking a priority for you.

6. Handle pipes and comments deliberately

Without an option, pamfile may stop after the first header, and on a pipe the process feeding it can expect its whole stream consumed regardless. Add -allimages whenever the source is a pipe, even if you believe it holds one image:

$ cat /usr/share/netpbm/pcxstd.ppm | pamfile -allimages -
-:    Image 0:    PPM plain, 16 by 1  maxval 255

The final - names standard input. -allimages also reports every image in a regular multi-image file, and has no effect combined with -count, which already reads the complete input.

If PAM header comments matter, add -comments:

$ pamfile -comments /usr/share/netpbm/pcxstd.ppm
/usr/share/netpbm/pcxstd.ppm:    PPM plain, 16 by 1  maxval 255
Comments:

For PBM, PGM and PPM files, pamfile reports no comments even if comment-like header material exists. The option is really only useful for PAM images.

7. Diagnose failures without changing the file

If pamfile cannot open an input, check the path and permissions first:

$ ls -l /path/to/image.pam
$ test -r /path/to/image.pam && echo readable
readable

If the file is readable but the format is rejected, keep the original and test a known-good Netpbm file instead. Warning: do not rename a file to make its extension look like a PPM, and do not run an image inspector as root. pamfile reads the format data, not the filename suffix, and elevated privileges fix nothing about malformed image data.

When a pipeline feeds pamfile, check both commands' behaviour. A producer that gets a broken pipe can report an error if pamfile only reads a header; retry with -allimages and follow the producer's documented error handling. The option consumes input, it does not make corrupt pixels valid.

Done means

  • Version confirmed: you know the installed Netpbm version and which pamfile binary runs.
  • Reading style matches the need: a human description is not confused with a machine interface.
  • Right flag for the job: -size for one simple dimensions result, -machine when filenames or metadata must survive.
  • Full stream handled when needed: -count or -allimages used when the complete input has to be consumed.
  • Nothing touched: the source image and system configuration are unchanged.