From 0aabc206a1797fb839f45820dadcbc056953a6eb Mon Sep 17 00:00:00 2001 From: Aiken Harris Date: Mon, 1 Jun 2026 00:36:52 +0200 Subject: [PATCH] Add BSF and BSR instruction wrappers --- xtoskrnl/ar/amd64/cpufunc.cc | 50 +++++++++++++++++++++++++++ xtoskrnl/ar/i686/cpufunc.cc | 50 +++++++++++++++++++++++++++ xtoskrnl/includes/ar/amd64/cpufunc.hh | 4 +++ xtoskrnl/includes/ar/i686/cpufunc.hh | 4 +++ 4 files changed, 108 insertions(+) diff --git a/xtoskrnl/ar/amd64/cpufunc.cc b/xtoskrnl/ar/amd64/cpufunc.cc index f0c6933..df04cc9 100644 --- a/xtoskrnl/ar/amd64/cpufunc.cc +++ b/xtoskrnl/ar/amd64/cpufunc.cc @@ -617,6 +617,56 @@ AR::CpuFunctions::ReadWriteBarrier(VOID) : "memory"); } +/** + * Performs a Bit Scan Forward instruction to locate the most significant set bit. + * + * @param Index + * Receives the zero-based index of the highest set bit when one is found. + * + * @param Mask + * Supplies the bitmap to scan. + * + * @return This routine returns TRUE when a set bit was found, otherwise FALSE. + * + * @since XT 1.0 + */ +XTCDECL +BOOLEAN +AR::CpuFunctions::ScanForwardBit(OUT PULONG Index, + IN ULONG Mask) +{ + /* Defer to the BSF instruction */ + __asm__("bsfl %[Mask], %[Index]" : [Index] "=r" (*Index) : [Mask] "mr" (Mask)); + + /* Report whether the input had any bit set */ + return Mask ? TRUE : FALSE; +} + +/** + * Performs a Bit Scan Reverse instruction to locate the most significant set bit. + * + * @param Index + * Receives the zero-based index of the highest set bit when one is found. + * + * @param Mask + * Supplies the bitmap to scan. + * + * @return This routine returns TRUE when a set bit was found, otherwise FALSE. + * + * @since XT 1.0 + */ +XTCDECL +BOOLEAN +AR::CpuFunctions::ScanReverseBit(OUT PULONG Index, + IN ULONG Mask) +{ + /* Defer to the BSR instruction */ + __asm__("bsrl %[Mask], %[Index]" : [Index] "=r" (*Index) : [Mask] "mr" (Mask)); + + /* Report whether the input had any bit set */ + return Mask ? TRUE : FALSE; +} + /** * Instructs the processor to set the interrupt flag. * diff --git a/xtoskrnl/ar/i686/cpufunc.cc b/xtoskrnl/ar/i686/cpufunc.cc index 784d184..b1465e0 100644 --- a/xtoskrnl/ar/i686/cpufunc.cc +++ b/xtoskrnl/ar/i686/cpufunc.cc @@ -587,6 +587,56 @@ AR::CpuFunctions::ReadWriteBarrier(VOID) : "memory"); } +/** + * Performs a Bit Scan Forward instruction to locate the most significant set bit. + * + * @param Index + * Receives the zero-based index of the highest set bit when one is found. + * + * @param Mask + * Supplies the bitmap to scan. + * + * @return This routine returns TRUE when a set bit was found, otherwise FALSE. + * + * @since XT 1.0 + */ +XTCDECL +BOOLEAN +AR::CpuFunctions::ScanForwardBit(OUT PULONG Index, + IN ULONG Mask) +{ + /* Defer to the BSF instruction */ + __asm__("bsfl %[Mask], %[Index]" : [Index] "=r" (*Index) : [Mask] "mr" (Mask)); + + /* Report whether the input had any bit set */ + return Mask ? TRUE : FALSE; +} + +/** + * Performs a Bit Scan Reverse instruction to locate the most significant set bit. + * + * @param Index + * Receives the zero-based index of the highest set bit when one is found. + * + * @param Mask + * Supplies the bitmap to scan. + * + * @return This routine returns TRUE when a set bit was found, otherwise FALSE. + * + * @since XT 1.0 + */ +XTCDECL +BOOLEAN +AR::CpuFunctions::ScanReverseBit(OUT PULONG Index, + IN ULONG Mask) +{ + /* Defer to the BSR instruction */ + __asm__("bsrl %[Mask], %[Index]" : [Index] "=r" (*Index) : [Mask] "mr" (Mask)); + + /* Report whether the input had any bit set */ + return Mask ? TRUE : FALSE; +} + /** * Instructs the processor to set the interrupt flag. * diff --git a/xtoskrnl/includes/ar/amd64/cpufunc.hh b/xtoskrnl/includes/ar/amd64/cpufunc.hh index 0d0a43c..b717095 100644 --- a/xtoskrnl/includes/ar/amd64/cpufunc.hh +++ b/xtoskrnl/includes/ar/amd64/cpufunc.hh @@ -42,6 +42,10 @@ namespace AR STATIC XTCDECL ULONGLONG ReadTimeStampCounter(VOID); STATIC XTCDECL ULONGLONG ReadTimeStampCounterProcessor(OUT PULONG TscAux); STATIC XTCDECL VOID ReadWriteBarrier(VOID); + STATIC XTCDECL BOOLEAN ScanForwardBit(OUT PULONG Index, + IN ULONG Mask); + STATIC XTCDECL BOOLEAN ScanReverseBit(OUT PULONG Index, + IN ULONG Mask); STATIC XTCDECL VOID SetInterruptFlag(VOID); STATIC XTCDECL VOID StoreGlobalDescriptorTable(OUT PVOID Destination); STATIC XTCDECL VOID StoreInterruptDescriptorTable(OUT PVOID Destination); diff --git a/xtoskrnl/includes/ar/i686/cpufunc.hh b/xtoskrnl/includes/ar/i686/cpufunc.hh index 28cfdb1..3e5b3b3 100644 --- a/xtoskrnl/includes/ar/i686/cpufunc.hh +++ b/xtoskrnl/includes/ar/i686/cpufunc.hh @@ -41,6 +41,10 @@ namespace AR STATIC XTCDECL ULONGLONG ReadTimeStampCounter(VOID); STATIC XTCDECL ULONGLONG ReadTimeStampCounterProcessor(OUT PULONG TscAux); STATIC XTCDECL VOID ReadWriteBarrier(VOID); + STATIC XTCDECL BOOLEAN ScanForwardBit(OUT PULONG Index, + IN ULONG Mask); + STATIC XTCDECL BOOLEAN ScanReverseBit(OUT PULONG Index, + IN ULONG Mask); STATIC XTCDECL VOID SetInterruptFlag(VOID); STATIC XTCDECL VOID StoreGlobalDescriptorTable(OUT PVOID Destination); STATIC XTCDECL VOID StoreInterruptDescriptorTable(OUT PVOID Destination);