/ callback function passed to loop_in_chunks to fill array slice */ /
| 249 | /* callback function passed to loop_in_chunks to fill array slice */ |
| 250 | /***************************************************************/ |
| 251 | static void get_array_slice_chunkloop(fields_chunk *fc, int ichnk, component cgrid, ivec is, |
| 252 | ivec ie, vec s0, vec s1, vec e0, vec e1, double dV0, |
| 253 | double dV1, ivec shift, complex<double> shift_phase, |
| 254 | const symmetry &S, int sn, void *data_) { |
| 255 | UNUSED(ichnk); |
| 256 | UNUSED(cgrid); |
| 257 | UNUSED(s0); |
| 258 | UNUSED(s1); |
| 259 | UNUSED(e0); |
| 260 | UNUSED(e1); |
| 261 | UNUSED(dV0); |
| 262 | UNUSED(dV1); |
| 263 | array_slice_data *data = (array_slice_data *)data_; |
| 264 | |
| 265 | //-----------------------------------------------------------------------// |
| 266 | // Find output chunk dimensions and strides, etc. |
| 267 | //-----------------------------------------------------------------------// |
| 268 | |
| 269 | int start[3] = {0, 0, 0}, count[3] = {1, 1, 1}; |
| 270 | ptrdiff_t offset[3] = {0, 0, 0}; |
| 271 | |
| 272 | ivec isS = S.transform(is, sn) + shift; |
| 273 | ivec ieS = S.transform(ie, sn) + shift; |
| 274 | |
| 275 | // figure out what yucky_directions (in LOOP_OVER_IVECS) |
| 276 | // correspond to what directions in the transformed vectors (in output). |
| 277 | ivec permute(zero_ivec(fc->gv.dim)); |
| 278 | for (int i = 0; i < 3; ++i) |
| 279 | permute.set_direction(fc->gv.yucky_direction(i), i); |
| 280 | permute = S.transform_unshifted(permute, sn); |
| 281 | LOOP_OVER_DIRECTIONS(permute.dim, d) { permute.set_direction(d, abs(permute.in_direction(d))); } |
| 282 | |
| 283 | // compute the size of the chunk to output, and its strides etc. |
| 284 | for (int i = 0; i < data->rank; ++i) { |
| 285 | direction d = data->ds[i]; |
| 286 | int isd = isS.in_direction(d), ied = ieS.in_direction(d); |
| 287 | start[i] = (std::min(isd, ied) - data->min_corner.in_direction(d)) / 2; |
| 288 | count[i] = abs(ied - isd) / 2 + 1; |
| 289 | if (ied < isd) offset[permute.in_direction(d)] = count[i] - 1; |
| 290 | } |
| 291 | |
| 292 | // slightly confusing: for array_slice, in contrast to |
| 293 | // h5fields, strides are computed using the dimensions of |
| 294 | // the full array slice, not the dimensions of the chunk. |
| 295 | size_t dims[3] = {1, 1, 1}; |
| 296 | for (int i = 0; i < data->rank; i++) { |
| 297 | direction d = data->ds[i]; |
| 298 | dims[i] = (data->max_corner.in_direction(d) - data->min_corner.in_direction(d)) / 2 + 1; |
| 299 | } |
| 300 | |
| 301 | ptrdiff_t stride[3] = {1, 1, 1}; |
| 302 | for (int i = 0; i < data->rank; ++i) { |
| 303 | direction d = data->ds[i]; |
| 304 | int j = permute.in_direction(d); |
| 305 | for (int k = i + 1; k < data->rank; ++k) |
| 306 | stride[j] *= dims[k]; |
| 307 | offset[j] *= stride[j]; |
| 308 | if (offset[j]) stride[j] *= -1; |
nothing calls this directly
no test coverage detected