Working on MP build (now can run, just crashes due to CPUs treading on each other...
[tpg/acess2.git] / Kernel / arch / x86 / mm_virt.c
index db89cc1..8902837 100644 (file)
@@ -12,6 +12,7 @@
 #define DEBUG  0
 #define SANITY 1
 #include <acess.h>
+#include <mm_virt.h>
 #include <mm_phys.h>
 #include <proc.h>
 
@@ -66,14 +67,15 @@ typedef Uint32      tTabEnt;
 #endif
 
 // === IMPORTS ===
+extern void    _UsertextEnd, _UsertextBase;
 extern Uint32  gaInitPageDir[1024];
 extern Uint32  gaInitPageTable[1024];
 extern void    Threads_SegFault(tVAddr Addr);
 extern void    Error_Backtrace(Uint eip, Uint ebp);
 
 // === PROTOTYPES ===
-void   MM_PreinitVirtual();
-void   MM_InstallVirtual();
+void   MM_PreinitVirtual(void);
+void   MM_InstallVirtual(void);
 void   MM_PageFault(tVAddr Addr, Uint ErrorCode, tRegs *Regs);
 void   MM_DumpTables(tVAddr Start, tVAddr End);
 tPAddr MM_DuplicatePage(tVAddr VAddr);
@@ -100,10 +102,10 @@ Uint32    gWorkerStacks[(NUM_WORKER_STACKS+31)/32];
 
 // === CODE ===
 /**
- * \fn void MM_PreinitVirtual()
+ * \fn void MM_PreinitVirtual(void)
  * \brief Maps the fractal mappings
  */
-void MM_PreinitVirtual()
+void MM_PreinitVirtual(void)
 {
        #if USE_PAE
        gaInitPageDir[ ((PAGE_TABLE_ADDR >> TAB)-3*512+3)*2 ] = ((tTabEnt)&gaInitPageDir - KERNEL_BASE) | 3;
@@ -114,10 +116,10 @@ void MM_PreinitVirtual()
 }
 
 /**
- * \fn void MM_InstallVirtual()
+ * \fn void MM_InstallVirtual(void)
  * \brief Sets up the constant page mappings
  */
-void MM_InstallVirtual()
+void MM_InstallVirtual(void)
 {
         int    i;
        
@@ -153,12 +155,17 @@ void MM_InstallVirtual()
                memset( &gaPageTable[i*1024], 0, 0x1000 );
        }
        #endif
+       
+       // Unset kernel on the User Text pages
+       for( i = ((tVAddr)&_UsertextEnd-(tVAddr)&_UsertextBase+0xFFF)/4096; i--; ) {
+               MM_SetFlags( (tVAddr)&_UsertextBase + i*4096, 0, MM_PFLAG_KERNEL );
+       }
 }
 
 /**
  * \brief Cleans up the SMP required mappings
  */
-void MM_FinishVirtualInit()
+void MM_FinishVirtualInit(void)
 {
        #if USE_PAE
        gaInitPDPT[ 0 ] = 0;
@@ -239,6 +246,19 @@ void MM_PageFault(tVAddr Addr, Uint ErrorCode, tRegs *Regs)
        
        //MM_DumpTables(0, -1); 
        
+       // Register Dump
+       Log("EAX %08x ECX %08x EDX %08x EBX %08x", Regs->eax, Regs->ecx, Regs->edx, Regs->ebx);
+       Log("ESP %08x EBP %08x ESI %08x EDI %08x", Regs->esp, Regs->ebp, Regs->esi, Regs->edi);
+       //Log("SS:ESP %04x:%08x", Regs->ss, Regs->esp);
+       Log("CS:EIP %04x:%08x", Regs->cs, Regs->eip);
+       Log("DS %04x ES %04x FS %04x GS %04x", Regs->ds, Regs->es, Regs->fs, Regs->gs);
+       {
+               Uint    dr0, dr1;
+               __ASM__ ("mov %%dr0, %0":"=r"(dr0):);
+               __ASM__ ("mov %%dr1, %0":"=r"(dr1):);
+               Log("DR0 %08x DR1 %08x", dr0, dr1);
+       }
+       
        Panic("Page Fault at 0x%x (Accessed 0x%x)", Regs->eip, Addr);
 }
 
@@ -405,27 +425,11 @@ tPAddr MM_GetPhysAddr(tVAddr Addr)
        return (gaPageTable[Addr >> 12] & ~0xFFF) | (Addr & 0xFFF);
 }
 
-
 /**
- * \fn int MM_IsUser(tVAddr VAddr)
- * \brief Checks if a page is user accessable
- */
-int MM_IsUser(tVAddr VAddr)
-{
-       if( !(gaPageDir[VAddr >> 22] & 1) )
-               return 0;
-       if( !(gaPageTable[VAddr >> 12] & 1) )
-               return 0;
-       if( !(gaPageTable[VAddr >> 12] & PF_USER) )
-               return 0;
-       return 1;
-}
-
-/**
- * \fn void MM_SetCR3(tPAddr CR3)
+ * \fn void MM_SetCR3(Uint CR3)
  * \brief Sets the current process space
  */
-void MM_SetCR3(tPAddr CR3)
+void MM_SetCR3(Uint CR3)
 {
        __asm__ __volatile__ ("mov %0, %%cr3"::"r"(CR3));
 }
@@ -487,7 +491,7 @@ int MM_Map(tVAddr VAddr, tPAddr PAddr)
  * \fn tVAddr MM_ClearUser()
  * \brief Clear user's address space
  */
-tVAddr MM_ClearUser()
+tVAddr MM_ClearUser(void)
 {
        Uint    i, j;
        
@@ -518,10 +522,10 @@ tVAddr MM_ClearUser()
 }
 
 /**
- * \fn tPAddr MM_Clone()
+ * \fn tPAddr MM_Clone(void)
  * \brief Clone the current address space
  */
-tPAddr MM_Clone()
+tPAddr MM_Clone(void)
 {
        Uint    i, j;
        tVAddr  ret;
@@ -644,10 +648,10 @@ tPAddr MM_Clone()
 }
 
 /**
- * \fn tVAddr MM_NewKStack()
+ * \fn tVAddr MM_NewKStack(void)
  * \brief Create a new kernel stack
  */
-tVAddr MM_NewKStack()
+tVAddr MM_NewKStack(void)
 {
        tVAddr  base = KERNEL_STACKS;
        Uint    i;
@@ -781,15 +785,25 @@ void MM_SetFlags(tVAddr VAddr, Uint Flags, Uint Mask)
        // Read-Only
        if( Mask & MM_PFLAG_RO )
        {
-               if( Flags & MM_PFLAG_RO )       *ent &= ~PF_WRITE;
-               else    *ent |= PF_WRITE;
+               if( Flags & MM_PFLAG_RO ) {
+                       *ent &= ~PF_WRITE;
+               }
+               else {
+                       gaPageDir[VAddr >> 22] |= PF_WRITE;
+                       *ent |= PF_WRITE;
+               }
        }
        
        // Kernel
        if( Mask & MM_PFLAG_KERNEL )
        {
-               if( Flags & MM_PFLAG_KERNEL )   *ent &= ~PF_USER;
-               else    *ent |= PF_USER;
+               if( Flags & MM_PFLAG_KERNEL ) {
+                       *ent &= ~PF_USER;
+               }
+               else {
+                       gaPageDir[VAddr >> 22] |= PF_USER;
+                       *ent |= PF_USER;
+               }
        }
        
        // Copy-On-Write
@@ -804,6 +818,33 @@ void MM_SetFlags(tVAddr VAddr, Uint Flags, Uint Mask)
                        *ent |= PF_WRITE;
                }
        }
+       
+       //Log("MM_SetFlags: *ent = 0x%08x, gaPageDir[%i] = 0x%08x",
+       //      *ent, VAddr >> 22, gaPageDir[VAddr >> 22]);
+}
+
+/**
+ * \brief Get the flags on a page
+ */
+Uint MM_GetFlags(tVAddr VAddr)
+{
+       tTabEnt *ent;
+       Uint    ret = 0;
+       
+       // Validity Check
+       if( !(gaPageDir[VAddr >> 22] & 1) )     return 0;
+       if( !(gaPageTable[VAddr >> 12] & 1) )   return 0;
+       
+       ent = &gaPageTable[VAddr >> 12];
+       
+       // Read-Only
+       if( !(*ent & PF_WRITE) )        ret |= MM_PFLAG_RO;
+       // Kernel
+       if( !(*ent & PF_USER) ) ret |= MM_PFLAG_KERNEL;
+       // Copy-On-Write
+       if( *ent & PF_COW )     ret |= MM_PFLAG_COW;
+       
+       return ret;
 }
 
 /**
@@ -1004,17 +1045,21 @@ tVAddr MM_AllocDMA(int Pages, int MaxBits, tPAddr *PhysAddr)
 void MM_UnmapHWPages(tVAddr VAddr, Uint Number)
 {
         int    i, j;
+       
+       //Log_Debug("VirtMem", "MM_UnmapHWPages: (VAddr=0x%08x, Number=%i)", VAddr, Number);
+       
        // Sanity Check
-       if(VAddr < HW_MAP_ADDR || VAddr-Number*0x1000 > HW_MAP_MAX)     return;
+       if(VAddr < HW_MAP_ADDR || VAddr+Number*0x1000 > HW_MAP_MAX)     return;
        
        i = VAddr >> 12;
        
        LOCK( &gilTempMappings );       // Temp and HW share a directory, so they share a lock
        
+       
        for( j = 0; j < Number; j++ )
        {
-               MM_DerefPhys( gaPageTable[ (HW_MAP_ADDR >> 12) + i + j ] );
-               gaPageTable[ (HW_MAP_ADDR >> 12) + i + j ] = 0;
+               MM_DerefPhys( gaPageTable[ i + j ] & ~0xFFF );
+               gaPageTable[ i + j ] = 0;
        }
        
        RELEASE( &gilTempMappings );

UCC git Repository :: git.ucc.asn.au