Skip to main content

core/stdarch/crates/core_arch/src/loongarch_shared/
mod.rs

1//! `Shared LoongArch` intrinsics
2
3use crate::arch::asm;
4
5/// Reads the lower 32-bit stable counter value and the counter ID
6#[inline(always)]
7#[unstable(feature = "stdarch_loongarch", issue = "117427")]
8pub fn rdtimel_w() -> (i32, isize) {
9    let (val, tid): (i32, isize);
10    unsafe { asm!("rdtimel.w {}, {}", out(reg) val, out(reg) tid, options(readonly, nostack)) };
11    (val, tid)
12}
13
14/// Reads the upper 32-bit stable counter value and the counter ID
15#[inline(always)]
16#[unstable(feature = "stdarch_loongarch", issue = "117427")]
17pub fn rdtimeh_w() -> (i32, isize) {
18    let (val, tid): (i32, isize);
19    unsafe { asm!("rdtimeh.w {}, {}", out(reg) val, out(reg) tid, options(readonly, nostack)) };
20    (val, tid)
21}
22
23#[allow(improper_ctypes)]
24unsafe extern "unadjusted" {
25    #[link_name = "llvm.loongarch.dbar"]
26    fn __dbar(a: i32);
27    #[link_name = "llvm.loongarch.ibar"]
28    fn __ibar(a: i32);
29    #[link_name = "llvm.loongarch.movgr2fcsr"]
30    fn __movgr2fcsr(a: i32, b: i32);
31    #[link_name = "llvm.loongarch.movfcsr2gr"]
32    fn __movfcsr2gr(a: i32) -> i32;
33    #[link_name = "llvm.loongarch.iocsrrd.b"]
34    fn __iocsrrd_b(a: i32) -> i32;
35    #[link_name = "llvm.loongarch.iocsrrd.h"]
36    fn __iocsrrd_h(a: i32) -> i32;
37    #[link_name = "llvm.loongarch.iocsrrd.w"]
38    fn __iocsrrd_w(a: i32) -> i32;
39    #[link_name = "llvm.loongarch.iocsrwr.b"]
40    fn __iocsrwr_b(a: i32, b: i32);
41    #[link_name = "llvm.loongarch.iocsrwr.h"]
42    fn __iocsrwr_h(a: i32, b: i32);
43    #[link_name = "llvm.loongarch.iocsrwr.w"]
44    fn __iocsrwr_w(a: i32, b: i32);
45    #[link_name = "llvm.loongarch.break"]
46    fn __break(a: i32);
47    #[link_name = "llvm.loongarch.cpucfg"]
48    fn __cpucfg(a: i32) -> i32;
49    #[link_name = "llvm.loongarch.syscall"]
50    fn __syscall(a: i32);
51    #[link_name = "llvm.loongarch.frecipe.s"]
52    fn __frecipe_s(a: f32) -> f32;
53    #[link_name = "llvm.loongarch.frecipe.d"]
54    fn __frecipe_d(a: f64) -> f64;
55    #[link_name = "llvm.loongarch.frsqrte.s"]
56    fn __frsqrte_s(a: f32) -> f32;
57    #[link_name = "llvm.loongarch.frsqrte.d"]
58    fn __frsqrte_d(a: f64) -> f64;
59}
60
61/// Generates the memory barrier instruction
62#[inline(always)]
63#[unstable(feature = "stdarch_loongarch", issue = "117427")]
64pub fn dbar<const IMM15: i32>() {
65    static_assert_uimm_bits!(IMM15, 15);
66    unsafe { __dbar(IMM15) };
67}
68
69/// Generates the instruction-fetch barrier instruction
70#[inline(always)]
71#[unstable(feature = "stdarch_loongarch", issue = "117427")]
72pub fn ibar<const IMM15: i32>() {
73    static_assert_uimm_bits!(IMM15, 15);
74    unsafe { __ibar(IMM15) };
75}
76
77/// Moves data from a GPR to the FCSR
78#[inline(always)]
79#[unstable(feature = "stdarch_loongarch", issue = "117427")]
80pub unsafe fn movgr2fcsr<const IMM2: i32>(a: i32) {
81    static_assert_uimm_bits!(IMM2, 2);
82    __movgr2fcsr(IMM2, a);
83}
84
85/// Moves data from a FCSR to the GPR
86#[inline(always)]
87#[unstable(feature = "stdarch_loongarch", issue = "117427")]
88pub fn movfcsr2gr<const IMM2: i32>() -> i32 {
89    static_assert_uimm_bits!(IMM2, 2);
90    unsafe { __movfcsr2gr(IMM2) }
91}
92
93/// Reads the 8-bit IO-CSR
94#[inline(always)]
95#[unstable(feature = "stdarch_loongarch", issue = "117427")]
96pub unsafe fn iocsrrd_b(a: i32) -> i32 {
97    __iocsrrd_b(a)
98}
99
100/// Reads the 16-bit IO-CSR
101#[inline(always)]
102#[unstable(feature = "stdarch_loongarch", issue = "117427")]
103pub unsafe fn iocsrrd_h(a: i32) -> i32 {
104    __iocsrrd_h(a)
105}
106
107/// Reads the 32-bit IO-CSR
108#[inline(always)]
109#[unstable(feature = "stdarch_loongarch", issue = "117427")]
110pub unsafe fn iocsrrd_w(a: i32) -> i32 {
111    __iocsrrd_w(a)
112}
113
114/// Writes the 8-bit IO-CSR
115#[inline(always)]
116#[unstable(feature = "stdarch_loongarch", issue = "117427")]
117pub unsafe fn iocsrwr_b(a: i32, b: i32) {
118    __iocsrwr_b(a, b)
119}
120
121/// Writes the 16-bit IO-CSR
122#[inline(always)]
123#[unstable(feature = "stdarch_loongarch", issue = "117427")]
124pub unsafe fn iocsrwr_h(a: i32, b: i32) {
125    __iocsrwr_h(a, b)
126}
127
128/// Writes the 32-bit IO-CSR
129#[inline(always)]
130#[unstable(feature = "stdarch_loongarch", issue = "117427")]
131pub unsafe fn iocsrwr_w(a: i32, b: i32) {
132    __iocsrwr_w(a, b)
133}
134
135/// Generates the breakpoint instruction
136#[inline(always)]
137#[unstable(feature = "stdarch_loongarch", issue = "117427")]
138pub unsafe fn brk<const IMM15: i32>() {
139    static_assert_uimm_bits!(IMM15, 15);
140    __break(IMM15);
141}
142
143/// Reads the CPU configuration register
144#[inline(always)]
145#[unstable(feature = "stdarch_loongarch", issue = "117427")]
146pub fn cpucfg(a: i32) -> i32 {
147    unsafe { __cpucfg(a) }
148}
149
150/// Generates the syscall instruction
151#[inline(always)]
152#[unstable(feature = "stdarch_loongarch", issue = "117427")]
153pub unsafe fn syscall<const IMM15: i32>() {
154    static_assert_uimm_bits!(IMM15, 15);
155    __syscall(IMM15);
156}
157
158/// Calculate the approximate single-precision result of 1.0 divided
159#[inline]
160#[target_feature(enable = "frecipe")]
161#[unstable(feature = "stdarch_loongarch", issue = "117427")]
162pub fn frecipe_s(a: f32) -> f32 {
163    unsafe { __frecipe_s(a) }
164}
165
166/// Calculate the approximate double-precision result of 1.0 divided
167#[inline]
168#[target_feature(enable = "frecipe")]
169#[unstable(feature = "stdarch_loongarch", issue = "117427")]
170pub fn frecipe_d(a: f64) -> f64 {
171    unsafe { __frecipe_d(a) }
172}
173
174/// Calculate the approximate single-precision result of dividing 1.0 by the square root
175#[inline]
176#[target_feature(enable = "frecipe")]
177#[unstable(feature = "stdarch_loongarch", issue = "117427")]
178pub fn frsqrte_s(a: f32) -> f32 {
179    unsafe { __frsqrte_s(a) }
180}
181
182/// Calculate the approximate double-precision result of dividing 1.0 by the square root
183#[inline]
184#[target_feature(enable = "frecipe")]
185#[unstable(feature = "stdarch_loongarch", issue = "117427")]
186pub fn frsqrte_d(a: f64) -> f64 {
187    unsafe { __frsqrte_d(a) }
188}