Improved memory management

The heap now sets it's size at run time instead of being hard coded

svn path=/trunk/; revision=2656
This commit is contained in:
Brian Palmer 2002-02-27 21:33:59 +00:00
parent 463cc8858c
commit b764471786
10 changed files with 173 additions and 56 deletions

View file

@ -33,8 +33,8 @@ LIB_FILES2 = comm/comm.a disk/disk.a mm/mm.a cache/cache.a
all: freeldr.sys
freeldr.sys: c_code.a
$(LD) -N -Ttext=0x8000 --oformat=binary -s -o f.sys c_code.a
freeldr.sys: c_code.a end.o
$(LD) -N -Ttext=0x8000 --oformat=binary -s -o f.sys c_code.a end.o
../bootsect/stubit ../bootsect/fatstub.bin f.sys freeldr.sys
freeldr.exe: asmcode.a c_code.a
@ -73,6 +73,9 @@ parseini.o: parseini.c parseini.h
oslist.o: oslist.c oslist.h
$(CC) $(FLAGS) -o oslist.o -c oslist.c
end.o: end.S
$(CC) $(FLAGS) -o end.o -c end.S
arch:
$(MAKE) -C arch

View file

@ -57,4 +57,6 @@
void enable_a20(void);
void stop_floppy(void);
extern unsigned long FreeLoaderModuleEnd;
#endif /* ! ASM */

View file

@ -106,7 +106,7 @@ EXTERN(_GetExtendedMemorySize)
EXTERN(_GetConventionalMemorySize)
//
// get conventional memory size in KB
// Get conventional memory size in KB
//
pushl %edx
@ -123,7 +123,7 @@ EXTERN(_GetConventionalMemorySize)
andl $0xffff,%eax*/ // clear carry
/* Save return value */
movl %eax,%edx
movzwl %ax,%edx
call switch_to_prot

27
freeldr/freeldr/end.S Normal file
View file

@ -0,0 +1,27 @@
/*
* FreeLoader
* Copyright (C) 1998-2002 Brian Palmer <brianp@sginet.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
.text
#define ASM
#include "arch.h"
EXTERN(_FreeLoaderModuleEnd)
.long _FreeLoaderModuleEnd

View file

@ -40,7 +40,6 @@ LONG GetTimeOut(VOID);
VOID BootMain(VOID)
{
ULONG Idx;
UCHAR SettingName[80];
UCHAR SettingValue[80];
ULONG SectionId;
@ -57,7 +56,7 @@ VOID BootMain(VOID)
DebugInit();
#endif
InitMemoryManager( (PVOID) 0x20000 /* BaseAddress */, 0x58000 /* Length */);
InitMemoryManager();
if (!ParseIniFile())
{

View file

@ -24,7 +24,7 @@
#include <multiboot.h>
VOID InitMemoryManager(PVOID BaseAddress, ULONG Length);
VOID InitMemoryManager(VOID);
PVOID AllocateMemory(ULONG NumberOfBytes);
VOID FreeMemory(PVOID MemBlock);

View file

@ -19,7 +19,7 @@
include ../rules.mk
OBJS = mm.o
OBJS = mm.o init.o
.PHONY : clean
@ -28,9 +28,12 @@ all: mm.a
mm.a: $(OBJS)
$(LD) -r -o mm.a $(OBJS)
mm.o: mm.c ../mm.h
mm.o: mm.c ../mm.h mem.h
$(CC) $(FLAGS) -o mm.o -c mm.c
init.o: init.c ../mm.h mem.h
$(CC) $(FLAGS) -o init.o -c init.c
clean:
- $(RM) *.o
- $(RM) *.a

81
freeldr/freeldr/mm/init.c Normal file
View file

@ -0,0 +1,81 @@
/*
* FreeLoader
* Copyright (C) 1998-2002 Brian Palmer <brianp@sginet.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <freeldr.h>
#include <arch.h>
#include <mm.h>
#include "mem.h"
#include <rtl.h>
#include <debug.h>
#include <ui.h>
ULONG RealFreeLoaderModuleEnd = 0;
PVOID HeapBaseAddress = NULL;
ULONG HeapLengthInBytes = 0;
ULONG HeapMemBlockCount = 0;
PMEMBLOCK HeapMemBlockArray = NULL;
VOID InitMemoryManager(VOID)
{
ULONG MemBlocks;
ULONG BaseAddress;
ULONG Length;
// Round up to the next page of memory
RealFreeLoaderModuleEnd = ((FreeLoaderModuleEnd + 4095) / 4096) * 4096;
BaseAddress = RealFreeLoaderModuleEnd;
Length = (MAXLOWMEMADDR - RealFreeLoaderModuleEnd);
DbgPrint((DPRINT_MEMORY, "Initializing Memory Manager.\n"));
DbgPrint((DPRINT_MEMORY, "Conventional memory size: %d KB\n", GetConventionalMemorySize()));
DbgPrint((DPRINT_MEMORY, "Low memory map:\n"));
DbgPrint((DPRINT_MEMORY, "00000\t1000\tReserved\n"));
DbgPrint((DPRINT_MEMORY, "01000\t6000\t16-bit stack\n"));
DbgPrint((DPRINT_MEMORY, "07000\t1000\tUnused\n"));
DbgPrint((DPRINT_MEMORY, "08000\t%x\tFreeLoader program code\n", (RealFreeLoaderModuleEnd - 0x8000)));
DbgPrint((DPRINT_MEMORY, "%x\t%x\tLow memory heap\n", BaseAddress, Length));
DbgPrint((DPRINT_MEMORY, "78000\t8000\t32-bit stack\n"));
DbgPrint((DPRINT_MEMORY, "80000\t10000\tFile system read buffer\n"));
DbgPrint((DPRINT_MEMORY, "90000\t10000\tDisk read buffer\n"));
DbgPrint((DPRINT_MEMORY, "A0000\t60000\tReserved\n"));
// Calculate how many memory blocks we have
MemBlocks = (Length / MEM_BLOCK_SIZE);
// Adjust the heap length so we can reserve
// enough storage space for the MEMBLOCK array
Length -= (MemBlocks * sizeof(MEMBLOCK));
// Initialize our tracking variables
HeapBaseAddress = BaseAddress;
HeapLengthInBytes = Length;
HeapMemBlockCount = (HeapLengthInBytes / MEM_BLOCK_SIZE);
HeapMemBlockArray = (PMEMBLOCK)(HeapBaseAddress + HeapLengthInBytes);
// Clear the memory
RtlZeroMemory(HeapBaseAddress, HeapLengthInBytes);
RtlZeroMemory(HeapMemBlockArray, (HeapMemBlockCount * sizeof(MEMBLOCK)));
#ifdef DEBUG
DbgPrint((DPRINT_MEMORY, "Memory Manager initialized. BaseAddress = 0x%x Length = 0x%x. %d blocks in heap.\n", BaseAddress, Length, HeapMemBlockCount));
//MemAllocTest();
#endif
}

48
freeldr/freeldr/mm/mem.h Normal file
View file

@ -0,0 +1,48 @@
/*
* FreeLoader
* Copyright (C) 1998-2002 Brian Palmer <brianp@sginet.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef __MEM_H
#define __MEM_H
//
// Define this to 1 if you want the entire contents
// of the memory allocation bitmap displayed
// when a chunk is allocated or freed
//
#define DUMP_MEM_MAP_ON_VERIFY 0
#define MEM_BLOCK_SIZE 256
typedef struct
{
BOOL MemBlockAllocated; // Is this block allocated or free
ULONG BlocksAllocated; // Block length, in multiples of MEM_BLOCK_SIZE
} MEMBLOCK, *PMEMBLOCK;
extern ULONG RealFreeLoaderModuleEnd;
extern PVOID HeapBaseAddress;
extern ULONG HeapLengthInBytes;
extern ULONG HeapMemBlockCount;
extern PMEMBLOCK HeapMemBlockArray;
#endif // defined __MEM_H

View file

@ -19,31 +19,12 @@
#include <freeldr.h>
#include <mm.h>
#include "mem.h"
#include <rtl.h>
#include <debug.h>
#include <ui.h>
//
// Define this to 1 if you want the entire contents
// of the memory allocation bitmap displayed
// when a chunk is allocated or freed
//
#define DUMP_MEM_MAP_ON_VERIFY 0
#define MEM_BLOCK_SIZE 256
typedef struct
{
BOOL MemBlockAllocated; // Is this block allocated or free
ULONG BlocksAllocated; // Block length, in multiples of 256 bytes
} MEMBLOCK, *PMEMBLOCK;
PVOID HeapBaseAddress = NULL;
ULONG HeapLengthInBytes = 0;
ULONG HeapMemBlockCount = 0;
PMEMBLOCK HeapMemBlockArray = NULL;
#ifdef DEBUG
ULONG AllocationCount = 0;
@ -54,33 +35,6 @@ VOID DecrementAllocationCount(VOID);
VOID MemAllocTest(VOID);
#endif // DEBUG
VOID InitMemoryManager(PVOID BaseAddress, ULONG Length)
{
ULONG MemBlocks;
// Calculate how many memory blocks we have
MemBlocks = (Length / MEM_BLOCK_SIZE);
// Adjust the heap length so we can reserve
// enough storage space for the MEMBLOCK array
Length -= (MemBlocks * sizeof(MEMBLOCK));
// Initialize our tracking variables
HeapBaseAddress = BaseAddress;
HeapLengthInBytes = Length;
HeapMemBlockCount = (HeapLengthInBytes / MEM_BLOCK_SIZE);
HeapMemBlockArray = (PMEMBLOCK)(HeapBaseAddress + HeapLengthInBytes);
// Clear the memory
RtlZeroMemory(HeapBaseAddress, HeapLengthInBytes);
RtlZeroMemory(HeapMemBlockArray, (HeapMemBlockCount * sizeof(MEMBLOCK)));
#ifdef DEBUG
DbgPrint((DPRINT_MEMORY, "Memory Manager initialized. BaseAddress = 0x%x Length = 0x%x. %d blocks in heap.\n", BaseAddress, Length, HeapMemBlockCount));
//MemAllocTest();
#endif
}
PVOID AllocateMemory(ULONG NumberOfBytes)
{
ULONG BlocksNeeded;