Summary
resolve_functional in src/rbc/bids/functional.py:90-98 queries for from-MNI152NLin6Asym_to-T1w (the inverse composite warp) and assigns it to anat_to_template. This variable is then passed to resample_bold_to_template where it's used in an ANTs transform chain that expects the forward direction (T1w -> template).
Evidence
Registration (src/rbc/core/anatomical/registration.py):
forward_xfm: composite created with reference_image=template, maps T1w -> template. Exported as from-T1w_to-MNI152NLin6Asym.
inverse_xfm: composite created with reference_image=T1w, maps template -> T1w. Exported as from-MNI152NLin6Asym_to-T1w.
Functional resampling (src/rbc/core/functional/resampling.py:167):
base_transforms = [anat_to_template, bold2anat_itk]
# Comment on line 172: "Order (last applied first): motion -> bold2anat -> anat2template"
ANTs applies transforms in reverse list order. With reference_image=template, the last-applied transform (anat_to_template, first in list) should map T1w -> template, i.e. the forward warp.
But resolve_functional queries from-MNI_to-T1w (the inverse warp) for this parameter.
The same issue affects _warp_mask_to_template (line 327), which also receives this value.
Action items
- Run
resample_bold_to_template with both forward_xfm and inverse_xfm on a test case and compare outputs to confirm which direction is correct
- Fix
resolve_functional if the query is wrong (swap to from-T1w_to-MNI152NLin6Asym)
- Consider renaming
forward_xfm/inverse_xfm in AnatomicalOutputs to something unambiguous (e.g. t1w_to_template_xfm / template_to_t1w_xfm) so the direction is always clear from the name
- Audit other resolve functions (
resolve_longitudinal_anat, resolve_longitudinal_func) for the same pattern
Context
Found while investigating #287. The naming inconsistency makes it hard to verify correctness of in-memory handoffs between pipeline stages.
Summary
resolve_functionalinsrc/rbc/bids/functional.py:90-98queries forfrom-MNI152NLin6Asym_to-T1w(the inverse composite warp) and assigns it toanat_to_template. This variable is then passed toresample_bold_to_templatewhere it's used in an ANTs transform chain that expects the forward direction (T1w -> template).Evidence
Registration (
src/rbc/core/anatomical/registration.py):forward_xfm: composite created withreference_image=template, maps T1w -> template. Exported asfrom-T1w_to-MNI152NLin6Asym.inverse_xfm: composite created withreference_image=T1w, maps template -> T1w. Exported asfrom-MNI152NLin6Asym_to-T1w.Functional resampling (
src/rbc/core/functional/resampling.py:167):ANTs applies transforms in reverse list order. With
reference_image=template, the last-applied transform (anat_to_template, first in list) should map T1w -> template, i.e. the forward warp.But
resolve_functionalqueriesfrom-MNI_to-T1w(the inverse warp) for this parameter.The same issue affects
_warp_mask_to_template(line 327), which also receives this value.Action items
resample_bold_to_templatewith bothforward_xfmandinverse_xfmon a test case and compare outputs to confirm which direction is correctresolve_functionalif the query is wrong (swap tofrom-T1w_to-MNI152NLin6Asym)forward_xfm/inverse_xfminAnatomicalOutputsto something unambiguous (e.g.t1w_to_template_xfm/template_to_t1w_xfm) so the direction is always clear from the nameresolve_longitudinal_anat,resolve_longitudinal_func) for the same patternContext
Found while investigating #287. The naming inconsistency makes it hard to verify correctness of in-memory handoffs between pipeline stages.