Skip to content

Fix: Prevent negative indices in downsample_fft when image dimension is less than MIN_IMG_SIZE#44

Open
leonardodtang wants to merge 7 commits intorohitrango:mainfrom
leonardodtang:main
Open

Fix: Prevent negative indices in downsample_fft when image dimension is less than MIN_IMG_SIZE#44
leonardodtang wants to merge 7 commits intorohitrango:mainfrom
leonardodtang:main

Conversation

@leonardodtang
Copy link

fireants.utils.imageutils.downsample_fft (line 163): When the global variable MIN_IMG_SIZE (default 32) is larger than one of the image's original dimensions, the calculated target_dims can be smaller than source_dims. This results in negative values within the start_idx array, which subsequently causes indexing to fail.

This is a common issue when processing non-brain MRI with high slice thickness and a small FOV, such as prostate MRI with imagedimensions of 20x192x192 (voxel size 3.5x1.35x1.35mm).

A quick fix would be to simply lower the MIN_IMG_SIZE to 16 or 8, but this should come with some caveats to limit the slice thickness to reasonable numbers.

Changes:

  • AbstractRegistration is modified to create a self.min_dim variable. self.min_dim is set with self._set_min_dim during initialization. In classes that inherit from AbstractRegistration, self.min_dim is used in place of MIN_IMG_SIZE
    • Modifying abstract class keeps minimum dimension consistent between fixed and moving image batches for each registration object
    • Raises ValueError if fixed or moving image is smaller than MIN_IMG_SHARDED_SIZE, currently set to 4. Can modify lower bound to something other than MIN_IMG_SHARDED_SIZE if 4 is too small.
  • CompositiveWarp and StationaryVelocity do not inherit from AbstractRegistration but use MIN_IMG_SIZE, so MIN_IMG_SIZE has been replaced with min_dim_f, calculated the same way as in AbstractRegistration._set_min_dim
  • The interpolate_mode for FakeBatchedImages in fireants.registration.abstract (line 336) appears to be broken, reverting to bilinear
  • fireants.registration.greedy.GreedyRegistration.get_inverse_warp_parameters erroneously refers to fixed_arrays which is not initialized (line 168). Changed to fixed_images

Tested affine and greedy registration on images with 24 and 20 slices. More testing may be necessary

…pendency. Allows for smaller minimum image sizes
@rohitrango rohitrango requested a review from Copilot October 13, 2025 14:23
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull Request Overview

This PR fixes a bug in the downsample_fft function where negative indices occur when image dimensions are smaller than MIN_IMG_SIZE (default 32). The issue commonly arises with medical images like prostate MRI that have small slice counts.

  • Replaces hardcoded MIN_IMG_SIZE with adaptive min_dim calculation that finds the largest power-of-2 dimension that fits the image
  • Adds minimum dimension validation with MIN_IMG_SHARDED_SIZE as the lower bound
  • Temporarily fixes interpolation mode issue in FakeBatchedImages

Reviewed Changes

Copilot reviewed 8 out of 8 changed files in this pull request and generated 5 comments.

Show a summary per file
File Description
fireants/registration/abstract.py Adds _set_min_dim() method to calculate adaptive minimum dimensions and fixes interpolation mode
fireants/registration/syn.py Replaces MIN_IMG_SIZE with self.min_dim in optimization loop
fireants/registration/rigid.py Replaces MIN_IMG_SIZE with self.min_dim for both fixed and moving image downsampling
fireants/registration/moments.py Updates downsampling logic to use self.min_dim instead of MIN_IMG_SIZE
fireants/registration/greedy.py Replaces MIN_IMG_SIZE with self.min_dim in image resizing calculations
fireants/registration/deformation/svf.py Implements standalone min_dim_f calculation for non-AbstractRegistration class
fireants/registration/deformation/compositive.py Adds adaptive minimum dimension logic similar to SVF implementation
fireants/registration/affine.py Updates downsampling to use self.min_dim instead of hardcoded constant

Tip: Customize your code reviews with copilot-instructions.md. Create the file or learn how to get started.

@rohitrango
Copy link
Owner

rohitrango commented Oct 17, 2025

looks good to me!

one last thing, can you add a unittest checking for this behavior? You can use synthetic images for this, we just want to check if the min image size is correct for different sizes of images that might be possible.

Thanks for your contribution!

@leonardodtang
Copy link
Author

Added tests/test_lowdim.py; I left in optional use of images used in tests/test_deformable_registration.py if/when they exist (not in the repo), uses synthetic data if not.

self.loss_fn.set_scales(self.scales)

# set min dim for img_size
fixed_arrays = self.fixed_images()
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

do we need to get fixed_arrays and moving_arrays? There is a shape attribute of the BatchedImages object that you can use directly

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants