stos: ex: Add per-cpu pool allocator groundwork
Signed-off-by: Chloe M. <chloe@mensia.org>
This commit is contained in:
@@ -9,6 +9,8 @@
|
|||||||
#include <hal/kpcr.h>
|
#include <hal/kpcr.h>
|
||||||
#include <hal/intr.h>
|
#include <hal/intr.h>
|
||||||
#include <ex/trace.h>
|
#include <ex/trace.h>
|
||||||
|
#include <ex/pool.h>
|
||||||
|
#include <ke/knot.h>
|
||||||
#include <machine/cpuid.h>
|
#include <machine/cpuid.h>
|
||||||
#include <machine/idt.h>
|
#include <machine/idt.h>
|
||||||
#include <stdef.h>
|
#include <stdef.h>
|
||||||
@@ -131,3 +133,22 @@ HalKpcrP1Init(KPCR *Kpcr)
|
|||||||
: "memory"
|
: "memory"
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
VOID
|
||||||
|
HalKpcrP2Init(KPCR *Kpcr)
|
||||||
|
{
|
||||||
|
ST_STATUS Status;
|
||||||
|
|
||||||
|
if (Kpcr == NULL) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Status = ExPoolInit(&Kpcr->AllocPool);
|
||||||
|
if (Status != STATUS_SUCCESS) {
|
||||||
|
KeKnot(
|
||||||
|
KNOT_MISC,
|
||||||
|
"failed to initialize pool for cpu%d\n",
|
||||||
|
Kpcr->CoreId
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -0,0 +1,65 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2026, Chloe M.
|
||||||
|
* Provided under the BSD-3 clause.
|
||||||
|
*
|
||||||
|
* Description: Pool allocator
|
||||||
|
* Author: Chloe M.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <ex/pool.h>
|
||||||
|
#include <ex/trace.h>
|
||||||
|
#include <mm/vmm.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#define DTRACE(Fmt, ...) \
|
||||||
|
TRACE("[ POOL ]: " Fmt, ##__VA_ARGS__)
|
||||||
|
|
||||||
|
/* Globals */
|
||||||
|
static USIZE PoolCount = 0;
|
||||||
|
|
||||||
|
static ST_STATUS
|
||||||
|
PoolInitBlock(MEMORY_BLOCK *Block)
|
||||||
|
{
|
||||||
|
if (Block == NULL) {
|
||||||
|
return STATUS_INVALID_PARAM;
|
||||||
|
}
|
||||||
|
|
||||||
|
Block->FirstPage = MmAllocPages(1);
|
||||||
|
if (Block->FirstPage == NULL) {
|
||||||
|
return STATUS_NO_MEMORY;
|
||||||
|
}
|
||||||
|
|
||||||
|
Block->LastPage = Block->FirstPage;
|
||||||
|
Block->PageCount = 1;
|
||||||
|
RtlMemSet(Block->FirstPage, 0, PAGESIZE);
|
||||||
|
return STATUS_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
ST_STATUS
|
||||||
|
ExPoolInit(MEMORY_POOL *Pool)
|
||||||
|
{
|
||||||
|
UCHAR LevelIdx;
|
||||||
|
MEMORY_BLOCK *Block;
|
||||||
|
ST_STATUS Status;
|
||||||
|
|
||||||
|
if (Pool == NULL) {
|
||||||
|
return STATUS_INVALID_PARAM;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Initialize the pools */
|
||||||
|
DTRACE("bringing up pool #%d\n", PoolCount);
|
||||||
|
for (LevelIdx = 0; LevelIdx < LEVEL_COUNT; ++LevelIdx) {
|
||||||
|
Block = &Pool->BlockLevels[LevelIdx];
|
||||||
|
Status = PoolInitBlock(Block);
|
||||||
|
|
||||||
|
/* XXX: We may wanna clean up our mess we made */
|
||||||
|
if (Status != STATUS_SUCCESS) {
|
||||||
|
DTRACE("critical: failed to initialize pool\n");
|
||||||
|
return STATUS_NO_MEMORY;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DTRACE("brought up %d levels for pool #%d : ok\n", LEVEL_COUNT, PoolCount);
|
||||||
|
++PoolCount;
|
||||||
|
return STATUS_SUCCESS;
|
||||||
|
}
|
||||||
@@ -0,0 +1,73 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2026, Chloe M.
|
||||||
|
* Provided under the BSD-3 clause.
|
||||||
|
*
|
||||||
|
* Description: Pool allocator
|
||||||
|
* Author: Chloe M.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _EX_POOL_H_
|
||||||
|
#define _EX_POOL_H_ 1
|
||||||
|
|
||||||
|
#include <hal/page.h>
|
||||||
|
#include <stapi/status.h>
|
||||||
|
#include <stdef.h>
|
||||||
|
|
||||||
|
/* Compute the granularity of a specific level */
|
||||||
|
#define LEVEL_GRAN(LEVEL) \
|
||||||
|
(1 << (3 + (LEVEL)))
|
||||||
|
|
||||||
|
/* Maximum levels per pool */
|
||||||
|
#define LEVEL_COUNT 8
|
||||||
|
|
||||||
|
/*
|
||||||
|
* When allocating pages, we sacrifice a little bit of its
|
||||||
|
* first bytes to store some metadata. This is the true size
|
||||||
|
* of unreserved / usable data.
|
||||||
|
*/
|
||||||
|
#define POOL_REAL_PAGESZ \
|
||||||
|
(PAGESIZE - sizeof(MEMORY_PAGE))
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Page data structure used internally to link together page
|
||||||
|
* lists
|
||||||
|
*
|
||||||
|
* @Bitmap: Bitmap to data [0 : free, 1 : allocated]
|
||||||
|
* @Next: Next page in list
|
||||||
|
*/
|
||||||
|
typedef struct _MEMORY_PAGE {
|
||||||
|
UQUAD Bitmap;
|
||||||
|
struct _MEMORY_PAGE *Next;
|
||||||
|
} MEMORY_PAGE;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* A memory block holds a list of memory chunks of a specific
|
||||||
|
* granularity.
|
||||||
|
*
|
||||||
|
* @FirstPage: First page in list
|
||||||
|
* @LastPage: Last page in list
|
||||||
|
* @PageCount: Number of pages total
|
||||||
|
*/
|
||||||
|
typedef struct {
|
||||||
|
MEMORY_PAGE *FirstPage;
|
||||||
|
MEMORY_PAGE *LastPage;
|
||||||
|
USIZE PageCount;
|
||||||
|
} MEMORY_BLOCK;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* A memory pool holds blocks of varying granularities
|
||||||
|
*
|
||||||
|
* @BlockLevels: Block levels [granularity : GRAN(level)]
|
||||||
|
*/
|
||||||
|
typedef struct {
|
||||||
|
MEMORY_BLOCK BlockLevels[LEVEL_COUNT];
|
||||||
|
} MEMORY_POOL;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Initialize a memory pool
|
||||||
|
*
|
||||||
|
* @Pool: Memory pool to initialize
|
||||||
|
*/
|
||||||
|
ST_STATUS ExPoolInit(MEMORY_POOL *Pool);
|
||||||
|
|
||||||
|
#endif /* !_EX_POOL_H_ */
|
||||||
@@ -11,6 +11,7 @@
|
|||||||
|
|
||||||
#include <stdef.h>
|
#include <stdef.h>
|
||||||
#include <machine/mcb.h>
|
#include <machine/mcb.h>
|
||||||
|
#include <ex/pool.h>
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The kernel processor control region contains MI
|
* The kernel processor control region contains MI
|
||||||
@@ -18,10 +19,12 @@
|
|||||||
*
|
*
|
||||||
* @CoreId: Processor core ID assigned by us
|
* @CoreId: Processor core ID assigned by us
|
||||||
* @Mcb: Machine-core block
|
* @Mcb: Machine-core block
|
||||||
|
* @AllocPool: Memory-allocation pool
|
||||||
*/
|
*/
|
||||||
typedef struct {
|
typedef struct {
|
||||||
USHORT CoreId;
|
USHORT CoreId;
|
||||||
MCB Mcb;
|
MCB Mcb;
|
||||||
|
MEMORY_POOL AllocPool;
|
||||||
} KPCR;
|
} KPCR;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -31,4 +34,11 @@ typedef struct {
|
|||||||
*/
|
*/
|
||||||
VOID HalKpcrP1Init(KPCR *Kpcr);
|
VOID HalKpcrP1Init(KPCR *Kpcr);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Phase 2 initialization of processor
|
||||||
|
*
|
||||||
|
* @Kpcr: KPCR to initialize
|
||||||
|
*/
|
||||||
|
VOID HalKpcrP2Init(KPCR *Kpcr);
|
||||||
|
|
||||||
#endif /* !_HAL_KPCR_H_ */
|
#endif /* !_HAL_KPCR_H_ */
|
||||||
|
|||||||
@@ -75,4 +75,7 @@ KiKernelEntry(VOID)
|
|||||||
|
|
||||||
/* Initialize ACPI */
|
/* Initialize ACPI */
|
||||||
AcpiInit();
|
AcpiInit();
|
||||||
|
|
||||||
|
/* Phase 2 initialization of the bootstrap core */
|
||||||
|
HalKpcrP2Init(&BootstrapCore);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user