diff options
author | Xi Ruoyao <xry111@xry111.site> | 2025-03-01 11:46:52 +0800 |
---|---|---|
committer | Lulu Cheng <chenglulu@loongson.cn> | 2025-08-18 09:09:36 +0800 |
commit | 8735a4fecab7e4c9f3e1962dc04e03aa14207f14 (patch) | |
tree | 363f1180ab98d52fc4660a68943300f79e6be339 /gcc | |
parent | 89c8638deb9ccb1f1e1a90f18f2e6b984b70fbe8 (diff) | |
download | gcc-8735a4fecab7e4c9f3e1962dc04e03aa14207f14.zip gcc-8735a4fecab7e4c9f3e1962dc04e03aa14207f14.tar.gz gcc-8735a4fecab7e4c9f3e1962dc04e03aa14207f14.tar.bz2 |
LoongArch: Implement 16-byte atomic store with LSX
If the vector is naturally aligned, it cannot cross cache lines so the
LSX store is guaranteed to be atomic. Thus we can use LSX to do the
lock-free atomic store, instead of using a lock.
gcc/ChangeLog:
* config/loongarch/sync.md (atomic_storeti_lsx): New
define_insn.
(atomic_storeti): New define_expand.
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/config/loongarch/sync.md | 44 |
1 files changed, 44 insertions, 0 deletions
diff --git a/gcc/config/loongarch/sync.md b/gcc/config/loongarch/sync.md index b0d3c85..a0129b6 100644 --- a/gcc/config/loongarch/sync.md +++ b/gcc/config/loongarch/sync.md @@ -209,6 +209,50 @@ } [(set (attr "length") (const_int 12))]) +(define_insn "atomic_storeti_lsx" + [(set (match_operand:TI 0 "memory_operand" "=m") + (unspec_volatile:TI + [(match_operand:V2DI 1 "register_operand" "f") + (match_operand:SI 2 "const_int_operand")] ;; model + UNSPEC_ATOMIC_STORE))] + "ISA_HAS_LSX && TARGET_64BIT" +{ + enum memmodel model = memmodel_base (INTVAL (operands[2])); + + switch (model) + { + case MEMMODEL_SEQ_CST: + return "dbar\t0x12\\n\\t" + "vst\t%w1,%0\\n\\t" + "dbar\t0x18"; + case MEMMODEL_RELEASE: + return "dbar\t0x12\\n\\t" + "vst\t%w1,%0"; + case MEMMODEL_RELAXED: + return "vst\t%w1,%0"; + default: + gcc_unreachable (); + } +} + [(set (attr "length") (const_int 12))]) + +(define_expand "atomic_storeti" + [(match_operand:TI 0 "memory_operand" "=m") + (match_operand:TI 1 "reg_or_0_operand" "rJ") + (match_operand:SI 2 "const_int_operand")] + "ISA_HAS_LSX && TARGET_64BIT" +{ + rtx vr = gen_reg_rtx (V2DImode), op1 = operands[1]; + rtvec v = rtvec_alloc (2); + + for (int i = 0; i < 2; i++) + RTVEC_ELT (v, i) = loongarch_subword (op1, i); + + emit_insn (gen_vec_initv2didi (vr, gen_rtx_PARALLEL (V2DImode, v))); + emit_insn (gen_atomic_storeti_lsx (operands[0], vr, operands[2])); + DONE; +}) + (define_insn "atomic_<amop><mode>" [(set (match_operand:GPR 0 "memory_operand" "+ZB") (unspec_volatile:GPR |