Allocate space for a frame bitmap
Basically there, but still some kinks to work out...
This commit is contained in:
parent
764297de59
commit
109ea7ce2e
2 changed files with 64 additions and 8 deletions
|
@ -10,6 +10,7 @@
|
||||||
#include "kstd/Memory.hh"
|
#include "kstd/Memory.hh"
|
||||||
#include "kstd/PrintFormat.hh"
|
#include "kstd/PrintFormat.hh"
|
||||||
#include "memory/FrameAllocator.hh"
|
#include "memory/FrameAllocator.hh"
|
||||||
|
#include "memory/Memory.hh"
|
||||||
|
|
||||||
namespace kernel {
|
namespace kernel {
|
||||||
|
|
||||||
|
@ -23,16 +24,68 @@ void
|
||||||
FrameAllocator::initialize(const StartupInformation& startupInformation)
|
FrameAllocator::initialize(const StartupInformation& startupInformation)
|
||||||
{
|
{
|
||||||
// Page frame bitmap starts immediately after the kernel.
|
// Page frame bitmap starts immediately after the kernel.
|
||||||
mBitmap = reinterpret_cast<u8*>(startupInformation.kernelEnd);
|
mBitmap = reinterpret_cast<Bitmap*>(startupInformation.kernelEnd);
|
||||||
|
|
||||||
const u32 pageSize = startupInformation.pageSize;
|
const u32 numberOfPages = startupInformation.memorySize() / memory::pageSize;
|
||||||
const u32 numberOfPages = startupInformation.multibootInformation->memoryKB() * 1024 / pageSize;
|
const u32 pagesPerBitmap = Bitmap::length;
|
||||||
mBitmapSize = numberOfPages / (sizeof(FrameBitmap) * 8);
|
|
||||||
|
mBitmapSize = numberOfPages / pagesPerBitmap;
|
||||||
|
if ((numberOfPages % pagesPerBitmap) != 0) {
|
||||||
|
// Add an extra bitmap for the last few pages.
|
||||||
|
mBitmapSize++;
|
||||||
|
}
|
||||||
|
|
||||||
kstd::printFormat("Allocated bitmap of %ld bytes for %ld pages at 0x%08lX\n", mBitmapSize, numberOfPages, u32(mBitmap));
|
kstd::printFormat("Allocated bitmap of %ld bytes for %ld pages at 0x%08lX\n", mBitmapSize, numberOfPages, u32(mBitmap));
|
||||||
|
|
||||||
// TODO: Before modifying this memory, maybe make sure none of the multiboot information is hanging out there?
|
// TODO: Before modifying this memory, maybe make sure none of the multiboot information is hanging out there?
|
||||||
|
|
||||||
kstd::Memory::zero(mBitmap, mBitmapSize);
|
kstd::Memory::zero(mBitmap, mBitmapSize);
|
||||||
|
|
||||||
|
// Lower 1 MB is always allocated.
|
||||||
|
reserveRange(0, 0x100000);
|
||||||
|
// Kernel image (including this frame bitmap) is always allocated.
|
||||||
|
reserveRange(startupInformation.kernelStart, startupInformation.kernelSize() + mBitmapSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
FrameAllocator::reserveRange(u32 start,
|
||||||
|
u32 length)
|
||||||
|
{
|
||||||
|
// TODO: `start` and `length` validation.
|
||||||
|
const u32 pagesPerBitmap = Bitmap::length;
|
||||||
|
|
||||||
|
const u32 startPage = memory::pageAlignDown(start) / memory::pageSize;
|
||||||
|
const u32 endPage = memory::pageAlignUp(start + length) / memory::pageSize;
|
||||||
|
|
||||||
|
// Iterators
|
||||||
|
u32 page = startPage;
|
||||||
|
u32 bitmapIndex = start / pagesPerBitmap;
|
||||||
|
u8 bitmapOffset = start % pagesPerBitmap;
|
||||||
|
|
||||||
|
kstd::printFormat("Reserving %ld pages for memory addresses between 0x%08lX and 0x%08lX\n", endPage - startPage, start, start + length);
|
||||||
|
|
||||||
|
// Fill in any entries that aren't aligned to pagesPerBitmap at the beginning.
|
||||||
|
while (bitmapOffset != 0) {
|
||||||
|
mBitmap[bitmapIndex].set(bitmapOffset);
|
||||||
|
bitmapOffset = (bitmapOffset + 1) % 8;
|
||||||
|
page++;
|
||||||
|
if (bitmapOffset == 0) {
|
||||||
|
bitmapIndex++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fill in entries in `pagesPerBitmap` sized chunks.
|
||||||
|
while ((endPage - page) > pagesPerBitmap) {
|
||||||
|
mBitmap[bitmapIndex++].fill();
|
||||||
|
page += pagesPerBitmap;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fill in any entries that aren't aligned to `pagesPerBitmap` at the end of the range.
|
||||||
|
while ((endPage - page) > 0) {
|
||||||
|
mBitmap[bitmapIndex].set(bitmapOffset);
|
||||||
|
bitmapOffset = (bitmapOffset + 1) % 8;
|
||||||
|
page++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
} /* namespace kernel */
|
} /* namespace kernel */
|
||||||
|
|
|
@ -10,9 +10,9 @@
|
||||||
#define __MEMORY_FRAMEALLOCATOR_HH__
|
#define __MEMORY_FRAMEALLOCATOR_HH__
|
||||||
|
|
||||||
#include "StartupInformation.hh"
|
#include "StartupInformation.hh"
|
||||||
|
#include "kstd/Bitmap.hh"
|
||||||
#include "kstd/Types.hh"
|
#include "kstd/Types.hh"
|
||||||
|
|
||||||
|
|
||||||
namespace kernel {
|
namespace kernel {
|
||||||
|
|
||||||
struct FrameAllocator
|
struct FrameAllocator
|
||||||
|
@ -22,12 +22,15 @@ struct FrameAllocator
|
||||||
void initialize(const StartupInformation& startupInformation);
|
void initialize(const StartupInformation& startupInformation);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef u8 FrameBitmap;
|
typedef kstd::Bitmap<u8> Bitmap;
|
||||||
|
|
||||||
/** Starting address of the frame allocation bitmap. */
|
/** Starting address of the frame allocation bitmap. */
|
||||||
FrameBitmap* mBitmap;
|
Bitmap* mBitmap;
|
||||||
/** Size of the bitmap in bytes. */
|
/** Size of the bitmap in `sizeof(Bitmap)` units. */
|
||||||
u32 mBitmapSize;
|
u32 mBitmapSize;
|
||||||
|
|
||||||
|
/** Reserve a range of memory. */
|
||||||
|
void reserveRange(u32 start, u32 length);
|
||||||
};
|
};
|
||||||
|
|
||||||
} /* namespace */
|
} /* namespace */
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue