Yalantis/uCrop · error · CImgIOException

load_pnm(): WIDTH and HEIGHT fields undefined in file '%s'.

Error message

load_pnm(): WIDTH and HEIGHT fields undefined in file '%s'.

What it means

After reading the PNM magic number, load_pnm() reads the next non-comment line and parses WIDTH, HEIGHT (and optionally DEPTH and COLORMAX) fields. If fewer than 2 unsigned integers are found (cimg_sscanf returns <2), the header is incomplete and the library throws CImgIOException.

Source

Thrown at ucrop/src/main/jni/CImg.h:57580

                                    cimg_instance);

      std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
      unsigned int ppm_type, W, H, D = 1, colormax = 255;
      CImg<charT> item(16384,1,1,1,0);
      int err, rval, gval, bval;
      const longT cimg_iobuffer = (longT)24*1024*1024;
      while ((err=std::fscanf(nfile,"%16383[^\n]",item.data()))!=EOF && (*item=='#' || !err)) std::fgetc(nfile);
      if (cimg_sscanf(item," P%u",&ppm_type)!=1) {
        if (!file) cimg::fclose(nfile);
        throw CImgIOException(_cimg_instance
                              "load_pnm(): PNM header not found in file '%s'.",
                              cimg_instance,
                              filename?filename:"(FILE*)");
      }
      while ((err=std::fscanf(nfile," %16383[^\n]",item.data()))!=EOF && (*item=='#' || !err)) std::fgetc(nfile);
      if ((err=cimg_sscanf(item," %u %u %u %u",&W,&H,&D,&colormax))<2) {
        if (!file) cimg::fclose(nfile);
        throw CImgIOException(_cimg_instance
                              "load_pnm(): WIDTH and HEIGHT fields undefined in file '%s'.",
                              cimg_instance,
                              filename?filename:"(FILE*)");
      }
      if (ppm_type!=1 && ppm_type!=4) {
        if (err==2 || (err==3 && (ppm_type==5 || ppm_type==7 || ppm_type==8 || ppm_type==9))) {
          while ((err=std::fscanf(nfile," %16383[^\n]",item.data()))!=EOF && (*item=='#' || !err)) std::fgetc(nfile);
          if (cimg_sscanf(item,"%u",&colormax)!=1)
            cimg::warn(_cimg_instance
                       "load_pnm(): COLORMAX field is undefined in file '%s'.",
                       cimg_instance,
                       filename?filename:"(FILE*)");
        } else { colormax = D; D = 1; }
      }
      std::fgetc(nfile);

      if (filename) { // Check that dimensions specified in file does not exceed the buffer dimension
        const cimg_int64 siz = cimg::fsize(filename);

View on GitHub (pinned to f788b534b4)

Solutions

  1. Open the file and confirm the second header line contains two or more integers (e.g. '640 480').
  2. Fix the generating code/exporter to emit 'width height' after the magic number.
  3. Re-export the image with a standard tool (`convert in.png out.pnm`) to regenerate a valid header.
  4. Check the file was fully written (compare size against expected dimensions); re-download if truncated.
  5. Catch CImgIOException around load_pnm and fall back to another decoder.

Example fix

// before
f << "P6\n";              // header incomplete
// after
f << "P6\n" << width << " " << height << "\n255\n";
Defensive patterns

Strategy: validation

Validate before calling

bool pnmHeaderComplete(const char* path) {
  std::ifstream f(path);
  std::string line1, line2;
  std::getline(f, line1); std::getline(f, line2);
  int a=0, b=0;
  return std::sscanf(line2.c_str(), "%d %d", &a, &b) == 2;
}

Type guard

bool hasTwoInts(const std::string& s) {
  int a, b;
  return std::sscanf(s.c_str(), " %d %d", &a, &b) == 2;
}

Try / catch

try {
  img.load_pnm(path);
} catch (cimg_library::CImgIOException& e) {
  std::cerr << "Malformed PNM header: " << e.what() << "\n";
}

Prevention

When it happens

Trigger: load_pnm() on a file with a valid 'P<digit>' magic line but missing or malformed width/height fields: header truncated after the magic number, non-numeric text where dimensions should be, extra comment lines not starting with '#' breaking the parser, or a file containing only 'P6'.

Common situations: Hand-written PNM generators that forgot the dimension line; truncation during network transfer or interrupted write; template files with placeholders like 'W H' left unsubstituted.

Understand the failure class

Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.

Related errors


AI-assisted analysis of Yalantis/uCrop@f788b534b4 (2026-09-08). Data as JSON: /api/errors/bd688dd256ed2a34. Report an issue: GitHub.