Skip to content

Commit 1cf9d2c

Browse files
committed
arch: Add utility functions for SMAP
Signed-off-by: Dennis Bonke <[email protected]>
1 parent 3dc2ab3 commit 1cf9d2c

File tree

1 file changed

+33
-0
lines changed

1 file changed

+33
-0
lines changed

src/aero_kernel/src/arch/x86_64/controlregs.rs

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,8 @@
1717
* along with Aero. If not, see <https://www.gnu.org/licenses/>.
1818
*/
1919

20+
use core::sync::atomic::{AtomicUsize, Ordering};
21+
2022
use crate::mem::paging::{PhysAddr, PhysFrame, VirtAddr};
2123

2224
bitflags::bitflags! {
@@ -273,3 +275,34 @@ pub fn read_cr2() -> VirtAddr {
273275
VirtAddr::new(value)
274276
}
275277
}
278+
279+
/// Returns true if Supervisor Mode Access Prevention (SMAP) is supported by the CPU and is enabled in Cr4.
280+
#[inline]
281+
pub fn smap_enabled() -> bool {
282+
read_cr4().contains(Cr4Flags::SUPERVISOR_MODE_ACCESS_PREVENTION)
283+
}
284+
285+
#[inline]
286+
pub fn with_userspace_access<F, R>(f: F) -> R
287+
where
288+
F: FnOnce() -> R,
289+
{
290+
static REF_COUNT: AtomicUsize = AtomicUsize::new(0);
291+
if smap_enabled() {
292+
unsafe {
293+
asm!("stac");
294+
}
295+
REF_COUNT.fetch_add(1, Ordering::Acquire);
296+
};
297+
let r = f();
298+
if smap_enabled() {
299+
REF_COUNT.fetch_sub(1, Ordering::Release);
300+
301+
if REF_COUNT.load(Ordering::Relaxed) == 0 {
302+
unsafe {
303+
asm!("clac");
304+
}
305+
}
306+
};
307+
r
308+
}

0 commit comments

Comments
 (0)