Neko 1.99.9
A portable framework for high-order spectral element flow simulations
Loading...
Searching...
No Matches
conv1_kernel.h
Go to the documentation of this file.
1#ifndef __MATH_CONV1_KERNEL_H__
2#define __MATH_CONV1_KERNEL_H__
3
4#include "elem_block.h"
5#include "dmma_kernel.h"
6#include "dmma_tma_kernel.h"
7/*
8 Copyright (c) 2021-2026, The Neko Authors
9 All rights reserved.
10
11 Redistribution and use in source and binary forms, with or without
12 modification, are permitted provided that the following conditions
13 are met:
14
15 * Redistributions of source code must retain the above copyright
16 notice, this list of conditions and the following disclaimer.
17
18 * Redistributions in binary form must reproduce the above
19 copyright notice, this list of conditions and the following
20 disclaimer in the documentation and/or other materials provided
21 with the distribution.
22
23 * Neither the name of the authors nor the names of its
24 contributors may be used to endorse or promote products derived
25 from this software without specific prior written permission.
26
27 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
28 "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
29 LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
30 FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
31 COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
32 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
33 BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
34 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
35 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
36 LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
37 ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
38 POSSIBILITY OF SUCH DAMAGE.
39*/
40
45template< typename T, const int LX, const int CHUNKS >
47 const T * __restrict__ u,
48 const T * __restrict__ vx,
49 const T * __restrict__ vy,
50 const T * __restrict__ vz,
51 const T * __restrict__ dx,
52 const T * __restrict__ dy,
53 const T * __restrict__ dz,
54 const T * __restrict__ drdx,
55 const T * __restrict__ dsdx,
56 const T * __restrict__ dtdx,
57 const T * __restrict__ drdy,
58 const T * __restrict__ dsdy,
59 const T * __restrict__ dtdy,
60 const T * __restrict__ drdz,
61 const T * __restrict__ dsdz,
62 const T * __restrict__ dtdz,
63 const T * __restrict__ jacinv) {
64
65 __shared__ T shu[LX * LX * LX];
66
67 __shared__ T shvx[LX * LX * LX];
68 __shared__ T shvy[LX * LX * LX];
69 __shared__ T shvz[LX * LX * LX];
70
74
76
77 const int e = blockIdx.x;
78 const int iii = threadIdx.x;
79 const int nchunks = (LX * LX * LX - 1) / CHUNKS + 1;
80 const int ele = e*LX*LX*LX;
81
82 if (iii < (LX * LX)) {
83 shdx[iii] = dx[iii];
84 shdy[iii] = dy[iii];
85 shdz[iii] = dz[iii];
86 }
87
88 int l = iii;
89 while(l < (LX * LX * LX)) {
90 shu[l] = u[l + ele];
91
92 shvx[l] = vx[l + ele];
93 shvy[l] = vy[l + ele];
94 shvz[l] = vz[l + ele];
95
96 shjacinv[l] = jacinv[l + ele];
97
98 l = l + CHUNKS;
99 }
100
102
103 for (int n = 0; n < nchunks; n++) {
104 const int ijk = iii + n * CHUNKS;
105 const int jk = ijk / LX;
106 const int i = ijk - jk * LX;
107 const int k = jk / LX;
108 const int j = jk - k * LX;
109 if ( i < LX && j < LX && k < LX) {
110 T rtmp = 0.0;
111 T stmp = 0.0;
112 T ttmp = 0.0;
113 for (int l = 0; l < LX; l++) {
114 rtmp += shdx[i + l * LX] * shu[l + j * LX + k * LX * LX];
115 stmp += shdy[j + l * LX] * shu[i + l * LX + k * LX * LX];
116 ttmp += shdz[k + l * LX] * shu[i + j * LX + l * LX * LX];
117 }
118
119 du[ijk + e * LX * LX * LX] = shjacinv[ijk] *
120 (shvx[ijk] * (drdx[ijk + ele] * rtmp
121 + dsdx[ijk + ele] * stmp
122 + dtdx[ijk + ele] * ttmp)
123 + shvy[ijk] * (drdy[ijk + ele] * rtmp
124 + dsdy[ijk + ele] * stmp
125 + dtdy[ijk + ele] * ttmp)
126 + shvz[ijk] * (drdz[ijk + ele] * rtmp
127 + dsdz[ijk + ele] * stmp
128 + dtdz[ijk + ele] * ttmp));
129 }
130 }
131}
132
133template< typename T, const int LX, const int EB >
136 const T * __restrict__ u,
153 const int nelv) {
154
155 __shared__ T shu[EB * LX * LX];
156
160
161 static_assert(sizeof(shu) +
162 sizeof(shdx) +
163 sizeof(shdy) +
164 sizeof(shdz)
166 "kstep block exceeds the shared memory budget");
167
168 const int eb = (EB == 1) ? 0 : threadIdx.z;
169 const int e_blk = blockIdx.x * EB + eb;
170 /* Threads past the last element still have to reach the barriers in
171 the k loop, so clamp their reads and drop their stores rather than
172 returning early. At EB == 1 this all constant folds away */
173 const bool active = (EB == 1) ? true : (e_blk < nelv);
174 const int e = active ? e_blk : (nelv - 1);
175 const int sh = eb * LX * LX;
176 const int j = threadIdx.y;
177 const int i = threadIdx.x;
178 const int ij = i + j * LX;
179 const int ele = e*LX*LX*LX;
180
181 if (eb == 0) {
182 shdx[ij] = dx[ij];
183 shdy[ij] = dy[ij];
184 shdz[ij] = dz[ij];
185 }
186
192
193#pragma unroll LX
194 for (int k = 0; k < LX; ++k) {
195 ru[k] = u[ij + k*LX*LX + ele];
196 rvx[k] = vx[ij + k*LX*LX + ele];
197 rvy[k] = vy[ij + k*LX*LX + ele];
198 rvz[k] = vz[ij + k*LX*LX + ele];
199 rjacinv[k] = jacinv[ij + k*LX*LX + ele];
200 }
201
203
204#pragma unroll
205 for (int k = 0; k < LX; ++k) {
206 const int ijk = ij + k*LX*LX;
207 T ttmp = 0.0;
208 shu[sh + ij] = ru[k];
209#pragma unroll
210 for (int l = 0; l < LX; l++) {
211 ttmp += shdz[k+l*LX] * ru[l];
212 }
214
215 T rtmp = 0.0;
216 T stmp = 0.0;
217#pragma unroll
218 for (int l = 0; l < LX; l++) {
219 rtmp += shdx[i+l*LX] * shu[sh + l+j*LX];
220 stmp += shdy[j+l*LX] * shu[sh + i+l*LX];
221 }
222
223 if (active) {
224 du[ijk + ele] = rjacinv[k] *
225 (rvx[k] * (drdx[ijk + ele] * rtmp
226 + dsdx[ijk + ele] * stmp
227 + dtdx[ijk + ele] * ttmp)
228 + rvy[k] * (drdy[ijk + ele] * rtmp
229 + dsdy[ijk + ele] * stmp
230 + dtdy[ijk + ele] * ttmp)
231 + rvz[k] * (drdz[ijk + ele] * rtmp
232 + dsdz[ijk + ele] * stmp
233 + dtdz[ijk + ele] * ttmp));
234 }
236 }
237}
238
239
240
257#if defined(__CUDA_ARCH__) && (__CUDA_ARCH__ >= 800) && (__CUDA_ARCH__ < 1000)
258
259template< const int LX, const int NW >
261void conv1_dmma_elem(double * __restrict__ du,
262 const double * __restrict__ u,
263 const double * __restrict__ vx,
264 const double * __restrict__ vy,
265 const double * __restrict__ vz,
266 const double * __restrict__ dx,
267 const double * __restrict__ dy,
268 const double * __restrict__ dz,
269 const double * __restrict__ drdx,
270 const double * __restrict__ dsdx,
271 const double * __restrict__ dtdx,
272 const double * __restrict__ drdy,
273 const double * __restrict__ dsdy,
274 const double * __restrict__ dtdy,
275 const double * __restrict__ drdz,
276 const double * __restrict__ dsdz,
277 const double * __restrict__ dtdz,
278 const double * __restrict__ jacinv,
279 const int nelv) {
280
281 /* Element independent, one copy per block. Block diagonal when more than
282 one element is packed: one LX x LX copy of D per sub-cube */
284 __shared__ __align__(16) double shdy[DMMA_MAT];
285 __shared__ __align__(16) double shdz[DMMA_MAT];
286
287 /* The pack, padded to DMMA_P^3. shu carries the input, shr, shs and sht
288 the reference derivatives */
289 __shared__ __align__(16) double shu[DMMA_CUBE];
290 __shared__ __align__(16) double shr[DMMA_CUBE];
291 __shared__ __align__(16) double shs[DMMA_CUBE];
292 __shared__ __align__(16) double sht[DMMA_CUBE];
293
295 sizeof(shdy) +
296 sizeof(shdz) +
297 sizeof(shu) +
298 sizeof(shr) +
299 sizeof(shs) +
300 sizeof(sht)
303
304 /* Elements per sub-cube axis, and per cube, see the note in dmma_kernel.h */
305 enum { PPA = (DMMA_P % LX == 0) ? (DMMA_P / LX) : 1,
306 PACK = PPA * PPA * PPA,
307 LX3 = LX * LX * LX,
308 NP = PACK * LX3 };
309
311
312 const int nthrds = 32 * NW;
313 const int tid = threadIdx.x;
314 const int wf = tid >> 5;
315 const int ebase = pack::ebase();
316
317 /* The padding has to be finite, see the note in dmma_kernel.h. At
318 LX == DMMA_P with one element packed there is none and this is folded
319 away */
320 if (PACK * LX3 < DMMA_CUBE) {
321 for (int p = tid; p < DMMA_CUBE; p += nthrds) {
322 shu[p] = 0.0;
323 }
324 }
325 if (LX < DMMA_P) {
326 for (int p = tid; p < DMMA_MAT; p += nthrds) {
327 shdx[p] = 0.0;
328 shdy[p] = 0.0;
329 shdz[p] = 0.0;
330 }
331 }
332 if (LX < DMMA_P) {
334 }
335
336 /* One copy of D per sub-cube, down the diagonal */
337 for (int p = tid; p < LX * LX; p += nthrds) {
338 const int i = p % LX;
339 const int l = p / LX;
340#pragma unroll
341 for (int b = 0; b < PPA; b++) {
342 const int m = (b * LX + i) + DMMA_P * (b * LX + l);
343 shdx[m] = dx[p];
344 shdy[m] = dy[p];
345 shdz[m] = dz[p];
346 }
347 }
348
349 for (int p = tid; p < NP; p += nthrds) {
350 const dmma_idx x = pack::map(p, ebase, nelv);
351
352 shu[x.c] = u[x.g];
353 }
354
356
360
362
363 /* Thirteen factor cubes for three contractions: the convecting velocity,
364 jacinv and the nine metrics all stream from global here, exactly as the
365 seven geometric factors do in the scalar axhelm dmma kernel */
366 for (int p = tid; p < NP; p += nthrds) {
367 const dmma_idx x = pack::map(p, ebase, nelv);
368
369 if (x.live) {
370 const int c = x.c;
371 const int gp = x.g;
372 const double rtmp = shr[c];
373 const double stmp = shs[c];
374 const double ttmp = sht[c];
375
376 du[gp] = jacinv[gp] *
377 (vx[gp] * (drdx[gp] * rtmp
378 + dsdx[gp] * stmp
379 + dtdx[gp] * ttmp)
380 + vy[gp] * (drdy[gp] * rtmp
381 + dsdy[gp] * stmp
382 + dtdy[gp] * ttmp)
383 + vz[gp] * (drdz[gp] * rtmp
384 + dsdz[gp] * stmp
385 + dtdz[gp] * ttmp));
386 }
387 }
388}
389
390#endif // __CUDA_ARCH__ in [800, 1000)
391
392/*
393 * Compile-time dispatch onto the DMMA element kernel. The launch macros in
394 * opr_conv1.cu are written for every LX the operator dispatches and for
395 * whatever `real` is, so every combination has to compile; the ones the
396 * strategy does not cover -- single precision, LX outside the supported
397 * range, a build without an fp64 tensor core arch -- resolve to this no-op.
398 * The autotuner never selects the strategy for them, see dmma_lx_supported()
399 * and cuda_have_dmma() in dmma_kernel.h.
400 */
401template< typename T, const int LX, const int NW >
404 const T * __restrict__, const T * __restrict__,
405 const T * __restrict__, const T * __restrict__,
406 const T * __restrict__, const T * __restrict__,
407 const T * __restrict__, const T * __restrict__,
408 const T * __restrict__, const T * __restrict__,
409 const T * __restrict__, const T * __restrict__,
410 const T * __restrict__, const T * __restrict__,
411 const T * __restrict__, const T * __restrict__,
412 const T * __restrict__,
413 const int) { }
414};
415
416#if defined(__CUDA_ARCH__) && (__CUDA_ARCH__ >= 800) && (__CUDA_ARCH__ < 1000)
417
418/* Keep in sync with dmma_lx_supported() in dmma_kernel.h */
419#define NEKO_CONV1_DMMA_DISPATCH(LXV) \
420 template< const int NW > \
421 struct conv1_dmma_dispatch< double, LXV, NW > { \
422 __device__ static void run(double * __restrict__ du, \
423 const double * __restrict__ u, \
424 const double * __restrict__ vx, \
425 const double * __restrict__ vy, \
426 const double * __restrict__ vz, \
427 const double * __restrict__ dx, \
428 const double * __restrict__ dy, \
429 const double * __restrict__ dz, \
430 const double * __restrict__ drdx, \
431 const double * __restrict__ dsdx, \
432 const double * __restrict__ dtdx, \
433 const double * __restrict__ drdy, \
434 const double * __restrict__ dsdy, \
435 const double * __restrict__ dtdy, \
436 const double * __restrict__ drdz, \
437 const double * __restrict__ dsdz, \
438 const double * __restrict__ dtdz, \
439 const double * __restrict__ jacinv, \
440 const int nelv) { \
441 conv1_dmma_elem< LXV, NW >(du, u, vx, vy, vz, dx, dy, dz, \
442 drdx, dsdx, dtdx, drdy, dsdy, dtdy, \
443 drdz, dsdz, dtdz, jacinv, nelv); \
444 } \
445 }
446
454
455#endif // __CUDA_ARCH__ in [800, 1000)
456
457template< typename T, const int LX, const int NW >
460 const T * __restrict__ u,
461 const T * __restrict__ vx,
462 const T * __restrict__ vy,
463 const T * __restrict__ vz,
464 const T * __restrict__ dx,
465 const T * __restrict__ dy,
466 const T * __restrict__ dz,
467 const T * __restrict__ drdx,
468 const T * __restrict__ dsdx,
469 const T * __restrict__ dtdx,
470 const T * __restrict__ drdy,
471 const T * __restrict__ dsdy,
472 const T * __restrict__ dtdy,
473 const T * __restrict__ drdz,
474 const T * __restrict__ dsdz,
475 const T * __restrict__ dtdz,
476 const T * __restrict__ jacinv,
477 const int nelv) {
478
480 drdx, dsdx, dtdx, drdy, dsdy, dtdy,
481 drdz, dsdz, dtdz, jacinv, nelv);
482}
483
508#if defined(__CUDA_ARCH__) && (__CUDA_ARCH__ >= 900) && \
509 (__CUDA_ARCH__ < 1000) && NEKO_TMA_TOOLKIT
510
511template< const int LX, const int NW >
513void conv1_dmma_tma_elem(double * __restrict__ du,
514 const double * __restrict__ u,
515 const double * __restrict__ vx,
516 const double * __restrict__ vy,
517 const double * __restrict__ vz,
518 const double * __restrict__ dx,
519 const double * __restrict__ dy,
520 const double * __restrict__ dz,
521 const double * __restrict__ drdx,
522 const double * __restrict__ dsdx,
523 const double * __restrict__ dtdx,
524 const double * __restrict__ drdy,
525 const double * __restrict__ dsdy,
526 const double * __restrict__ dtdy,
527 const double * __restrict__ drdz,
528 const double * __restrict__ dsdz,
529 const double * __restrict__ dtdz,
530 const double * __restrict__ jacinv) {
531
532 /* Only lx == DMMA_P stages as a contiguous run of bytes, which is what a
533 bulk copy moves; see the scope note in dmma_tma_kernel.h. Keep in step
534 with dmma_tma_conv1_lx_supported() */
535 static_assert(LX == DMMA_P,
536 "the dmma tma variant stages whole cubes only");
537
541
542 enum { CUBE_BYTES = DMMA_CUBE * (int) sizeof(double) };
543
544 const int nthrds = 32 * NW;
545 const int tid = threadIdx.x;
546 const int wf = tid >> 5;
547 const int ebase = blockIdx.x * DMMA_CUBE;
548
549 if (tid == 0) {
550 tma_barrier_init(&sm.bar_u, 1);
551 tma_barrier_init(&sm.bar_g, 1);
552 }
553
554 /* At LX == DMMA_P the derivative matrix fills the staged one exactly, and
555 there is no padding anywhere to zero */
556 for (int p = tid; p < DMMA_MAT; p += nthrds) {
557 sm.dx[p] = dx[p];
558 sm.dy[p] = dy[p];
559 sm.dz[p] = dz[p];
560 }
561
562 /* Both barriers initialised and every derivative matrix staged before
563 anyone waits on the one or contracts with the other */
565
566 if (tid == 0) {
567 tma_expect(&sm.bar_u, CUBE_BYTES);
568 tma_load(sm.u, u + ebase, CUBE_BYTES, &sm.bar_u);
569
571 tma_load(sm.g[0], vx + ebase, CUBE_BYTES, &sm.bar_g);
572 tma_load(sm.g[1], vy + ebase, CUBE_BYTES, &sm.bar_g);
573 tma_load(sm.g[2], vz + ebase, CUBE_BYTES, &sm.bar_g);
574 tma_load(sm.g[3], jacinv + ebase, CUBE_BYTES, &sm.bar_g);
575 tma_load(sm.g[4], drdx + ebase, CUBE_BYTES, &sm.bar_g);
576 tma_load(sm.g[5], dsdx + ebase, CUBE_BYTES, &sm.bar_g);
577 tma_load(sm.g[6], dtdx + ebase, CUBE_BYTES, &sm.bar_g);
578 tma_load(sm.g[7], drdy + ebase, CUBE_BYTES, &sm.bar_g);
579 tma_load(sm.g[8], dsdy + ebase, CUBE_BYTES, &sm.bar_g);
580 tma_load(sm.g[9], dtdy + ebase, CUBE_BYTES, &sm.bar_g);
581 tma_load(sm.g[10], drdz + ebase, CUBE_BYTES, &sm.bar_g);
582 tma_load(sm.g[11], dsdz + ebase, CUBE_BYTES, &sm.bar_g);
583 tma_load(sm.g[12], dtdz + ebase, CUBE_BYTES, &sm.bar_g);
584 }
585
586 /* u only. The thirteen factor cubes are still arriving */
587 tma_wait(&sm.bar_u, 0);
588
592
594
595 tma_wait(&sm.bar_g, 0);
596
597 /* The staged input is dead once the contractions have been read out of it,
598 which the barrier above guarantees, so the result is formed in it and
599 leaves as one bulk store rather than DMMA_CUBE scalar ones */
600 for (int p = tid; p < DMMA_CUBE; p += nthrds) {
601 const double rtmp = sm.r[p];
602 const double stmp = sm.s[p];
603 const double ttmp = sm.t[p];
604
605 sm.u[p] = sm.g[3][p] *
606 (sm.g[0][p] * (sm.g[4][p] * rtmp
607 + sm.g[5][p] * stmp
608 + sm.g[6][p] * ttmp)
609 + sm.g[1][p] * (sm.g[7][p] * rtmp
610 + sm.g[8][p] * stmp
611 + sm.g[9][p] * ttmp)
612 + sm.g[2][p] * (sm.g[10][p] * rtmp
613 + sm.g[11][p] * stmp
614 + sm.g[12][p] * ttmp));
615 }
616
617 /* The pointwise pass wrote sm.u through the generic proxy and the bulk store
618 reads it through the async one, so the fence is needed on top of the
619 barrier; see tma_fence_shared() */
622
623 if (tid == 0) {
624 tma_store(du + ebase, sm.u, CUBE_BYTES);
626 }
627
628 /* The store reads sm.u asynchronously, and shared memory lives only as long
629 as the block does: nothing may retire until it has been read out */
631}
632
633#endif // __CUDA_ARCH__ == sm_90 with a CUDA 12 toolkit
634
635/*
636 * Compile-time dispatch onto the TMA staged DMMA element kernel, see the note
637 * on conv1_dmma_dispatch above. The no-op covers everything the strategy does
638 * not: single precision, any lx but DMMA_P, a build without sm_90, and a
639 * toolkit older than CUDA 12.
640 */
641template< typename T, const int LX, const int NW >
644 const T * __restrict__, const T * __restrict__,
645 const T * __restrict__, const T * __restrict__,
646 const T * __restrict__, const T * __restrict__,
647 const T * __restrict__, const T * __restrict__,
648 const T * __restrict__, const T * __restrict__,
649 const T * __restrict__, const T * __restrict__,
650 const T * __restrict__, const T * __restrict__,
651 const T * __restrict__, const T * __restrict__,
652 const T * __restrict__) { }
653};
654
655#if defined(__CUDA_ARCH__) && (__CUDA_ARCH__ >= 900) && \
656 (__CUDA_ARCH__ < 1000) && NEKO_TMA_TOOLKIT
657
658/* Keep in sync with dmma_tma_conv1_lx_supported() in dmma_tma_kernel.h */
659#define NEKO_CONV1_DMMA_TMA_DISPATCH(LXV) \
660 template< const int NW > \
661 struct conv1_dmma_tma_dispatch< double, LXV, NW > { \
662 __device__ static void run(double * __restrict__ du, \
663 const double * __restrict__ u, \
664 const double * __restrict__ vx, \
665 const double * __restrict__ vy, \
666 const double * __restrict__ vz, \
667 const double * __restrict__ dx, \
668 const double * __restrict__ dy, \
669 const double * __restrict__ dz, \
670 const double * __restrict__ drdx, \
671 const double * __restrict__ dsdx, \
672 const double * __restrict__ dtdx, \
673 const double * __restrict__ drdy, \
674 const double * __restrict__ dsdy, \
675 const double * __restrict__ dtdy, \
676 const double * __restrict__ drdz, \
677 const double * __restrict__ dsdz, \
678 const double * __restrict__ dtdz, \
679 const double * __restrict__ jacinv) { \
680 conv1_dmma_tma_elem< LXV, NW >(du, u, vx, vy, vz, dx, dy, dz, \
681 drdx, dsdx, dtdx, drdy, dsdy, dtdy, \
682 drdz, dsdz, dtdz, jacinv); \
683 } \
684 }
685
687
688#endif // __CUDA_ARCH__ == sm_90 with a CUDA 12 toolkit
689
690template< typename T, const int LX, const int NW >
693 const T * __restrict__ u,
694 const T * __restrict__ vx,
695 const T * __restrict__ vy,
696 const T * __restrict__ vz,
697 const T * __restrict__ dx,
698 const T * __restrict__ dy,
699 const T * __restrict__ dz,
700 const T * __restrict__ drdx,
701 const T * __restrict__ dsdx,
702 const T * __restrict__ dtdx,
703 const T * __restrict__ drdy,
704 const T * __restrict__ dsdy,
705 const T * __restrict__ dtdy,
706 const T * __restrict__ drdz,
707 const T * __restrict__ dsdz,
708 const T * __restrict__ dtdz,
709 const T * __restrict__ jacinv) {
710
712 drdx, dsdx, dtdx,
713 drdy, dsdy, dtdy,
714 drdz, dsdz, dtdz, jacinv);
715}
716
717/*
718 * Opt into the TMA variant's dynamic allocation, once per specialisation; see
719 * the note on opgrad_dmma_tma_optin() in opgrad_kernel.h. The tuner has
720 * already ruled the device out via cuda_have_tma_conv1(), which is a larger
721 * request than opgrad's and is queried separately.
722 */
723template< typename T, const int LX, const int NW >
724static inline bool conv1_dmma_tma_optin()
725{
726 static int state = -1;
727
728 if (state < 0) {
729 const void * const fn =
734
735 if (err == cudaSuccess) {
739 }
740 state = (err == cudaSuccess) ? 1 : 0;
741 if (state == 0) {
743 }
744 }
745 return state == 1;
746}
747
748#endif // __MATH_CONV1_KERNEL_H__
__global__ void ale_add_kinematics_kernel(const int n, T *__restrict__ wx, T *__restrict__ wy, T *__restrict__ wz, const T *__restrict__ x_ref, const T *__restrict__ y_ref, const T *__restrict__ z_ref, const T *__restrict__ phi, const T *__restrict__ x, const T *__restrict__ y, const T *__restrict__ z, const kinematics_params_t kin_params)
__shared__ T shu[LX *LX]
__global__ void const T *__restrict__ x
const bool active
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dz
T rvy[LX]
const int sh
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ jacinv
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dy
T ru[LX]
const int eb
__shared__ T shdy[LX *LX]
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ drdx
const int i
T rvx[LX]
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dx
const int ij
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const int nelv
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dtdx
T rvz[LX]
T rjacinv[LX]
__shared__ T shdx[LX *LX]
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dtdz
const int e
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dsdx
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dtdy
static bool conv1_dmma_tma_optin()
__shared__ T shdz[LX *LX]
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dsdz
const int e_blk
__global__ void conv1_kernel_1d(T *__restrict__ du, const T *__restrict__ u, const T *__restrict__ vx, const T *__restrict__ vy, const T *__restrict__ vz, const T *__restrict__ dx, const T *__restrict__ dy, const T *__restrict__ dz, const T *__restrict__ drdx, const T *__restrict__ dsdx, const T *__restrict__ dtdx, const T *__restrict__ drdy, const T *__restrict__ dsdy, const T *__restrict__ dtdy, const T *__restrict__ drdz, const T *__restrict__ dsdz, const T *__restrict__ dtdz, const T *__restrict__ jacinv)
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ vz
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ dsdy
const int ele
__global__ void const T *__restrict__ const T *__restrict__ vx
__global__ void const T *__restrict__ u
const int j
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ drdy
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ vy
__syncthreads()
__global__ void const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ const T *__restrict__ drdz
#define NEKO_EB_MAX_SMEM
Definition elem_block.h:60
#define NEKO_EB_BOUNDS(NT)
Definition elem_block.h:95
@ DMMA_CUBE
@ DMMA_MAT
@ DMMA_P
#define NEKO_CONV1_TMA_SMEM
#define DMMA_NG_CONV1
static __device__ void run(T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const int)
static __device__ void run(T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__, const T *__restrict__)