Skip to content

Commit

Permalink
Add processor APIs (#13)
Browse files Browse the repository at this point in the history
Add processor APIs and test
  • Loading branch information
nigriMSFT authored May 2, 2024
1 parent 3798f6c commit c6ac906
Show file tree
Hide file tree
Showing 12 changed files with 334 additions and 1 deletion.
13 changes: 13 additions & 0 deletions inc/cxplat_posix.h
Original file line number Diff line number Diff line change
Expand Up @@ -221,6 +221,7 @@ InterlockedFetchAndSetBoolean(

#define CXPLAT_STATUS_SUCCESS ((CXPLAT_STATUS)0) // 0
#define CXPLAT_STATUS_OUT_OF_MEMORY ((CXPLAT_STATUS)ENOMEM) // 12
#define CXPLAT_STATUS_NOT_SUPPORTED ((CXPLAT_STATUS)EOPNOTSUPP) // 95 (102 on macOS)

//
// Code Annotations
Expand Down Expand Up @@ -598,6 +599,18 @@ CxPlatInternalEventWaitWithTimeout(
#define CxPlatEventWaitForever(Event) CxPlatInternalEventWaitForever(&Event)
#define CxPlatEventWaitWithTimeout(Event, TimeoutMs) CxPlatInternalEventWaitWithTimeout(&Event, TimeoutMs)

//
// Processor Interfaces
//

extern uint32_t CxPlatProcessorCount;
#define CxPlatProcCount() CxPlatProcessorCount

uint32_t
CxPlatProcCurrentNumber(
void
);

//
// Crypto Interfaces
//
Expand Down
9 changes: 9 additions & 0 deletions inc/cxplat_winkernel.h
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ typedef UINT64 uint64_t;

#define CXPLAT_STATUS_SUCCESS STATUS_SUCCESS // 0x0
#define CXPLAT_STATUS_OUT_OF_MEMORY STATUS_NO_MEMORY // 0xc0000017
#define CXPLAT_STATUS_NOT_SUPPORTED STATUS_NOT_SUPPORTED // 0xc00000bb

//
// Code Annotations
Expand Down Expand Up @@ -344,6 +345,14 @@ CxPlatInternalEventWaitWithTimeout(
#define CxPlatEventWaitWithTimeout(Event, TimeoutMs) \
(STATUS_SUCCESS == CxPlatInternalEventWaitWithTimeout(&Event, TimeoutMs))

//
// Processor Interfaces
//

extern uint32_t CxPlatProcessorCount;
#define CxPlatProcCount() CxPlatProcessorCount
#define CxPlatProcCurrentNumber() (KeGetCurrentProcessorIndex() % CxPlatProcessorCount)

//
// Crypto Interfaces
//
Expand Down
34 changes: 34 additions & 0 deletions inc/cxplat_winuser.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ extern "C" {

#define CXPLAT_STATUS_SUCCESS S_OK // 0x0
#define CXPLAT_STATUS_OUT_OF_MEMORY E_OUTOFMEMORY // 0x8007000e
#define CXPLAT_STATUS_NOT_SUPPORTED E_NOINTERFACE // 0x80004002

//
// Code Annotations
Expand Down Expand Up @@ -344,6 +345,39 @@ CxPlatEventWaitWithTimeout(
return WAIT_OBJECT_0 == WaitForSingleObject(Event, TimeoutMs);
}

//
// Processor Interfaces
//

typedef struct CXPLAT_PROCESSOR_INFO {
uint32_t Index; // Index in the current group
uint16_t Group; // The group number this processor is a part of
} CXPLAT_PROCESSOR_INFO;

typedef struct CXPLAT_PROCESSOR_GROUP_INFO {
KAFFINITY Mask; // Bit mask of active processors in the group
uint32_t Count; // Count of active processors in the group
uint32_t Offset; // Base process index offset this group starts at
} CXPLAT_PROCESSOR_GROUP_INFO;

extern CXPLAT_PROCESSOR_INFO* CxPlatProcessorInfo;
extern CXPLAT_PROCESSOR_GROUP_INFO* CxPlatProcessorGroupInfo;

extern uint32_t CxPlatProcessorCount;
#define CxPlatProcCount() CxPlatProcessorCount

_IRQL_requires_max_(DISPATCH_LEVEL)
inline
uint32_t
CxPlatProcCurrentNumber(
void
) {
PROCESSOR_NUMBER ProcNumber;
GetCurrentProcessorNumberEx(&ProcNumber);
const CXPLAT_PROCESSOR_GROUP_INFO* Group = &CxPlatProcessorGroupInfo[ProcNumber.Group];
return Group->Offset + (ProcNumber.Number % Group->Count);
}

//
// Crypto Interfaces
//
Expand Down
28 changes: 28 additions & 0 deletions src/lib/cxplat_posix.c
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@ CX_PLATFORM CxPlatform = { NULL };
//
int RandomFd = -1;

uint32_t CxPlatProcessorCount;

#ifdef __clang__
__attribute__((noinline, noreturn, optnone))
#else
Expand Down Expand Up @@ -99,6 +101,16 @@ CxPlatInitialize(
CxPlatform.AllocCounter = 0;
#endif

#if defined(CX_PLATFORM_DARWIN)
//
// arm64 macOS has no way to get the current proc, so treat as single core.
// Intel macOS can return incorrect values for CPUID, so treat as single core.
//
CxPlatProcessorCount = 1;
#else
CxPlatProcessorCount = (uint32_t)sysconf(_SC_NPROCESSORS_ONLN);
#endif

RandomFd = open("/dev/urandom", O_RDONLY|O_CLOEXEC);
if (RandomFd == -1) {
CxPlatTraceEvent(
Expand Down Expand Up @@ -255,6 +267,22 @@ CxPlatSleep(
UNREFERENCED_PARAMETER(ErrorCode);
}

uint32_t
CxPlatProcCurrentNumber(
void
)
{
#if defined(CX_PLATFORM_LINUX)
return (uint32_t)sched_getcpu() % CxPlatProcessorCount;
#elif defined(CX_PLATFORM_DARWIN)
//
// arm64 macOS has no way to get the current proc, so treat as single core.
// Intel macOS can return incorrect values for CPUID, so treat as single core.
//
return 0;
#endif // CX_PLATFORM_DARWIN
}

CXPLAT_STATUS
CxPlatRandom(
_In_ uint32_t BufferLen,
Expand Down
4 changes: 4 additions & 0 deletions src/lib/cxplat_winkernel.c
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ typedef struct CX_PLATFORM {
} CX_PLATFORM;

uint64_t CxPlatPerfFreq;
uint32_t CxPlatProcessorCount;
CX_PLATFORM CxPlatform = { NULL };

PAGEDX
Expand All @@ -35,6 +36,9 @@ CxPlatInitialize(
{
PAGED_CODE();

CxPlatProcessorCount =
(uint32_t)KeQueryActiveProcessorCountEx(ALL_PROCESSOR_GROUPS);

(VOID)KeQueryPerformanceCounter((LARGE_INTEGER*)&CxPlatPerfFreq);

CXPLAT_STATUS Status =
Expand Down
Loading

0 comments on commit c6ac906

Please sign in to comment.