Browse Source

Code for GLM analysis pipeline

Michael Hanke 8 years ago
parent
commit
e24b382c86

File diff suppressed because it is too large
+ 1566 - 0
code/1stlevel_design.fsf


+ 411 - 0
code/2ndlevel_design.fsf

@@ -0,0 +1,411 @@
+
+# FEAT version number
+set fmri(version) 6.00
+
+# Are we in MELODIC?
+set fmri(inmelodic) 0
+
+# Analysis level
+# 1 : First-level analysis
+# 2 : Higher-level analysis
+set fmri(level) 2
+
+# Which stages to run
+# 0 : No first-level analysis (registration and/or group stats only)
+# 7 : Full first-level analysis
+# 1 : Pre-processing
+# 2 : Statistics
+set fmri(analysis) 2
+
+# Use relative filenames
+set fmri(relative_yn) 0
+
+# Balloon help
+set fmri(help_yn) 0
+
+# Run Featwatcher
+set fmri(featwatcher_yn) 0
+
+# Cleanup first-level standard-space images
+set fmri(sscleanup_yn) 0
+
+# Output directory
+set fmri(outputdir) "/home/data/psyinf/forrest_gump/collection/visloc/###SUB###/2ndlvl_z164"
+
+# TR(s)
+set fmri(tr) 3
+
+# Total volumes
+set fmri(npts) 4
+
+# Delete volumes
+set fmri(ndelete) 0
+
+# Perfusion tag/control order
+set fmri(tagfirst) 1
+
+# Number of first-level analyses
+set fmri(multiple) 4
+
+# Higher-level input type
+# 1 : Inputs are lower-level FEAT directories
+# 2 : Inputs are cope images from FEAT directories
+set fmri(inputtype) 1
+
+# Carry out pre-stats processing?
+set fmri(filtering_yn) 0
+
+# Brain/background threshold, %
+set fmri(brain_thresh) 10
+
+# Critical z for design efficiency calculation
+set fmri(critical_z) 5.3
+
+# Noise level
+set fmri(noise) 0.66
+
+# Noise AR(1)
+set fmri(noisear) 0.34
+
+# Motion correction
+# 0 : None
+# 1 : MCFLIRT
+set fmri(mc) 1
+
+# Spin-history (currently obsolete)
+set fmri(sh_yn) 0
+
+# B0 fieldmap unwarping?
+set fmri(regunwarp_yn) 0
+
+# EPI dwell time (ms)
+set fmri(dwell) 0.7
+
+# EPI TE (ms)
+set fmri(te) 35
+
+# % Signal loss threshold
+set fmri(signallossthresh) 10
+
+# Unwarp direction
+set fmri(unwarp_dir) y-
+
+# Slice timing correction
+# 0 : None
+# 1 : Regular up (0, 1, 2, 3, ...)
+# 2 : Regular down
+# 3 : Use slice order file
+# 4 : Use slice timings file
+# 5 : Interleaved (0, 2, 4 ... 1, 3, 5 ... )
+set fmri(st) 0
+
+# Slice timings file
+set fmri(st_file) ""
+
+# BET brain extraction
+set fmri(bet_yn) 1
+
+# Spatial smoothing FWHM (mm)
+set fmri(smooth) 5
+
+# Intensity normalization
+set fmri(norm_yn) 0
+
+# Perfusion subtraction
+set fmri(perfsub_yn) 0
+
+# Highpass temporal filtering
+set fmri(temphp_yn) 1
+
+# Lowpass temporal filtering
+set fmri(templp_yn) 0
+
+# MELODIC ICA data exploration
+set fmri(melodic_yn) 0
+
+# Carry out main stats?
+set fmri(stats_yn) 1
+
+# Carry out prewhitening?
+set fmri(prewhiten_yn) 1
+
+# Add motion parameters to model
+# 0 : No
+# 1 : Yes
+set fmri(motionevs) 0
+set fmri(motionevsbeta) ""
+set fmri(scriptevsbeta) ""
+
+# Robust outlier detection in FLAME?
+set fmri(robust_yn) 1
+
+# Higher-level modelling
+# 3 : Fixed effects
+# 0 : Mixed Effects: Simple OLS
+# 2 : Mixed Effects: FLAME 1
+# 1 : Mixed Effects: FLAME 1+2
+set fmri(mixed_yn) 2
+
+# Number of EVs
+set fmri(evs_orig) 1
+set fmri(evs_real) 1
+set fmri(evs_vox) 0
+
+# Number of contrasts
+set fmri(ncon_orig) 1
+set fmri(ncon_real) 1
+
+# Number of F-tests
+set fmri(nftests_orig) 0
+set fmri(nftests_real) 0
+
+# Add constant column to design matrix? (obsolete)
+set fmri(constcol) 0
+
+# Carry out post-stats steps?
+set fmri(poststats_yn) 0
+
+# Pre-threshold masking?
+set fmri(threshmask) ""
+
+# Thresholding
+# 0 : None
+# 1 : Uncorrected
+# 2 : Voxel
+# 3 : Cluster
+set fmri(thresh) 3
+
+# P threshold
+set fmri(prob_thresh) 0.05
+
+# Z threshold
+set fmri(z_thresh) 1.64
+
+# Z min/max for colour rendering
+# 0 : Use actual Z min/max
+# 1 : Use preset Z min/max
+set fmri(zdisplay) 0
+
+# Z min in colour rendering
+set fmri(zmin) 2
+
+# Z max in colour rendering
+set fmri(zmax) 8
+
+# Colour rendering type
+# 0 : Solid blobs
+# 1 : Transparent blobs
+set fmri(rendertype) 1
+
+# Background image for higher-level stats overlays
+# 1 : Mean highres
+# 2 : First highres
+# 3 : Mean functional
+# 4 : First functional
+# 5 : Standard space template
+set fmri(bgimage) 5
+
+# Create time series plots
+set fmri(tsplot_yn) 0
+
+# Registration to initial structural
+set fmri(reginitial_highres_yn) 0
+
+# Search space for registration to initial structural
+# 0   : No search
+# 90  : Normal search
+# 180 : Full search
+set fmri(reginitial_highres_search) 90
+
+# Degrees of Freedom for registration to initial structural
+set fmri(reginitial_highres_dof) 3
+
+# Registration to main structural
+set fmri(reghighres_yn) 0
+
+# Search space for registration to main structural
+# 0   : No search
+# 90  : Normal search
+# 180 : Full search
+set fmri(reghighres_search) 90
+
+# Degrees of Freedom for registration to main structural
+set fmri(reghighres_dof) BBR
+
+# Registration to standard image?
+set fmri(regstandard_yn) 1
+
+# Use alternate reference images?
+set fmri(alternateReference_yn) 0
+
+# Standard image
+set fmri(regstandard) "/usr/share/fsl/5.0/data/standard/MNI152_T1_2mm_brain"
+
+# Search space for registration to standard space
+# 0   : No search
+# 90  : Normal search
+# 180 : Full search
+set fmri(regstandard_search) 90
+
+# Degrees of Freedom for registration to standard space
+set fmri(regstandard_dof) 12
+
+# Do nonlinear registration from structural to standard space?
+set fmri(regstandard_nonlinear_yn) 0
+
+# Control nonlinear warp field resolution
+set fmri(regstandard_nonlinear_warpres) 10 
+
+# High pass filter cutoff
+set fmri(paradigm_hp) 100
+
+# Number of lower-level copes feeding into higher-level analysis
+set fmri(ncopeinputs) 10
+
+# Use lower-level cope 1 for higher-level analysis
+set fmri(copeinput.1) 1
+
+# Use lower-level cope 2 for higher-level analysis
+set fmri(copeinput.2) 1
+
+# Use lower-level cope 3 for higher-level analysis
+set fmri(copeinput.3) 1
+
+# Use lower-level cope 4 for higher-level analysis
+set fmri(copeinput.4) 1
+
+# Use lower-level cope 5 for higher-level analysis
+set fmri(copeinput.5) 1
+
+# Use lower-level cope 6 for higher-level analysis
+set fmri(copeinput.6) 1
+
+# Use lower-level cope 7 for higher-level analysis
+set fmri(copeinput.7) 1
+
+# Use lower-level cope 8 for higher-level analysis
+set fmri(copeinput.8) 1
+
+# Use lower-level cope 9 for higher-level analysis
+set fmri(copeinput.9) 1
+
+# Use lower-level cope 10 for higher-level analysis
+set fmri(copeinput.10) 1
+
+# 4D AVW data or FEAT directory (1)
+set feat_files(1) "/home/data/psyinf/forrest_gump/collection/visloc/###SUB###/run-1.feat"
+
+# 4D AVW data or FEAT directory (2)
+set feat_files(2) "/home/data/psyinf/forrest_gump/collection/visloc/###SUB###/run-2.feat"
+
+# 4D AVW data or FEAT directory (3)
+set feat_files(3) "/home/data/psyinf/forrest_gump/collection/visloc/###SUB###/run-3.feat"
+
+# 4D AVW data or FEAT directory (4)
+set feat_files(4) "/home/data/psyinf/forrest_gump/collection/visloc/###SUB###/run-4.feat"
+
+# Add confound EVs text file
+set fmri(confoundevs) 0
+
+# EV 1 title
+set fmri(evtitle1) ""
+
+# Basic waveform shape (EV 1)
+# 0 : Square
+# 1 : Sinusoid
+# 2 : Custom (1 entry per volume)
+# 3 : Custom (3 column format)
+# 4 : Interaction
+# 10 : Empty (all zeros)
+set fmri(shape1) 2
+
+# Convolution (EV 1)
+# 0 : None
+# 1 : Gaussian
+# 2 : Gamma
+# 3 : Double-Gamma HRF
+# 4 : Gamma basis functions
+# 5 : Sine basis functions
+# 6 : FIR basis functions
+set fmri(convolve1) 0
+
+# Convolve phase (EV 1)
+set fmri(convolve_phase1) 0
+
+# Apply temporal filtering (EV 1)
+set fmri(tempfilt_yn1) 0
+
+# Add temporal derivative (EV 1)
+set fmri(deriv_yn1) 0
+
+# Custom EV file (EV 1)
+set fmri(custom1) "dummy"
+
+# Orthogonalise EV 1 wrt EV 0
+set fmri(ortho1.0) 0
+
+# Orthogonalise EV 1 wrt EV 1
+set fmri(ortho1.1) 0
+
+# Higher-level EV value for EV 1 and input 1
+set fmri(evg1.1) 1
+
+# Higher-level EV value for EV 1 and input 2
+set fmri(evg2.1) 1
+
+# Higher-level EV value for EV 1 and input 3
+set fmri(evg3.1) 1
+
+# Higher-level EV value for EV 1 and input 4
+set fmri(evg4.1) 1
+
+# Group membership for input 1
+set fmri(groupmem.1) 1
+
+# Group membership for input 2
+set fmri(groupmem.2) 1
+
+# Group membership for input 3
+set fmri(groupmem.3) 1
+
+# Group membership for input 4
+set fmri(groupmem.4) 1
+
+# Contrast & F-tests mode
+# real : control real EVs
+# orig : control original EVs
+set fmri(con_mode_old) real
+set fmri(con_mode) real
+
+# Display images for contrast_real 1
+set fmri(conpic_real.1) 1
+
+# Title for contrast_real 1
+set fmri(conname_real.1) "group mean"
+
+# Real contrast_real vector 1 element 1
+set fmri(con_real1.1) 1
+
+# Contrast masking - use >0 instead of thresholding?
+set fmri(conmask_zerothresh_yn) 0
+
+# Do contrast masking at all?
+set fmri(conmask1_1) 0
+
+##########################################################
+# Now options that don't appear in the GUI
+
+# Alternative (to BETting) mask image
+set fmri(alternative_mask) ""
+
+# Initial structural space registration initialisation transform
+set fmri(init_initial_highres) ""
+
+# Structural space registration initialisation transform
+set fmri(init_highres) ""
+
+# Standard space registration initialisation transform
+set fmri(init_standard) ""
+
+# For full FEAT analysis: overwrite existing .feat output dir?
+set fmri(overwrite_yn) 0

+ 133 - 0
code/compute_1stlvl_glm.submit

@@ -0,0 +1,133 @@
+# auto-generate file (generate_1st_level_design.sh) -- do not modify!
+universe = vanilla
+output = condor_logs/$(CLUSTER).$(PROCESS).out
+error = condor_logs/$(CLUSTER).$(PROCESS).err
+log = condor_logs/$(CLUSTER).$(PROCESS).log
+getenv = True
+request_cpus = 1
+request_memory = 4000
+should_transfer_files = NO
+transfer_executable = False
+initialdir = /home/data/psyinf/forrest_gump/collection/visloc
+executable = $ENV(FSLDIR)/bin/feat
+
+arguments = sub-01/run-1_1st.fsf
+queue
+arguments = sub-01/run-2_1st.fsf
+queue
+arguments = sub-01/run-3_1st.fsf
+queue
+arguments = sub-01/run-4_1st.fsf
+queue
+arguments = sub-02/run-1_1st.fsf
+queue
+arguments = sub-02/run-2_1st.fsf
+queue
+arguments = sub-02/run-3_1st.fsf
+queue
+arguments = sub-02/run-4_1st.fsf
+queue
+arguments = sub-03/run-1_1st.fsf
+queue
+arguments = sub-03/run-2_1st.fsf
+queue
+arguments = sub-03/run-3_1st.fsf
+queue
+arguments = sub-03/run-4_1st.fsf
+queue
+arguments = sub-04/run-1_1st.fsf
+queue
+arguments = sub-04/run-2_1st.fsf
+queue
+arguments = sub-04/run-3_1st.fsf
+queue
+arguments = sub-04/run-4_1st.fsf
+queue
+arguments = sub-05/run-1_1st.fsf
+queue
+arguments = sub-05/run-2_1st.fsf
+queue
+arguments = sub-05/run-3_1st.fsf
+queue
+arguments = sub-05/run-4_1st.fsf
+queue
+arguments = sub-06/run-1_1st.fsf
+queue
+arguments = sub-06/run-2_1st.fsf
+queue
+arguments = sub-06/run-3_1st.fsf
+queue
+arguments = sub-06/run-4_1st.fsf
+queue
+arguments = sub-09/run-1_1st.fsf
+queue
+arguments = sub-09/run-2_1st.fsf
+queue
+arguments = sub-09/run-3_1st.fsf
+queue
+arguments = sub-09/run-4_1st.fsf
+queue
+arguments = sub-10/run-1_1st.fsf
+queue
+arguments = sub-10/run-2_1st.fsf
+queue
+arguments = sub-10/run-3_1st.fsf
+queue
+arguments = sub-10/run-4_1st.fsf
+queue
+arguments = sub-14/run-1_1st.fsf
+queue
+arguments = sub-14/run-2_1st.fsf
+queue
+arguments = sub-14/run-3_1st.fsf
+queue
+arguments = sub-14/run-4_1st.fsf
+queue
+arguments = sub-15/run-1_1st.fsf
+queue
+arguments = sub-15/run-2_1st.fsf
+queue
+arguments = sub-15/run-3_1st.fsf
+queue
+arguments = sub-15/run-4_1st.fsf
+queue
+arguments = sub-16/run-1_1st.fsf
+queue
+arguments = sub-16/run-2_1st.fsf
+queue
+arguments = sub-16/run-3_1st.fsf
+queue
+arguments = sub-16/run-4_1st.fsf
+queue
+arguments = sub-17/run-1_1st.fsf
+queue
+arguments = sub-17/run-2_1st.fsf
+queue
+arguments = sub-17/run-3_1st.fsf
+queue
+arguments = sub-17/run-4_1st.fsf
+queue
+arguments = sub-18/run-1_1st.fsf
+queue
+arguments = sub-18/run-2_1st.fsf
+queue
+arguments = sub-18/run-3_1st.fsf
+queue
+arguments = sub-18/run-4_1st.fsf
+queue
+arguments = sub-19/run-1_1st.fsf
+queue
+arguments = sub-19/run-2_1st.fsf
+queue
+arguments = sub-19/run-3_1st.fsf
+queue
+arguments = sub-19/run-4_1st.fsf
+queue
+arguments = sub-20/run-1_1st.fsf
+queue
+arguments = sub-20/run-2_1st.fsf
+queue
+arguments = sub-20/run-3_1st.fsf
+queue
+arguments = sub-20/run-4_1st.fsf
+queue

+ 43 - 0
code/compute_2ndlvl_glm.submit

@@ -0,0 +1,43 @@
+# auto-generate file (generate_2nd_level_design.sh) -- do not modify!
+universe = vanilla
+output = condor_logs/$(CLUSTER).$(PROCESS).out
+error = condor_logs/$(CLUSTER).$(PROCESS).err
+log = condor_logs/$(CLUSTER).$(PROCESS).log
+getenv = True
+request_cpus = 1
+request_memory = 2000
+should_transfer_files = NO
+transfer_executable = False
+initialdir = /home/data/psyinf/forrest_gump/collection/visloc
+executable = $ENV(FSLDIR)/bin/feat
+
+arguments = sub-01/2nd_z164.fsf
+queue
+arguments = sub-02/2nd_z164.fsf
+queue
+arguments = sub-03/2nd_z164.fsf
+queue
+arguments = sub-04/2nd_z164.fsf
+queue
+arguments = sub-05/2nd_z164.fsf
+queue
+arguments = sub-06/2nd_z164.fsf
+queue
+arguments = sub-09/2nd_z164.fsf
+queue
+arguments = sub-10/2nd_z164.fsf
+queue
+arguments = sub-14/2nd_z164.fsf
+queue
+arguments = sub-15/2nd_z164.fsf
+queue
+arguments = sub-16/2nd_z164.fsf
+queue
+arguments = sub-17/2nd_z164.fsf
+queue
+arguments = sub-18/2nd_z164.fsf
+queue
+arguments = sub-19/2nd_z164.fsf
+queue
+arguments = sub-20/2nd_z164.fsf
+queue

+ 29 - 0
code/generate_1st_level_design.sh

@@ -0,0 +1,29 @@
+#!/bin/bash
+
+set -e
+set -u
+
+cat << EOT > code/compute_1stlvl_glm.submit
+# auto-generate file (generate_1st_level_design.sh) -- do not modify!
+universe = vanilla
+output = condor_logs/\$(CLUSTER).\$(PROCESS).out
+error = condor_logs/\$(CLUSTER).\$(PROCESS).err
+log = condor_logs/\$(CLUSTER).\$(PROCESS).log
+getenv = True
+request_cpus = 1
+request_memory = 4000
+should_transfer_files = NO
+transfer_executable = False
+initialdir = /home/data/psyinf/forrest_gump/collection/visloc
+executable = \$ENV(FSLDIR)/bin/feat
+
+EOT
+
+for sub in sub-*; do
+  subid=$(echo "$sub" | cut -d '-' -f2-)
+  for run in $sub/onsets/run*; do
+    runid=$(echo "$(basename $run)" | cut -d '-' -f2-)
+    sed -e "s/###SUB###/sub-${subid}/g" -e "s/###RUN###/run-${runid}/g" code/1stlevel_design.fsf > "$sub/run-${runid}_1st.fsf"
+    printf "arguments = $sub/run-${runid}_1st.fsf\nqueue\n" >> code/compute_1stlvl_glm.submit
+  done
+done

+ 28 - 0
code/generate_2nd_level_design.sh

@@ -0,0 +1,28 @@
+#!/bin/bash
+
+set -e
+set -u
+
+cat << EOT > code/compute_2ndlvl_glm.submit
+# auto-generate file (generate_2nd_level_design.sh) -- do not modify!
+universe = vanilla
+output = condor_logs/\$(CLUSTER).\$(PROCESS).out
+error = condor_logs/\$(CLUSTER).\$(PROCESS).err
+log = condor_logs/\$(CLUSTER).\$(PROCESS).log
+getenv = True
+request_cpus = 1
+request_memory = 2000
+should_transfer_files = NO
+transfer_executable = False
+initialdir = /home/data/psyinf/forrest_gump/collection/visloc
+executable = \$ENV(FSLDIR)/bin/feat
+
+EOT
+
+label="2nd_z164"
+
+for sub in sub-*; do
+  subid=$(echo "$sub" | cut -d '-' -f2-)
+  sed -e "s/###SUB###/sub-${subid}/g" code/2ndlevel_design.fsf > "$sub/${label}.fsf"
+  printf "arguments = $sub/${label}.fsf\nqueue\n" >> code/compute_2ndlvl_glm.submit
+done

+ 61 - 0
code/localizerstats2mask.sh

@@ -0,0 +1,61 @@
+#!/bin/bash
+# Take all localizer 1st-level GLM analysis results, computes and average zstat map
+# for both contrasts of interest, masks them with the given mask image, and thresholds to
+# identify the voxels matching the desired percentile of largest values
+#
+# Usage:
+#   code/localizerstats2mask.sh sub-4 VT_roi 90
+
+set -e
+set -u
+
+sub=$1
+mask=$2
+percentile=$3
+dsdir="$(readlink -f .)"
+
+wdir=$(mktemp -d --suffix=localizer2mask)
+trap "rm -rf $wdir" SIGINT SIGTERM
+cd "$wdir"
+
+# define contrast names
+contrasts=(dummy all ffa ppa eba loc vis ffa_alt ppa_alt eba_alt loc_alt)
+
+##combine MNI2T1 and T12BOLD
+#$FSLDIR/bin/convert_xfm \
+#  -omat mni2bold.mat \
+#  -concat ${dsdir}/src/tnt/${sub}/t1w/in_bold/xfm_6dof.mat \
+#  ${dsdir}/src/tnt/${sub}/t1w/in_mni152/tmpl2subj.mat
+
+## re-slice mask
+#$FSLDIR/bin/flirt \
+#  -in "${dsdir}/${mask}" \
+#  -ref ${dsdir}/src/tnt/${sub}/bold/brain \
+#  -applyxfm -init mni2bold.mat \
+#  -out mask \
+#  -interp nearestneighbour
+
+## apply transformation to subject template for all runs
+#for f in ${dsdir}/${sub}/run-*.feat; do
+#  $FSLDIR/bin/featregapply "$f"
+#  # make zstats
+#  $FSLDIR/bin/fslmaths $f/reg_standard/stats/varcope1 -sqrt $f/reg_standard/stats/stdcope1
+#  $FSLDIR/bin/fslmaths $f/reg_standard/stats/varcope2 -sqrt $f/reg_standard/stats/stdcope2
+#  $FSLDIR/bin/fslmaths $f/reg_standard/stats/cope1 -div $f/reg_standard/stats/stdcope1 $f/reg_standard/stats/zstat1
+#  $FSLDIR/bin/fslmaths $f/reg_standard/stats/cope2 -div $f/reg_standard/stats/stdcope2 $f/reg_standard/stats/zstat2
+#done
+
+# make average zstat across all runs -- mask
+for i in $(seq 10); do
+  $FSLDIR/bin/fslmerge -t zstat${i}_merged ${dsdir}/${sub}/run-*.feat/stats/zstat${i}.nii*
+  #$FSLDIR/bin/fslmaths zstat${i}_merged -Tmean -mas mask zstat${i}
+  $FSLDIR/bin/fslmaths zstat${i}_merged -Tmean zstat${i}
+  # take desired upper percentile and threshold for mask
+  fslmaths zstat${i} \
+    -thr $($FSLDIR/bin/fslstats zstat${i} -P "$percentile") \
+    ${dsdir}/${sub}/${contrasts[$i]}_thr${percentile}
+done
+
+cd -
+rm -rf "$wdir"
+

+ 42 - 0
code/localizerstats2mask.submit

@@ -0,0 +1,42 @@
+universe = vanilla
+output = condor_logs/$(CLUSTER).$(PROCESS).out
+error = condor_logs/$(CLUSTER).$(PROCESS).err
+log = condor_logs/$(CLUSTER).$(PROCESS).log
+getenv = True
+request_cpus = 1
+request_memory = 1000
+should_transfer_files = NO
+transfer_executable = False
+initialdir = /home/data/psyinf/forrest_gump/collection/visloc
+executable = code/localizerstats2mask.sh
+
+arguments = sub-01 dummy 99.9
+queue
+arguments = sub-02 dummy 99.9
+queue
+arguments = sub-03 dummy 99.9
+queue
+arguments = sub-04 dummy 99.9
+queue
+arguments = sub-05 dummy 99.9
+queue
+arguments = sub-06 dummy 99.9
+queue
+arguments = sub-09 dummy 99.9
+queue
+arguments = sub-10 dummy 99.9
+queue
+arguments = sub-14 dummy 99.9
+queue
+arguments = sub-15 dummy 99.9
+queue
+arguments = sub-16 dummy 99.9
+queue
+arguments = sub-17 dummy 99.9
+queue
+arguments = sub-18 dummy 99.9
+queue
+arguments = sub-19 dummy 99.9
+queue
+arguments = sub-20 dummy 99.9
+queue

+ 63 - 0
code/reg2std4feat

@@ -0,0 +1,63 @@
+#!/bin/bash
+#
+# Usage: reg2std4feat <tntdir> <inspace> <stdspace> <feat_dir> [<feat_dir> ...]
+#
+# Example: reg2std4feat src/tnt/ bold3Tp2 grpbold3Tp2 sub-/run*_testme.feat
+#
+# This script makes the assumption that there is no highres space, but
+# alignment was performed from BOLD directly to a group template (most
+# likely computed from BOLD as well)
+#
+
+set -e
+set -u
+
+tntdir="$1"
+shift
+inspace="$1"
+shift
+stdspace="$1"
+shift
+
+for featdir in $@; do
+	subj="$(echo $featdir| sed -e 's,.*\(sub-.*\)/.*,\1,g')"
+	tntsubdir="${tntdir}/${subj}"
+	# sane defaults
+	tmpl2std_mat="$FSLDIR/etc/flirtsch/ident.mat"
+	tmpl2std_warp=""
+	# cleanup existing standard space registration
+	[ -d "$featdir/reg_standard" ] && rm -rf "$featdir/reg_standard" || true
+	# place reg info in existing featdir in a way that featregapply would
+	# swallow it
+	regdir="$featdir/reg"
+	mkdir -p "$regdir"
+	# remove any possibly existing standard space setup
+	rm -rf "$regdir"/*standard*
+	if [ "$inspace" != "$stdspace" ]; then
+		xfmdir="$tntsubdir/$inspace/in_$stdspace"
+		# check that we have the xfm info
+		[ $(imtest "$xfmdir/brain") -eq 1 ] && : || echo "cannot find transformation"
+		if [ -e "$xfmdir/xfm_12dof.mat" ]; then
+			tmpl2std_mat="$xfmdir/xfm_12dof.mat"
+		fi
+		if [ $(imtest "$xfmdir/subj2tmpl_warp") -eq 1 ]; then
+			tmpl2std_warp="$xfmdir/subj2tmpl_warp"
+		fi
+		imcp "$xfmdir/brain" "$regdir/standard"
+	else
+		# we stay in the 
+		imcp "$tntsubdir/$inspace/brain" "$regdir/standard"
+	fi
+	if [ -e "$regdir/example_func2highres.mat" ]; then
+		convert_xfm -omat "$regdir/example_func2standard.mat" \
+			-concat "$tmpl2std_mat" \
+			"$regdir/example_func2highres.mat"
+	else
+		cp "$tmpl2std_mat" "$regdir/example_func2highres.mat"
+		cp "$tmpl2std_mat" "$regdir/example_func2standard.mat"
+	fi
+	if [ -n "$tmpl2std_warp" ]; then
+		imcp "$tmpl2std_warp" "$regdir/highres2standard_warp"
+	fi
+done
+