Yalantis/uCrop · error · CImgArgumentException

insert(): Invalid insertion request of specified image (%u,%

Error message

insert(): Invalid insertion request of specified image (%u,%u,%u,%u,%p) at position %u.

What it means

CImgList<T>::insert(img, pos, is_shared) validates the insertion position: the normalized position npos (= list width when pos==~0U, i.e. "append") must satisfy npos <= _width. Passing a pos greater than the current list size throws CImgArgumentException "insert(): Invalid insertion request ... at position %u" (ucrop/src/main/jni/CImg.h:65754), printing the image's dimensions and pointer for diagnosis.

Source

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

    //@}
    //---------------------------
    //
    //! \name List Manipulation
    //@{
    //---------------------------

    //! Insert a copy of the image \c img into the current image list, at position \c pos.
    /**
        \param img Image to insert a copy to the list.
        \param pos Index of the insertion.
        \param is_shared Tells if the inserted image is a shared copy of \c img or not.
    **/
    template<typename t>
    CImgList<T>& insert(const CImg<t>& img, const unsigned int pos=~0U, const bool is_shared=false) {
      const unsigned int npos = pos==~0U?_width:pos;
      if (npos>_width)
        throw CImgArgumentException(_cimglist_instance
                                    "insert(): Invalid insertion request of specified image (%u,%u,%u,%u,%p) "
                                    "at position %u.",
                                    cimglist_instance,
                                    img._width,img._height,img._depth,img._spectrum,img._data,npos);
      if (is_shared)
        throw CImgArgumentException(_cimglist_instance
                                    "insert(): Invalid insertion request of specified shared image "
                                    "CImg<%s>(%u,%u,%u,%u,%p) at position %u (pixel types are different).",
                                    cimglist_instance,
                                    img.pixel_type(),img._width,img._height,img._depth,img._spectrum,img._data,npos);

      CImg<T> *const new_data = (++_width>_allocated_width)?new CImg<T>[_allocated_width?(_allocated_width<<=1):
                                                                        (_allocated_width=16)]:0;
      if (!_data) { // Insert new element into empty list
        _data = new_data;
        *_data = img;
      } else {
        if (new_data) { // Insert with re-allocation

View on GitHub (pinned to f788b534b4)

Solutions

  1. Clamp the position: use pos = std::min(pos, (unsigned)list.size()) or pass the default ~0U to append.
  2. Recompute list.size() immediately before insert() rather than caching it across mutations.
  3. Reject negative/oversized user input before converting to the unsigned pos parameter.
  4. Use push_back-equivalent behavior (insert with default pos) when order does not matter.

Example fix

// before
const unsigned int pos = computedIndex; // may exceed size
list.insert(img, pos);

// after
unsigned int pos = computedIndex;
if (pos > list.size()) pos = list.size(); // clamp; ~0U appends
list.insert(img, pos);
Defensive patterns

Strategy: validation

Validate before calling

unsigned int npos = (pos == ~0U) ? list.size() : pos; if (pos != ~0U && pos > list.size()) { pos = list.size(); /* clamp or report error */ }

Type guard

static inline bool validInsertPos(const CImgList<T>& l, unsigned int pos) { return pos == ~0U || pos <= l.size(); }

Try / catch

try { list.insert(img, pos); } catch (CImgArgumentException& e) { /* clamp pos to list.size() and retry, or report */ }

Prevention

When it happens

Trigger: Calling insert(img, pos) with pos > list.size() (e.g. inserting at index 5 into a 3-element list); computing a position from an off-by-one loop or from a stale size captured before removals; passing a negative int that wraps to a huge unsigned value.

Common situations: Building lists by inserting at computed indices after prior inserts/removes changed the size; porting code that used signed indices; loop counters exceeding the list length; GUI code inserting at a selection index that no longer exists after deletion.

Understand the failure class

Background: "value must be between 0 and 1" / "out of range" / "must not be negative" errors: fixing range-validation failures across open-source libraries — this error's family across 42 libraries.

Related errors


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