diff options
author | Alyssa Rosenzweig <alyssa@rosenzweig.io> | 2023-05-11 09:58:39 -0400 |
---|---|---|
committer | Marge Bot <emma+marge@anholt.net> | 2023-05-12 20:39:46 +0000 |
commit | ee6ddce6361d761909d36a9cb2a4d851c6f6fb52 (patch) | |
tree | 33542a9d66cb596f648487d848afce941b8d767d /src/freedreno | |
parent | 6ff97776b77b3eb8446fd274913d808c146d1d9d (diff) | |
download | mesa-ee6ddce6361d761909d36a9cb2a4d851c6f6fb52.tar.gz |
ir3: Use unified atomics
Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
Reviewed-by: Jesse Natalie <jenatali@microsoft.com>
Reviewed-by: Rob Clark <robclark@freedesktop.org>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/22914>
Diffstat (limited to 'src/freedreno')
-rw-r--r-- | src/freedreno/ir3/ir3_a4xx.c | 118 | ||||
-rw-r--r-- | src/freedreno/ir3/ir3_a6xx.c | 151 | ||||
-rw-r--r-- | src/freedreno/ir3/ir3_compiler_nir.c | 84 | ||||
-rw-r--r-- | src/freedreno/ir3/ir3_image.c | 31 | ||||
-rw-r--r-- | src/freedreno/ir3/ir3_nir.c | 15 | ||||
-rw-r--r-- | src/freedreno/ir3/ir3_nir_lower_64b.c | 43 | ||||
-rw-r--r-- | src/freedreno/ir3/ir3_nir_lower_io_offsets.c | 24 |
7 files changed, 148 insertions, 318 deletions
diff --git a/src/freedreno/ir3/ir3_a4xx.c b/src/freedreno/ir3/ir3_a4xx.c index 5a87078aa11..3c3489bb0f6 100644 --- a/src/freedreno/ir3/ir3_a4xx.c +++ b/src/freedreno/ir3/ir3_a4xx.c @@ -126,6 +126,40 @@ emit_intrinsic_store_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) array_insert(b, b->keeps, stgb); } +static struct ir3_instruction * +emit_atomic(struct ir3_block *b, + nir_atomic_op op, + struct ir3_instruction *bo, + struct ir3_instruction *data, + struct ir3_instruction *offset, + struct ir3_instruction *byte_offset) +{ + switch (op) { + case nir_atomic_op_iadd: + return ir3_ATOMIC_S_ADD(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_imin: + return ir3_ATOMIC_S_MIN(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_umin: + return ir3_ATOMIC_S_MIN(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_imax: + return ir3_ATOMIC_S_MAX(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_umax: + return ir3_ATOMIC_S_MAX(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_iand: + return ir3_ATOMIC_S_AND(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_ior: + return ir3_ATOMIC_S_OR(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_ixor: + return ir3_ATOMIC_S_XOR(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_xchg: + return ir3_ATOMIC_S_XCHG(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + case nir_atomic_op_cmpxchg: + return ir3_ATOMIC_S_CMPXCHG(b, bo, 0, data, 0, offset, 0, byte_offset, 0); + default: + unreachable("boo"); + } +} + /* * SSBO atomic intrinsics * @@ -140,7 +174,7 @@ emit_intrinsic_store_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) * 1: The byte offset into the SSBO buffer of the variable that the atomic * operation will operate on. * 2: The data parameter to the atomic function (i.e. the value to add - * in ssbo_atomic_add, etc). + * in, etc). * 3: CompSwap: the second data parameter. * Non-CompSwap: The dword offset into the SSBO buffer variable. * 4: CompSwap: The dword offset into the SSBO buffer variable. @@ -152,8 +186,8 @@ static struct ir3_instruction * emit_intrinsic_atomic_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) { struct ir3_block *b = ctx->block; - struct ir3_instruction *atomic; - type_t type = TYPE_U32; + nir_atomic_op op = nir_intrinsic_atomic_op(intr); + type_t type = nir_atomic_op_type(op) == nir_type_int ? TYPE_S32 : TYPE_U32; struct ir3_instruction *ssbo = ir3_ssbo_to_ibo(ctx, intr->src[0]); @@ -161,50 +195,18 @@ emit_intrinsic_atomic_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) /* 64b byte offset */ struct ir3_instruction *byte_offset = byte_offset_to_address(ctx, &intr->src[0], ir3_get_src(ctx, &intr->src[1])[0]); - /* dword offset for everything but comp_swap */ + /* dword offset for everything but cmpxchg */ struct ir3_instruction *src3 = ir3_get_src(ctx, &intr->src[3])[0]; - switch (intr->intrinsic) { - case nir_intrinsic_ssbo_atomic_add_ir3: - atomic = ir3_ATOMIC_S_ADD(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_imin_ir3: - atomic = ir3_ATOMIC_S_MIN(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - type = TYPE_S32; - break; - case nir_intrinsic_ssbo_atomic_umin_ir3: - atomic = ir3_ATOMIC_S_MIN(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_imax_ir3: - atomic = ir3_ATOMIC_S_MAX(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - type = TYPE_S32; - break; - case nir_intrinsic_ssbo_atomic_umax_ir3: - atomic = ir3_ATOMIC_S_MAX(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_and_ir3: - atomic = ir3_ATOMIC_S_AND(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_or_ir3: - atomic = ir3_ATOMIC_S_OR(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_xor_ir3: - atomic = ir3_ATOMIC_S_XOR(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_exchange_ir3: - atomic = ir3_ATOMIC_S_XCHG(b, ssbo, 0, data, 0, src3, 0, byte_offset, 0); - break; - case nir_intrinsic_ssbo_atomic_comp_swap_ir3: + if (op == nir_atomic_op_cmpxchg) { /* for cmpxchg, src0 is [ui]vec2(data, compare): */ data = ir3_collect(b, src3, data); - struct ir3_instruction *dword_offset = ir3_get_src(ctx, &intr->src[4])[0]; - atomic = ir3_ATOMIC_S_CMPXCHG(b, ssbo, 0, data, 0, dword_offset, 0, - byte_offset, 0); - break; - default: - unreachable("boo"); + src3 = ir3_get_src(ctx, &intr->src[4])[0]; } + struct ir3_instruction *atomic = + emit_atomic(b, op, ssbo, data, src3, byte_offset); + atomic->cat6.iim_val = 1; atomic->cat6.d = 4; atomic->cat6.type = type; @@ -369,6 +371,7 @@ emit_intrinsic_atomic_image(struct ir3_context *ctx, nir_intrinsic_instr *intr) struct ir3_instruction *const *coords = ir3_get_src(ctx, &intr->src[1]); struct ir3_instruction *image = ir3_image_to_ibo(ctx, intr->src[0]); unsigned ncoords = ir3_get_image_coords(intr, NULL); + nir_atomic_op op = nir_intrinsic_atomic_op(intr); /* src0 is value (or uvec2(value, compare)) * src1 is coords @@ -378,39 +381,10 @@ emit_intrinsic_atomic_image(struct ir3_context *ctx, nir_intrinsic_instr *intr) src1 = ir3_create_collect(b, coords, ncoords); src2 = get_image_offset(ctx, intr, coords, ctx->compiler->gen == 4); - switch (intr->intrinsic) { - case nir_intrinsic_image_atomic_add: - atomic = ir3_ATOMIC_S_ADD(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_imin: - case nir_intrinsic_image_atomic_umin: - atomic = ir3_ATOMIC_S_MIN(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_imax: - case nir_intrinsic_image_atomic_umax: - atomic = ir3_ATOMIC_S_MAX(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_and: - atomic = ir3_ATOMIC_S_AND(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_or: - atomic = ir3_ATOMIC_S_OR(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_xor: - atomic = ir3_ATOMIC_S_XOR(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_exchange: - atomic = ir3_ATOMIC_S_XCHG(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - case nir_intrinsic_image_atomic_comp_swap: - /* for cmpxchg, src0 is [ui]vec2(data, compare): */ + if (op == nir_atomic_op_cmpxchg) src0 = ir3_collect(b, ir3_get_src(ctx, &intr->src[4])[0], src0); - atomic = ir3_ATOMIC_S_CMPXCHG(b, image, 0, src0, 0, src1, 0, src2, 0); - break; - default: - unreachable("boo"); - } + atomic = emit_atomic(b, op, image, src0, src1, src2); atomic->cat6.iim_val = 1; atomic->cat6.d = ncoords; atomic->cat6.type = ir3_get_type_for_image_intrinsic(intr); diff --git a/src/freedreno/ir3/ir3_a6xx.c b/src/freedreno/ir3/ir3_a6xx.c index d5314c54ef5..c45f6108a32 100644 --- a/src/freedreno/ir3/ir3_a6xx.c +++ b/src/freedreno/ir3/ir3_a6xx.c @@ -89,6 +89,39 @@ emit_intrinsic_store_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) array_insert(b, b->keeps, stib); } +static struct ir3_instruction * +emit_atomic(struct ir3_block *b, + nir_atomic_op op, + struct ir3_instruction *ibo, + struct ir3_instruction *src0, + struct ir3_instruction *src1) +{ + switch (op) { + case nir_atomic_op_iadd: + return ir3_ATOMIC_B_ADD(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_imin: + return ir3_ATOMIC_B_MIN(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_umin: + return ir3_ATOMIC_B_MIN(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_imax: + return ir3_ATOMIC_B_MAX(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_umax: + return ir3_ATOMIC_B_MAX(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_iand: + return ir3_ATOMIC_B_AND(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_ior: + return ir3_ATOMIC_B_OR(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_ixor: + return ir3_ATOMIC_B_XOR(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_xchg: + return ir3_ATOMIC_B_XCHG(b, ibo, 0, src0, 0, src1, 0); + case nir_atomic_op_cmpxchg: + return ir3_ATOMIC_B_CMPXCHG(b, ibo, 0, src0, 0, src1, 0); + default: + unreachable("boo"); + } +} + /* * SSBO atomic intrinsics * @@ -103,7 +136,7 @@ emit_intrinsic_store_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) * 1: The offset into the SSBO buffer of the variable that the atomic * operation will operate on. * 2: The data parameter to the atomic function (i.e. the value to add - * in ssbo_atomic_add, etc). + * in, etc). * 3: For CompSwap only: the second data parameter. */ static struct ir3_instruction * @@ -111,7 +144,8 @@ emit_intrinsic_atomic_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) { struct ir3_block *b = ctx->block; struct ir3_instruction *atomic, *ibo, *src0, *src1, *data, *dummy; - type_t type = TYPE_U32; + nir_atomic_op op = nir_intrinsic_atomic_op(intr); + type_t type = nir_atomic_op_type(op) == nir_type_int ? TYPE_S32 : TYPE_U32; ibo = ir3_ssbo_to_ibo(ctx, intr->src[0]); @@ -133,7 +167,7 @@ emit_intrinsic_atomic_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) */ dummy = create_immed(b, 0); - if (intr->intrinsic == nir_intrinsic_ssbo_atomic_comp_swap_ir3) { + if (op == nir_atomic_op_cmpxchg) { src0 = ir3_get_src(ctx, &intr->src[4])[0]; struct ir3_instruction *compare = ir3_get_src(ctx, &intr->src[3])[0]; src1 = ir3_collect(b, dummy, compare, data); @@ -142,43 +176,7 @@ emit_intrinsic_atomic_ssbo(struct ir3_context *ctx, nir_intrinsic_instr *intr) src1 = ir3_collect(b, dummy, data); } - switch (intr->intrinsic) { - case nir_intrinsic_ssbo_atomic_add_ir3: - atomic = ir3_ATOMIC_B_ADD(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_imin_ir3: - atomic = ir3_ATOMIC_B_MIN(b, ibo, 0, src0, 0, src1, 0); - type = TYPE_S32; - break; - case nir_intrinsic_ssbo_atomic_umin_ir3: - atomic = ir3_ATOMIC_B_MIN(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_imax_ir3: - atomic = ir3_ATOMIC_B_MAX(b, ibo, 0, src0, 0, src1, 0); - type = TYPE_S32; - break; - case nir_intrinsic_ssbo_atomic_umax_ir3: - atomic = ir3_ATOMIC_B_MAX(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_and_ir3: - atomic = ir3_ATOMIC_B_AND(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_or_ir3: - atomic = ir3_ATOMIC_B_OR(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_xor_ir3: - atomic = ir3_ATOMIC_B_XOR(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_exchange_ir3: - atomic = ir3_ATOMIC_B_XCHG(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_ssbo_atomic_comp_swap_ir3: - atomic = ir3_ATOMIC_B_CMPXCHG(b, ibo, 0, src0, 0, src1, 0); - break; - default: - unreachable("boo"); - } - + atomic = emit_atomic(b, op, ibo, src0, src1); atomic->cat6.iim_val = 1; atomic->cat6.d = 1; atomic->cat6.type = type; @@ -259,6 +257,7 @@ emit_intrinsic_atomic_image(struct ir3_context *ctx, nir_intrinsic_instr *intr) struct ir3_instruction *const *coords = ir3_get_src(ctx, &intr->src[1]); struct ir3_instruction *value = ir3_get_src(ctx, &intr->src[3])[0]; unsigned ncoords = ir3_get_image_coords(intr, NULL); + nir_atomic_op op = nir_intrinsic_atomic_op(intr); ibo = ir3_image_to_ibo(ctx, intr->src[0]); @@ -277,55 +276,14 @@ emit_intrinsic_atomic_image(struct ir3_context *ctx, nir_intrinsic_instr *intr) dummy = create_immed(b, 0); src0 = ir3_create_collect(b, coords, ncoords); - if (intr->intrinsic == nir_intrinsic_image_atomic_comp_swap || - intr->intrinsic == nir_intrinsic_bindless_image_atomic_comp_swap) { + if (op == nir_atomic_op_cmpxchg) { struct ir3_instruction *compare = ir3_get_src(ctx, &intr->src[4])[0]; src1 = ir3_collect(b, dummy, compare, value); } else { src1 = ir3_collect(b, dummy, value); } - switch (intr->intrinsic) { - case nir_intrinsic_image_atomic_add: - case nir_intrinsic_bindless_image_atomic_add: - atomic = ir3_ATOMIC_B_ADD(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_imin: - case nir_intrinsic_image_atomic_umin: - case nir_intrinsic_bindless_image_atomic_imin: - case nir_intrinsic_bindless_image_atomic_umin: - atomic = ir3_ATOMIC_B_MIN(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_imax: - case nir_intrinsic_image_atomic_umax: - case nir_intrinsic_bindless_image_atomic_imax: - case nir_intrinsic_bindless_image_atomic_umax: - atomic = ir3_ATOMIC_B_MAX(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_and: - case nir_intrinsic_bindless_image_atomic_and: - atomic = ir3_ATOMIC_B_AND(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_or: - case nir_intrinsic_bindless_image_atomic_or: - atomic = ir3_ATOMIC_B_OR(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_xor: - case nir_intrinsic_bindless_image_atomic_xor: - atomic = ir3_ATOMIC_B_XOR(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_exchange: - case nir_intrinsic_bindless_image_atomic_exchange: - atomic = ir3_ATOMIC_B_XCHG(b, ibo, 0, src0, 0, src1, 0); - break; - case nir_intrinsic_image_atomic_comp_swap: - case nir_intrinsic_bindless_image_atomic_comp_swap: - atomic = ir3_ATOMIC_B_CMPXCHG(b, ibo, 0, src0, 0, src1, 0); - break; - default: - unreachable("boo"); - } - + atomic = emit_atomic(b, op, ibo, src0, src1); atomic->cat6.iim_val = 1; atomic->cat6.d = ncoords; atomic->cat6.type = ir3_get_type_for_image_intrinsic(intr); @@ -447,49 +405,50 @@ emit_intrinsic_atomic_global(struct ir3_context *ctx, nir_intrinsic_instr *intr) struct ir3_block *b = ctx->block; struct ir3_instruction *addr, *atomic, *src1; struct ir3_instruction *value = ir3_get_src(ctx, &intr->src[1])[0]; - type_t type = TYPE_U32; + nir_atomic_op op = nir_intrinsic_atomic_op(intr); + type_t type = nir_atomic_op_type(op) == nir_type_int ? TYPE_S32 : TYPE_U32; addr = ir3_collect(b, ir3_get_src(ctx, &intr->src[0])[0], ir3_get_src(ctx, &intr->src[0])[1]); - if (intr->intrinsic == nir_intrinsic_global_atomic_comp_swap_ir3) { + if (op == nir_atomic_op_cmpxchg) { struct ir3_instruction *compare = ir3_get_src(ctx, &intr->src[2])[0]; src1 = ir3_collect(b, compare, value); } else { src1 = value; } - switch (intr->intrinsic) { - case nir_intrinsic_global_atomic_add_ir3: + switch (op) { + case nir_atomic_op_iadd: atomic = ir3_ATOMIC_G_ADD(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_imin_ir3: + case nir_atomic_op_imin: atomic = ir3_ATOMIC_G_MIN(b, addr, 0, src1, 0); type = TYPE_S32; break; - case nir_intrinsic_global_atomic_umin_ir3: + case nir_atomic_op_umin: atomic = ir3_ATOMIC_G_MIN(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_imax_ir3: + case nir_atomic_op_imax: atomic = ir3_ATOMIC_G_MAX(b, addr, 0, src1, 0); type = TYPE_S32; break; - case nir_intrinsic_global_atomic_umax_ir3: + case nir_atomic_op_umax: atomic = ir3_ATOMIC_G_MAX(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_and_ir3: + case nir_atomic_op_iand: atomic = ir3_ATOMIC_G_AND(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_or_ir3: + case nir_atomic_op_ior: atomic = ir3_ATOMIC_G_OR(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_xor_ir3: + case nir_atomic_op_ixor: atomic = ir3_ATOMIC_G_XOR(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_exchange_ir3: + case nir_atomic_op_xchg: atomic = ir3_ATOMIC_G_XCHG(b, addr, 0, src1, 0); break; - case nir_intrinsic_global_atomic_comp_swap_ir3: + case nir_atomic_op_cmpxchg: atomic = ir3_ATOMIC_G_CMPXCHG(b, addr, 0, src1, 0); break; default: diff --git a/src/freedreno/ir3/ir3_compiler_nir.c b/src/freedreno/ir3/ir3_compiler_nir.c index 19f9cf6fd49..f8316f417a4 100644 --- a/src/freedreno/ir3/ir3_compiler_nir.c +++ b/src/freedreno/ir3/ir3_compiler_nir.c @@ -1192,7 +1192,7 @@ emit_intrinsic_store_shared_ir3(struct ir3_context *ctx, * 0: The offset into the shared variable storage region that the atomic * operation will operate on. * 1: The data parameter to the atomic function (i.e. the value to add - * in shared_atomic_add, etc). + * in, etc). * 2: For CompSwap only: the second data parameter. */ static struct ir3_instruction * @@ -1205,37 +1205,37 @@ emit_intrinsic_atomic_shared(struct ir3_context *ctx, nir_intrinsic_instr *intr) src0 = ir3_get_src(ctx, &intr->src[0])[0]; /* offset */ src1 = ir3_get_src(ctx, &intr->src[1])[0]; /* value */ - switch (intr->intrinsic) { - case nir_intrinsic_shared_atomic_add: + switch (nir_intrinsic_atomic_op(intr)) { + case nir_atomic_op_iadd: atomic = ir3_ATOMIC_ADD(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_imin: + case nir_atomic_op_imin: atomic = ir3_ATOMIC_MIN(b, src0, 0, src1, 0); type = TYPE_S32; break; - case nir_intrinsic_shared_atomic_umin: + case nir_atomic_op_umin: atomic = ir3_ATOMIC_MIN(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_imax: + case nir_atomic_op_imax: atomic = ir3_ATOMIC_MAX(b, src0, 0, src1, 0); type = TYPE_S32; break; - case nir_intrinsic_shared_atomic_umax: + case nir_atomic_op_umax: atomic = ir3_ATOMIC_MAX(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_and: + case nir_atomic_op_iand: atomic = ir3_ATOMIC_AND(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_or: + case nir_atomic_op_ior: atomic = ir3_ATOMIC_OR(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_xor: + case nir_atomic_op_ixor: atomic = ir3_ATOMIC_XOR(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_exchange: + case nir_atomic_op_xchg: atomic = ir3_ATOMIC_XCHG(b, src0, 0, src1, 0); break; - case nir_intrinsic_shared_atomic_comp_swap: + case nir_atomic_op_cmpxchg: /* for cmpxchg, src1 is [ui]vec2(data, compare): */ src1 = ir3_collect(b, ir3_get_src(ctx, &intr->src[2])[0], src1); atomic = ir3_ATOMIC_CMPXCHG(b, src0, 0, src1, 0); @@ -2151,16 +2151,8 @@ emit_intrinsic(struct ir3_context *ctx, nir_intrinsic_instr *intr) case nir_intrinsic_get_ssbo_size: emit_intrinsic_ssbo_size(ctx, intr, dst); break; - case nir_intrinsic_ssbo_atomic_add_ir3: - case nir_intrinsic_ssbo_atomic_imin_ir3: - case nir_intrinsic_ssbo_atomic_umin_ir3: - case nir_intrinsic_ssbo_atomic_imax_ir3: - case nir_intrinsic_ssbo_atomic_umax_ir3: - case nir_intrinsic_ssbo_atomic_and_ir3: - case nir_intrinsic_ssbo_atomic_or_ir3: - case nir_intrinsic_ssbo_atomic_xor_ir3: - case nir_intrinsic_ssbo_atomic_exchange_ir3: - case nir_intrinsic_ssbo_atomic_comp_swap_ir3: + case nir_intrinsic_ssbo_atomic_ir3: + case nir_intrinsic_ssbo_atomic_swap_ir3: dst[0] = ctx->funcs->emit_intrinsic_atomic_ssbo(ctx, intr); break; case nir_intrinsic_load_shared: @@ -2169,16 +2161,8 @@ emit_intrinsic(struct ir3_context *ctx, nir_intrinsic_instr *intr) case nir_intrinsic_store_shared: emit_intrinsic_store_shared(ctx, intr); break; - case nir_intrinsic_shared_atomic_add: - case nir_intrinsic_shared_atomic_imin: - case nir_intrinsic_shared_atomic_umin: - case nir_intrinsic_shared_atomic_imax: - case nir_intrinsic_shared_atomic_umax: - case nir_intrinsic_shared_atomic_and: - case nir_intrinsic_shared_atomic_or: - case nir_intrinsic_shared_atomic_xor: - case nir_intrinsic_shared_atomic_exchange: - case nir_intrinsic_shared_atomic_comp_swap: + case nir_intrinsic_shared_atomic: + case nir_intrinsic_shared_atomic_swap: dst[0] = emit_intrinsic_atomic_shared(ctx, intr); break; case nir_intrinsic_load_scratch: @@ -2199,26 +2183,10 @@ emit_intrinsic(struct ir3_context *ctx, nir_intrinsic_instr *intr) case nir_intrinsic_bindless_image_size: ctx->funcs->emit_intrinsic_image_size(ctx, intr, dst); break; - case nir_intrinsic_image_atomic_add: - case nir_intrinsic_bindless_image_atomic_add: - case nir_intrinsic_image_atomic_imin: - case nir_intrinsic_bindless_image_atomic_imin: - case nir_intrinsic_image_atomic_umin: - case nir_intrinsic_bindless_image_atomic_umin: - case nir_intrinsic_image_atomic_imax: - case nir_intrinsic_bindless_image_atomic_imax: - case nir_intrinsic_image_atomic_umax: - case nir_intrinsic_bindless_image_atomic_umax: - case nir_intrinsic_image_atomic_and: - case nir_intrinsic_bindless_image_atomic_and: - case nir_intrinsic_image_atomic_or: - case nir_intrinsic_bindless_image_atomic_or: - case nir_intrinsic_image_atomic_xor: - case nir_intrinsic_bindless_image_atomic_xor: - case nir_intrinsic_image_atomic_exchange: - case nir_intrinsic_bindless_image_atomic_exchange: - case nir_intrinsic_image_atomic_comp_swap: - case nir_intrinsic_bindless_image_atomic_comp_swap: + case nir_intrinsic_image_atomic: + case nir_intrinsic_bindless_image_atomic: + case nir_intrinsic_image_atomic_swap: + case nir_intrinsic_bindless_image_atomic_swap: dst[0] = ctx->funcs->emit_intrinsic_atomic_image(ctx, intr); break; case nir_intrinsic_scoped_barrier: @@ -2591,16 +2559,8 @@ emit_intrinsic(struct ir3_context *ctx, nir_intrinsic_instr *intr) case nir_intrinsic_bindless_resource_ir3: dst[0] = ir3_get_src(ctx, &intr->src[0])[0]; break; - case nir_intrinsic_global_atomic_add_ir3: - case nir_intrinsic_global_atomic_imin_ir3: - case nir_intrinsic_global_atomic_umin_ir3: - case nir_intrinsic_global_atomic_imax_ir3: - case nir_intrinsic_global_atomic_umax_ir3: - case nir_intrinsic_global_atomic_and_ir3: - case nir_intrinsic_global_atomic_or_ir3: - case nir_intrinsic_global_atomic_xor_ir3: - case nir_intrinsic_global_atomic_exchange_ir3: - case nir_intrinsic_global_atomic_comp_swap_ir3: { + case nir_intrinsic_global_atomic_ir3: + case nir_intrinsic_global_atomic_swap_ir3: { dst[0] = ctx->funcs->emit_intrinsic_atomic_global(ctx, intr); break; } diff --git a/src/freedreno/ir3/ir3_image.c b/src/freedreno/ir3/ir3_image.c index f52c188944a..9e732485f2f 100644 --- a/src/freedreno/ir3/ir3_image.c +++ b/src/freedreno/ir3/ir3_image.c @@ -136,32 +136,11 @@ ir3_get_type_for_image_intrinsic(const nir_intrinsic_instr *instr) type = nir_type_uint; break; - case nir_intrinsic_image_atomic_add: - case nir_intrinsic_bindless_image_atomic_add: - case nir_intrinsic_image_atomic_umin: - case nir_intrinsic_bindless_image_atomic_umin: - case nir_intrinsic_image_atomic_umax: - case nir_intrinsic_bindless_image_atomic_umax: - case nir_intrinsic_image_atomic_and: - case nir_intrinsic_bindless_image_atomic_and: - case nir_intrinsic_image_atomic_or: - case nir_intrinsic_bindless_image_atomic_or: - case nir_intrinsic_image_atomic_xor: - case nir_intrinsic_bindless_image_atomic_xor: - case nir_intrinsic_image_atomic_exchange: - case nir_intrinsic_bindless_image_atomic_exchange: - case nir_intrinsic_image_atomic_comp_swap: - case nir_intrinsic_bindless_image_atomic_comp_swap: - case nir_intrinsic_image_atomic_inc_wrap: - case nir_intrinsic_bindless_image_atomic_inc_wrap: - type = nir_type_uint; - break; - - case nir_intrinsic_image_atomic_imin: - case nir_intrinsic_bindless_image_atomic_imin: - case nir_intrinsic_image_atomic_imax: - case nir_intrinsic_bindless_image_atomic_imax: - type = nir_type_int; + case nir_intrinsic_image_atomic: + case nir_intrinsic_bindless_image_atomic: + case nir_intrinsic_image_atomic_swap: + case nir_intrinsic_bindless_image_atomic_swap: + type = nir_atomic_op_type(nir_intrinsic_atomic_op(instr)); break; default: diff --git a/src/freedreno/ir3/ir3_nir.c b/src/freedreno/ir3/ir3_nir.c index 8bf3d720038..c0f40c7aa10 100644 --- a/src/freedreno/ir3/ir3_nir.c +++ b/src/freedreno/ir3/ir3_nir.c @@ -381,6 +381,9 @@ ir3_finalize_nir(struct ir3_compiler *compiler, nir_shader *s) OPT_V(s, nir_remove_dead_variables, nir_var_function_temp, NULL); + /* Temporary stopgap until the core is transitioned to unified atomics */ + OPT_V(s, nir_lower_legacy_atomics); + if (ir3_shader_debug & IR3_DBG_DISASM) { mesa_logi("----------------------"); nir_log_shaderi(s); @@ -842,16 +845,8 @@ ir3_nir_scan_driver_consts(struct ir3_compiler *compiler, nir_shader *shader, st unsigned idx; switch (intr->intrinsic) { - case nir_intrinsic_image_atomic_add: - case nir_intrinsic_image_atomic_imin: - case nir_intrinsic_image_atomic_umin: - case nir_intrinsic_image_atomic_imax: - case nir_intrinsic_image_atomic_umax: - case nir_intrinsic_image_atomic_and: - case nir_intrinsic_image_atomic_or: - case nir_intrinsic_image_atomic_xor: - case nir_intrinsic_image_atomic_exchange: - case nir_intrinsic_image_atomic_comp_swap: + case nir_intrinsic_image_atomic: + case nir_intrinsic_image_atomic_swap: case nir_intrinsic_image_load: case nir_intrinsic_image_store: case nir_intrinsic_image_size: diff --git a/src/freedreno/ir3/ir3_nir_lower_64b.c b/src/freedreno/ir3/ir3_nir_lower_64b.c index 9c6ae66dc09..f43205fe29c 100644 --- a/src/freedreno/ir3/ir3_nir_lower_64b.c +++ b/src/freedreno/ir3/ir3_nir_lower_64b.c @@ -233,16 +233,8 @@ lower_64b_global_filter(const nir_instr *instr, const void *unused) case nir_intrinsic_load_global: case nir_intrinsic_load_global_constant: case nir_intrinsic_store_global: - case nir_intrinsic_global_atomic_add: - case nir_intrinsic_global_atomic_imin: - case nir_intrinsic_global_atomic_umin: - case nir_intrinsic_global_atomic_imax: - case nir_intrinsic_global_atomic_umax: - case nir_intrinsic_global_atomic_and: - case nir_intrinsic_global_atomic_or: - case nir_intrinsic_global_atomic_xor: - case nir_intrinsic_global_atomic_exchange: - case nir_intrinsic_global_atomic_comp_swap: + case nir_intrinsic_global_atomic: + case nir_intrinsic_global_atomic_swap: return true; default: return false; @@ -265,31 +257,18 @@ lower_64b_global(nir_builder *b, nir_instr *instr, void *unused) * those up into max 4 components per load/store. */ -#define GLOBAL_IR3_2SRC(name) \ - case nir_intrinsic_##name: { \ - return nir_build_##name##_ir3(b, nir_dest_bit_size(intr->dest), addr, \ - nir_ssa_for_src(b, intr->src[1], 1)); \ - } - - switch (intr->intrinsic) { - GLOBAL_IR3_2SRC(global_atomic_add) - GLOBAL_IR3_2SRC(global_atomic_imin) - GLOBAL_IR3_2SRC(global_atomic_umin) - GLOBAL_IR3_2SRC(global_atomic_imax) - GLOBAL_IR3_2SRC(global_atomic_umax) - GLOBAL_IR3_2SRC(global_atomic_and) - GLOBAL_IR3_2SRC(global_atomic_or) - GLOBAL_IR3_2SRC(global_atomic_xor) - GLOBAL_IR3_2SRC(global_atomic_exchange) - case nir_intrinsic_global_atomic_comp_swap: - return nir_build_global_atomic_comp_swap_ir3( + if (intr->intrinsic == nir_intrinsic_global_atomic) { + return nir_build_global_atomic_ir3( + b, nir_dest_bit_size(intr->dest), addr, + nir_ssa_for_src(b, intr->src[1], 1), + .atomic_op = nir_intrinsic_atomic_op(intr)); + } else if (intr->intrinsic == nir_intrinsic_global_atomic_swap) { + return nir_build_global_atomic_swap_ir3( b, nir_dest_bit_size(intr->dest), addr, nir_ssa_for_src(b, intr->src[1], 1), - nir_ssa_for_src(b, intr->src[2], 1)); - default: - break; + nir_ssa_for_src(b, intr->src[2], 1), + .atomic_op = nir_intrinsic_atomic_op(intr)); } -#undef GLOBAL_IR3_2SRC if (load) { unsigned num_comp = nir_intrinsic_dest_components(intr); diff --git a/src/freedreno/ir3/ir3_nir_lower_io_offsets.c b/src/freedreno/ir3/ir3_nir_lower_io_offsets.c index d7df5b8ecfc..280ab756296 100644 --- a/src/freedreno/ir3/ir3_nir_lower_io_offsets.c +++ b/src/freedreno/ir3/ir3_nir_lower_io_offsets.c @@ -55,26 +55,10 @@ get_ir3_intrinsic_for_ssbo_intrinsic(unsigned intrinsic, return nir_intrinsic_store_ssbo_ir3; case nir_intrinsic_load_ssbo: return nir_intrinsic_load_ssbo_ir3; - case nir_intrinsic_ssbo_atomic_add: - return nir_intrinsic_ssbo_atomic_add_ir3; - case nir_intrinsic_ssbo_atomic_imin: - return nir_intrinsic_ssbo_atomic_imin_ir3; - case nir_intrinsic_ssbo_atomic_umin: - return nir_intrinsic_ssbo_atomic_umin_ir3; - case nir_intrinsic_ssbo_atomic_imax: - return nir_intrinsic_ssbo_atomic_imax_ir3; - case nir_intrinsic_ssbo_atomic_umax: - return nir_intrinsic_ssbo_atomic_umax_ir3; - case nir_intrinsic_ssbo_atomic_and: - return nir_intrinsic_ssbo_atomic_and_ir3; - case nir_intrinsic_ssbo_atomic_or: - return nir_intrinsic_ssbo_atomic_or_ir3; - case nir_intrinsic_ssbo_atomic_xor: - return nir_intrinsic_ssbo_atomic_xor_ir3; - case nir_intrinsic_ssbo_atomic_exchange: - return nir_intrinsic_ssbo_atomic_exchange_ir3; - case nir_intrinsic_ssbo_atomic_comp_swap: - return nir_intrinsic_ssbo_atomic_comp_swap_ir3; + case nir_intrinsic_ssbo_atomic: + return nir_intrinsic_ssbo_atomic_ir3; + case nir_intrinsic_ssbo_atomic_swap: + return nir_intrinsic_ssbo_atomic_swap_ir3; default: break; } |