X-Git-Url: https://git.ucc.asn.au/?a=blobdiff_plain;f=Kernel%2Fheap.c;h=fc99f56c212147a018eb809d2b9abe853bad0ded;hb=89366ca2a9eccc040127d193e55da74507d6026f;hp=34dd5f2c44d621a161152679fa3c03d25785327f;hpb=c4088eaf5b79c6a19d46bee499a1c184bc2f129b;p=tpg%2Facess2.git diff --git a/Kernel/heap.c b/Kernel/heap.c index 34dd5f2c..fc99f56c 100644 --- a/Kernel/heap.c +++ b/Kernel/heap.c @@ -28,10 +28,10 @@ void Heap_Install(void); void *Heap_Extend(int Bytes); void *Heap_Merge(tHeapHead *Head); -void *Heap_Allocate(const char *File, int Line, size_t Bytes); -void *Heap_AllocateZero(const char *File, int Line, size_t Bytes); -void *Heap_Reallocate(const char *File, int Line, void *Ptr, size_t Bytes); -void Heap_Deallocate(void *Ptr); +//void *Heap_Allocate(const char *File, int Line, size_t Bytes); +//void *Heap_AllocateZero(const char *File, int Line, size_t Bytes); +//void *Heap_Reallocate(const char *File, int Line, void *Ptr, size_t Bytes); +//void Heap_Deallocate(void *Ptr); void Heap_Dump(void); void Heap_Stats(void); @@ -62,6 +62,11 @@ void *Heap_Extend(int Bytes) if( (tVAddr)gHeapEnd == MM_KHEAP_MAX ) return NULL; + if( Bytes == 0 ) { + Log_Warning("Heap", "Heap_Extend called with Bytes=%i", Bytes); + return NULL; + } + // Bounds Check if( (tVAddr)gHeapEnd + ((Bytes+0xFFF)&~0xFFF) > MM_KHEAP_MAX ) { Bytes = MM_KHEAP_MAX - (tVAddr)gHeapEnd; @@ -69,11 +74,17 @@ void *Heap_Extend(int Bytes) } // Heap expands in pages - for(i=0;i<(Bytes+0xFFF)>>12;i++) - MM_Allocate( (tVAddr)gHeapEnd+(i<<12) ); + for( i = 0; i < (Bytes+0xFFF) >> 12; i ++ ) + { + if( !MM_Allocate( (tVAddr)gHeapEnd+(i<<12) ) ) + { + Warning("OOM - Heap_Extend"); + return NULL; + } + } // Increas heap end - gHeapEnd += i << 12; + gHeapEnd = (Uint8*)gHeapEnd + (i << 12); // Create Block head->Size = (Bytes+0xFFF)&~0xFFF; @@ -200,9 +211,11 @@ void *Heap_Allocate(const char *File, int Line, size_t __Bytes) head->Magic = MAGIC_USED; head->File = File; head->Line = Line; + head->ValidSize = __Bytes; + head->AllocateTime = now(); Mutex_Release(&glHeap); // Release spinlock #if DEBUG_TRACE - Log("[Heap ] Malloc'd %p (%i bytes), returning to %p", head->Data, head->Size, __builtin_return_address(0)); + Debug("[Heap ] Malloc'd %p (%i bytes), returning to %p", head->Data, head->Size, __builtin_return_address(0)); #endif return head->Data; } @@ -235,9 +248,11 @@ void *Heap_Allocate(const char *File, int Line, size_t __Bytes) best->Magic = MAGIC_USED; // Mark block as used best->File = File; best->Line = Line; + best->ValidSize = __Bytes; + best->AllocateTime = now(); Mutex_Release(&glHeap); // Release spinlock #if DEBUG_TRACE - Log("[Heap ] Malloc'd %p (%i bytes), returning to %p", best->Data, best->Size, __builtin_return_address(0)); + Debug("[Heap ] Malloc'd %p (%i bytes), returning to %s:%i", best->Data, best->Size, File, Line); #endif return best->Data; } @@ -258,11 +273,11 @@ void *Heap_Allocate(const char *File, int Line, size_t __Bytes) best->Magic = MAGIC_USED; // Mark block as used best->File = File; best->Line = Line; + best->AllocateTime = now(); Mutex_Release(&glHeap); // Release spinlock #if DEBUG_TRACE - Log_Debug("Heap", "newhead(%p)->Size = 0x%x", newhead, newhead->Size); - Log_Debug("Heap", "Malloc'd %p (0x%x bytes), returning to %s:%i", + Debug("[Heap ] Malloc'd %p (0x%x bytes), returning to %s:%i", best->Data, best->Size, File, Line); #endif return best->Data; @@ -274,18 +289,17 @@ void *Heap_Allocate(const char *File, int Line, size_t __Bytes) */ void Heap_Deallocate(void *Ptr) { - tHeapHead *head; + tHeapHead *head = (void*)( (Uint)Ptr - sizeof(tHeapHead) ); tHeapFoot *foot; - #if DEBUG_TRACE - Log_Log("Heap", "free: Ptr = %p", Ptr); - Log_Log("Heap", "free: Returns to %p", __builtin_return_address(0)); - #endif - // INVLPTR is returned from Heap_Allocate when the allocation // size is zero. if( Ptr == INVLPTR ) return; + #if DEBUG_TRACE + Debug("[Heap ] free: %p freed by %p (%i old)", Ptr, __builtin_return_address(0), now()-head->AllocateTime); + #endif + // Alignment Check if( (Uint)Ptr & (sizeof(Uint)-1) ) { Log_Warning("Heap", "free - Passed a non-aligned address (%p)", Ptr); @@ -308,7 +322,7 @@ void Heap_Deallocate(void *Ptr) } if(head->Magic != MAGIC_USED) { Log_Warning("Heap", "free - Magic value is invalid (%p, 0x%x)", head, head->Magic); - Log_Notice("Heap", "Allocated %s:%i", head->File, head->Line); + Log_Notice("Heap", "Allocated by %s:%i", head->File, head->Line); return; } @@ -316,12 +330,12 @@ void Heap_Deallocate(void *Ptr) foot = (void*)( (Uint)head + head->Size - sizeof(tHeapFoot) ); if(foot->Head != head) { Log_Warning("Heap", "free - Footer backlink is incorrect (%p, 0x%x)", head, foot->Head); - Log_Notice("Heap", "Allocated %s:%i", head->File, head->Line); + Log_Notice("Heap", "Allocated by %s:%i", head->File, head->Line); return; } if(foot->Magic != MAGIC_FOOT) { Log_Warning("Heap", "free - Footer magic is invalid (%p, %p = 0x%x)", head, &foot->Magic, foot->Magic); - Log_Notice("Heap", "Allocated %s:%i", head->File, head->Line); + Log_Notice("Heap", "Allocated by %s:%i", head->File, head->Line); return; } @@ -555,9 +569,10 @@ void Heap_Dump(void) return ; #if !VERBOSE_DUMP - Log_Log("Heap", "%p (0x%llx): 0x%08lx (%i) %4C", + Log_Log("Heap", "%p (%P): 0x%08lx %i %4C", head, MM_GetPhysAddr((Uint)head), head->Size, head->ValidSize, &head->Magic); - Log_Log("Heap", "%p %4C", foot->Head, &foot->Magic); + if(foot) + Log_Log("Heap", "Backlink = %p %4C", foot->Head, &foot->Magic); if(head->File) { Log_Log("Heap", "%sowned by %s:%i", (head->Magic==MAGIC_FREE?"was ":""), head->File, head->Line); @@ -574,7 +589,7 @@ void Heap_Dump(void) head = foot->Head; while( (tVAddr)head >= (tVAddr)badHead ) { - Log_Log("Heap", "%p (0x%llx): 0x%08lx %i %4C", + Log_Log("Heap", "%p (%P): 0x%08lx %i %4C", head, MM_GetPhysAddr((Uint)head), head->Size, head->ValidSize, &head->Magic); Log_Log("Heap", "%p %4C", foot->Head, &foot->Magic); if(head->File) @@ -653,17 +668,29 @@ void Heap_Stats(void) // Print the block info? #if 1 - Log_Debug("Heap", "%p - 0x%x (%i) Owned by %s:%i", - head, head->Size, head->ValidSize, head->File, head->Line); + if( head->Magic == MAGIC_FREE ) + Log_Debug("Heap", "%p (%P) - 0x%x free", + head->Data, MM_GetPhysAddr((tVAddr)&head->Data), head->Size); + else + Log_Debug("Heap", "%p (%P) - 0x%x (%i) Owned by %s:%i (%lli ms old)", + head->Data, MM_GetPhysAddr((tVAddr)&head->Data), head->Size, head->ValidSize, head->File, head->Line, + now() - head->AllocateTime + ); #endif } Log_Log("Heap", "%i blocks (0x%x bytes)", nBlocks, totalBytes); Log_Log("Heap", "%i free blocks (0x%x bytes)", nFree, freeBytes); - frag = (nFree-1)*10000/nBlocks; + if(nBlocks != 0) + frag = (nFree-1)*10000/nBlocks; + else + frag = 0; Log_Log("Heap", "%i.%02i%% Heap Fragmentation", frag/100, frag%100); avgAlloc = (totalBytes-freeBytes)/(nBlocks-nFree); - overhead = (sizeof(tHeapFoot)+sizeof(tHeapHead))*10000/avgAlloc; + if(avgAlloc != 0) + overhead = (sizeof(tHeapFoot)+sizeof(tHeapHead))*10000/avgAlloc; + else + overhead = 0; Log_Log("Heap", "Average allocation: %i bytes, Average Overhead: %i.%02i%%", avgAlloc, overhead/100, overhead%100 );