Skip to content

Panic in unsharpen() on zero-dimension image #3028

Description

@MinghuaWang

Describe the bug

imageops::unsharpen() panics with "Option::unwrap() on a None value" when called on an image with zero width or zero height.

Panic info:

thread 'main' panicked at src/imageops/filter_1d.rs:83:50:
called `Option::unwrap()` on a `None` value

Stack trace:

thread 'main' panicked at src/imageops/filter_1d.rs:83:50:
called `Option::unwrap()` on a `None` value
stack backtrace:
   0: __rustc::rust_begin_unwind
             at /rustc/ec7c02612527d185c379900b613311bc1dcbf7dc/library/std/src/panicking.rs:697:5
   1: core::panicking::panic_fmt
             at /rustc/ec7c02612527d185c379900b613311bc1dcbf7dc/library/core/src/panicking.rs:75:14
   2: core::panicking::panic
             at /rustc/ec7c02612527d185c379900b613311bc1dcbf7dc/library/core/src/panicking.rs:145:5
   3: core::option::unwrap_failed
             at /rustc/ec7c02612527d185c379900b613311bc1dcbf7dc/library/core/src/option.rs:2130:5
   4: core::option::Option<T>::unwrap
             at /home/tony/.rustup/toolchains/nightly-2025-08-06-x86_64-unknown-linux-gnu/lib/rustlib/src/rust/library/core/src/option.rs:1009:21
   5: image::imageops::filter_1d::make_arena_row
             at ./src/imageops/filter_1d.rs:83:50
   6: image::imageops::filter_1d::filter_2d_separable_ring_queue
             at ./src/imageops/filter_1d.rs:529:5
   7: image::imageops::filter_1d::filter_2d_separable
             at ./src/imageops/filter_1d.rs:674:16
   8: image::imageops::filter_1d::filter_2d_sep_rgb_f32
             at ./src/imageops/filter_1d.rs:866:5
   9: image::imageops::sample::gaussian_blur_indirect_impl
             at ./src/imageops/sample.rs:1574:13
  10: image::imageops::sample::gaussian_blur_indirect
             at ./src/imageops/sample.rs:1499:14
  11: image::imageops::sample::blur_advanced
             at ./src/imageops/sample.rs:1054:5
  12: image::imageops::sample::unsharpen
             at ./src/imageops/sample.rs:1623:19
  13: image::images::dynimage::DynamicImage::unsharpen
             at ./src/images/dynimage.rs:1278:38
  14: poc_05_unsharpen_zero_dim::main
             at ./examples/poc_05_unsharpen_zero_dim.rs:11:17

Expected behavior

Should return an empty image (same dimensions) without panicking.

To reproduce

Input file: poc_input_0x0.ppm (11 bytes, valid PPM P6 with 0×0 dimensions)

fn main() {
    let img = image::open("poc_input_0x0.ppm").expect("Failed to load image");
    let _ = img.unsharpen(1.0, 10);
}

poc_input_0x0.ppm can be created by: echo "P6\n0 0\n255" > poc_input_0x0.ppm

Test environment

  • Version: image crate main branch
  • OS: Ubuntu 24.04, 64-bit
  • Rustc version: rustc 1.91.0-nightly (ec7c02612 2025-08-05)

Suggested fix

  1. move let (width, height) = image.dimensions(); to the top of the function
  2. add an early return for zero dimensions.
pub fn unsharpen<I, P, S>(image: &I, sigma: f32, threshold: i32) -> ImageBuffer<P, Vec<S>>
where ...
{
+    let (width, height) = image.dimensions();
+    if width == 0 || height == 0 {
+        return image.buffer_like();
+    }
     let mut tmp = blur_advanced(image, GaussianBlurParameters::new_from_sigma(sigma));
 
     let max = S::DEFAULT_MAX_VALUE;
     let max: i32 = NumCast::from(max).unwrap();
-    let (width, height) = image.dimensions();
    // ... rest unchanged
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    kind: panicThis bug causes panics

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions