1#![cfg_attr(nightly, feature(core_intrinsics))]
2#![cfg_attr(not(feature = "std"), no_std)]
3#![allow(internal_features)]
4
5#![doc = include_str!("../README.md")]
6
7mod disjoint_bitor;
8mod test;
9
10pub use disjoint_bitor::*;
11
12#[inline(always)]
18pub fn abort() -> ! {
19 #[cfg(nightly)]
20 core::intrinsics::abort();
21
22 #[cfg(not(nightly))] {
23 #[cfg(feature = "std")]
25 std::process::abort();
26
27 #[cfg(not(feature = "std"))]
29 panic!();
30 }
31}
32
33#[inline(always)]
47pub fn breakpoint() {
48 #[cfg(nightly)]
49 core::intrinsics::breakpoint();
50
51 #[cfg(not(nightly))] {
52 #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
53 unsafe { core::arch::asm!("int3", options(nomem, nostack)) };
54
55 #[cfg(target_arch = "arm")]
56 unsafe { core::arch::asm!("bkpt", options(nomem, nostack)) };
57
58 #[cfg(target_arch = "aarch64")]
59 unsafe { core::arch::asm!("brk #0xf000", options(nomem, nostack)) };
60
61 #[cfg(any(target_arch = "riscv32", target_arch = "riscv64"))]
62 unsafe { core::arch::asm!("ebreak", options(nomem, nostack)) };
63
64 #[cfg(any(target_arch = "mips", target_arch = "mips64"))]
65 unsafe { core::arch::asm!("break", options(nomem, nostack)) };
66 }
67}
68
69#[inline(always)]
71pub const fn cold_path() {
72 #[cfg(nightly)]
73 core::intrinsics::cold_path();
74}
75
76#[inline(always)]
79pub const fn likely(b: bool) -> bool {
80 #[cfg(nightly)]
81 return core::intrinsics::likely(b);
82
83 #[cfg(not(nightly))]
84 return b;
85}
86
87#[inline(always)]
90pub const fn unlikely(b: bool) -> bool {
91 #[cfg(nightly)]
92 return core::intrinsics::unlikely(b);
93
94 #[cfg(not(nightly))]
95 return b;
96}
97
98#[inline(always)]
103pub unsafe fn prefetch_read_data<T>(_data: *const T, _locality: i32) {
104 #[cfg(nightly)]
105 unsafe {
106 core::intrinsics::prefetch_read_data(_data, _locality);
107 }
108}
109
110#[inline(always)]
115pub unsafe fn prefetch_read_instruction<T>(_data: *const T, _locality: i32) {
116 #[cfg(nightly)]
117 unsafe {
118 core::intrinsics::prefetch_read_instruction(_data, _locality);
119 }
120}
121
122#[inline(always)]
127pub unsafe fn prefetch_write_data<T>(_data: *const T, _locality: i32) {
128 #[cfg(nightly)]
129 unsafe {
130 core::intrinsics::prefetch_write_data(_data, _locality);
131 }
132}
133
134#[inline(always)]
139pub unsafe fn prefetch_write_instruction<T>(_data: *const T, _locality: i32) {
140 #[cfg(nightly)]
141 unsafe {
142 core::intrinsics::prefetch_write_instruction(_data, _locality);
143 }
144}
145
146#[inline(always)]
149pub fn select_unpredictable<T>(b: bool, true_val: T, false_val: T) -> T {
150 #[cfg(nightly)]
151 return core::intrinsics::select_unpredictable(b, true_val, false_val);
152
153 #[cfg(not(nightly))]
154 return if b { true_val } else { false_val };
155}
156
157#[inline(always)]
166pub unsafe fn disjoint_bitor<T: DisjointBitOr>(a: T, b: T) -> T {
167 unsafe { a.disjoint_bitor(b) }
168}
169
170#[inline(always)]
175pub const unsafe fn transmute_unchecked<Src, Dst>(src: Src) -> Dst {
176 #[cfg(nightly)]
177 return unsafe { core::intrinsics::transmute_unchecked(src) };
178
179 #[cfg(not(nightly))]
180 unsafe {
181 let dst = core::mem::transmute::<*const Src, *const Dst>(&src as *const Src);
182 core::mem::forget(src);
183 dst.read()
184 }
185}
186
187#[inline(always)]
193pub const unsafe fn raw_eq<T>(a: &T, b: &T) -> bool {
194 #[cfg(nightly)]
195 return unsafe { core::intrinsics::raw_eq(a, b) };
196
197 #[cfg(not(nightly))]
198 unsafe {
199 let a = core::slice::from_raw_parts(a as *const T as *const u8, size_of::<T>());
200 let b = core::slice::from_raw_parts(b as *const T as *const u8, size_of::<T>());
201
202 let mut i = 0;
204 while i < size_of::<T>() {
205 if a[i] != b[i] {
206 return false;
207 }
208
209 i += 1;
210 }
211
212 true
213 }
214}
215
216pub unsafe fn nontemporal_store<T>(ptr: *mut T, val: T) {
222 unsafe {
223 #[cfg(nightly)]
224 core::intrinsics::nontemporal_store(ptr, val);
225
226 #[cfg(not(nightly))]
227 ptr.write(val);
228 }
229}