1use std::fmt;
2
3use rustc_span::Symbol;
4
5use super::{InlineAsmArch, InlineAsmType, ModifierInfo};
6
7def_reg_class! {
8 LoongArch LoongArchInlineAsmRegClass {
9 reg,
10 freg,
11 }
12}
13
14impl LoongArchInlineAsmRegClass {
15 pub fn valid_modifiers(self, _arch: super::InlineAsmArch) -> &'static [char] {
16 &[]
17 }
18
19 pub fn suggest_class(self, _arch: InlineAsmArch, _ty: InlineAsmType) -> Option<Self> {
20 None
21 }
22
23 pub fn suggest_modifier(
24 self,
25 _arch: InlineAsmArch,
26 _ty: InlineAsmType,
27 ) -> Option<ModifierInfo> {
28 None
29 }
30
31 pub fn default_modifier(self, _arch: InlineAsmArch) -> Option<ModifierInfo> {
32 None
33 }
34
35 pub fn supported_types(
36 self,
37 arch: InlineAsmArch,
38 ) -> &'static [(InlineAsmType, Option<Symbol>)] {
39 match (self, arch) {
40 (Self::reg, InlineAsmArch::LoongArch64) => {
41 types! { _: I8, I16, I32, I64, F16, F32, F64; }
42 }
43 (Self::reg, InlineAsmArch::LoongArch32) => types! { _: I8, I16, I32, F16, F32; },
44 (Self::freg, _) => types! { f: F16, F32; d: F64; },
45 _ => unreachable!("unsupported register class"),
46 }
47 }
48}
49
50def_regs! {
52 LoongArch LoongArchInlineAsmReg LoongArchInlineAsmRegClass {
53 r1: reg = ["$r1","$ra"],
54 r4: reg = ["$r4","$a0"],
55 r5: reg = ["$r5","$a1"],
56 r6: reg = ["$r6","$a2"],
57 r7: reg = ["$r7","$a3"],
58 r8: reg = ["$r8","$a4"],
59 r9: reg = ["$r9","$a5"],
60 r10: reg = ["$r10","$a6"],
61 r11: reg = ["$r11","$a7"],
62 r12: reg = ["$r12","$t0"],
63 r13: reg = ["$r13","$t1"],
64 r14: reg = ["$r14","$t2"],
65 r15: reg = ["$r15","$t3"],
66 r16: reg = ["$r16","$t4"],
67 r17: reg = ["$r17","$t5"],
68 r18: reg = ["$r18","$t6"],
69 r19: reg = ["$r19","$t7"],
70 r20: reg = ["$r20","$t8"],
71 r23: reg = ["$r23","$s0"],
72 r24: reg = ["$r24","$s1"],
73 r25: reg = ["$r25","$s2"],
74 r26: reg = ["$r26","$s3"],
75 r27: reg = ["$r27","$s4"],
76 r28: reg = ["$r28","$s5"],
77 r29: reg = ["$r29","$s6"],
78 r30: reg = ["$r30","$s7"],
79 f0: freg = ["$f0","$fa0"],
80 f1: freg = ["$f1","$fa1"],
81 f2: freg = ["$f2","$fa2"],
82 f3: freg = ["$f3","$fa3"],
83 f4: freg = ["$f4","$fa4"],
84 f5: freg = ["$f5","$fa5"],
85 f6: freg = ["$f6","$fa6"],
86 f7: freg = ["$f7","$fa7"],
87 f8: freg = ["$f8","$ft0"],
88 f9: freg = ["$f9","$ft1"],
89 f10: freg = ["$f10","$ft2"],
90 f11: freg = ["$f11","$ft3"],
91 f12: freg = ["$f12","$ft4"],
92 f13: freg = ["$f13","$ft5"],
93 f14: freg = ["$f14","$ft6"],
94 f15: freg = ["$f15","$ft7"],
95 f16: freg = ["$f16","$ft8"],
96 f17: freg = ["$f17","$ft9"],
97 f18: freg = ["$f18","$ft10"],
98 f19: freg = ["$f19","$ft11"],
99 f20: freg = ["$f20","$ft12"],
100 f21: freg = ["$f21","$ft13"],
101 f22: freg = ["$f22","$ft14"],
102 f23: freg = ["$f23","$ft15"],
103 f24: freg = ["$f24","$fs0"],
104 f25: freg = ["$f25","$fs1"],
105 f26: freg = ["$f26","$fs2"],
106 f27: freg = ["$f27","$fs3"],
107 f28: freg = ["$f28","$fs4"],
108 f29: freg = ["$f29","$fs5"],
109 f30: freg = ["$f30","$fs6"],
110 f31: freg = ["$f31","$fs7"],
111 #error = ["$r0","$zero"] =>
112 "constant zero cannot be used as an operand for inline asm",
113 #error = ["$r2","$tp"] =>
114 "reserved for TLS",
115 #error = ["$r3","$sp"] =>
116 "the stack pointer cannot be used as an operand for inline asm",
117 #error = ["$r21"] =>
118 "reserved by the ABI",
119 #error = ["$r22","$fp"] =>
120 "the frame pointer cannot be used as an operand for inline asm",
121 #error = ["$r31","$s8"] =>
122 "$r31 is used internally by LLVM and cannot be used as an operand for inline asm",
123 }
124}
125
126impl LoongArchInlineAsmReg {
127 pub fn emit(
128 self,
129 out: &mut dyn fmt::Write,
130 _arch: InlineAsmArch,
131 _modifier: Option<char>,
132 ) -> fmt::Result {
133 out.write_str(self.name())
134 }
135}