From c4088eaf5b79c6a19d46bee499a1c184bc2f129b Mon Sep 17 00:00:00 2001
From: John Hodge <tpg@mutabah.net>
Date: Wed, 19 Jan 2011 07:44:34 +0800
Subject: [PATCH] - Misc changes

- Tracing case where interrupts are disabled
 > In the x86 build, somewhere (in some cases) IF is cleared when it should
   not be, causing a system lock up.
- Sped up Heap_Allocate with __Bytes == 0 (returns an non-null invalid pointer)
---
 Kernel/Makefile.BuildNum.x86_64   |  2 +-
 Kernel/arch/x86/include/arch.h    |  2 ++
 Kernel/arch/x86/irq.c             |  9 +++++++--
 Kernel/arch/x86/lib.c             |  9 +++++++--
 Kernel/arch/x86_64/include/arch.h |  2 ++
 Kernel/heap.c                     | 13 +++++++++++--
 6 files changed, 30 insertions(+), 7 deletions(-)

diff --git a/Kernel/Makefile.BuildNum.x86_64 b/Kernel/Makefile.BuildNum.x86_64
index 9c07d1bc..89ed6d5e 100644
--- a/Kernel/Makefile.BuildNum.x86_64
+++ b/Kernel/Makefile.BuildNum.x86_64
@@ -1 +1 @@
-BUILD_NUM = 223
+BUILD_NUM = 224
diff --git a/Kernel/arch/x86/include/arch.h b/Kernel/arch/x86/include/arch.h
index c4b3a2e6..109f6506 100644
--- a/Kernel/arch/x86/include/arch.h
+++ b/Kernel/arch/x86/include/arch.h
@@ -10,6 +10,8 @@
 #define	KERNEL_BASE	0xC0000000
 #define BITS	32
 
+#define INVLPTR	((void*)-1)
+
 // Allow nested spinlocks?
 #define STACKED_LOCKS	2	// 0: No, 1: Per-CPU, 2: Per-Thread
 #define LOCK_DISABLE_INTS	1
diff --git a/Kernel/arch/x86/irq.c b/Kernel/arch/x86/irq.c
index 7ff1fe94..e08f1ba0 100644
--- a/Kernel/arch/x86/irq.c
+++ b/Kernel/arch/x86/irq.c
@@ -6,6 +6,7 @@
 
 // === CONSTANTS ===
 #define	MAX_CALLBACKS_PER_IRQ	4
+#define TRACE_IRQS	0
 
 // === TYPES ===
 typedef void (*tIRQ_Callback)(int);
@@ -28,9 +29,13 @@ void IRQ_Handler(tRegs *Regs)
 
 	for( i = 0; i < MAX_CALLBACKS_PER_IRQ; i++ )
 	{
-		//Log(" IRQ_Handler: Call %p", gIRQ_Handlers[Regs->int_num][i]);
-		if( gIRQ_Handlers[Regs->int_num][i] )
+		if( gIRQ_Handlers[Regs->int_num][i] ) {
 			gIRQ_Handlers[Regs->int_num][i](Regs->int_num);
+			#if TRACE_IRQS
+			if( Regs->int_num != 8 )
+				Log("IRQ %i: Call %p", Regs->int_num, gIRQ_Handlers[Regs->int_num][i]);
+			#endif
+		}
 	}
 
 	//Log(" IRQ_Handler: Resetting");
diff --git a/Kernel/arch/x86/lib.c b/Kernel/arch/x86/lib.c
index 1f563948..86117ccb 100644
--- a/Kernel/arch/x86/lib.c
+++ b/Kernel/arch/x86/lib.c
@@ -58,8 +58,8 @@ void SHORTLOCK(struct sShortSpinlock *Lock)
 	#endif
 	
 	#if LOCK_DISABLE_INTS
-	// Save interrupt state and clear interrupts
-	__ASM__ ("pushf;\n\tpop %%eax\n\tcli" : "=a"(IF));
+	// Save interrupt state
+	__ASM__ ("pushf;\n\tpop %0" : "=r"(IF));
 	IF &= 0x200;	// AND out all but the interrupt flag
 	#endif
 	
@@ -93,9 +93,14 @@ void SHORTLOCK(struct sShortSpinlock *Lock)
 		#else
 		__ASM__("xchgl %%eax, (%%edi)":"=a"(v):"a"(1),"D"(&Lock->Lock));
 		#endif
+		
+		#if LOCK_DISABLE_INTS
+		if( v )	__ASM__("sti");	// Re-enable interrupts
+		#endif
 	}
 	
 	#if LOCK_DISABLE_INTS
+	__ASM__("cli");
 	Lock->IF = IF;
 	#endif
 }
diff --git a/Kernel/arch/x86_64/include/arch.h b/Kernel/arch/x86_64/include/arch.h
index 78b2acce..038b6384 100644
--- a/Kernel/arch/x86_64/include/arch.h
+++ b/Kernel/arch/x86_64/include/arch.h
@@ -13,6 +13,8 @@
 #define STACKED_LOCKS	0
 #define LOCK_DISABLE_INTS	1
 
+#define INVLPTR	((void*)0x0FFFFFFFFFFFFFFFULL)
+
 //#define INT_MAX	0x7FFFFFFF
 //#define UINT_MAX	0xFFFFFFFF
 
diff --git a/Kernel/heap.c b/Kernel/heap.c
index abf5f27e..34dd5f2c 100644
--- a/Kernel/heap.c
+++ b/Kernel/heap.c
@@ -143,6 +143,11 @@ void *Heap_Allocate(const char *File, int Line, size_t __Bytes)
 	tHeapHead	*best = NULL;
 	Uint	bestSize = 0;	// Speed hack
 	size_t	Bytes;
+
+	if( __Bytes == 0 ) {
+		//return NULL;	// TODO: Return a known un-mapped range.
+		return INVLPTR;
+	}
 	
 	// Get required size
 	#if POW2_SIZES
@@ -277,6 +282,10 @@ void Heap_Deallocate(void *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;
+	
 	// Alignment Check
 	if( (Uint)Ptr & (sizeof(Uint)-1) ) {
 		Log_Warning("Heap", "free - Passed a non-aligned address (%p)", Ptr);
@@ -644,8 +653,8 @@ void Heap_Stats(void)
 		
 		// Print the block info?
 		#if 1
-		Log_Debug("Heap", "%p - 0x%x Owned by %s:%i",
-			head, head->Size, head->File, head->Line);
+		Log_Debug("Heap", "%p - 0x%x (%i) Owned by %s:%i",
+			head, head->Size, head->ValidSize, head->File, head->Line);
 		#endif
 	}
 
-- 
GitLab