Merge branch 'master' of git://git.ucc.asn.au/tpg/acess2
[tpg/acess2.git] / Kernel / vfs / mmap.c
index 7b4d103..9fe9282 100644 (file)
@@ -1,6 +1,9 @@
 /*
- * Acess2 VFS
- * - Open, Close and ChDir
+ * Acess2 Kernel VFS
+ * - By John Hodge (thePowersGang)
+ *
+ * mmap.c
+ * - VFS_MMap support
  */
 #define DEBUG  0
 #include <acess.h>
@@ -29,6 +32,9 @@ void *VFS_MMap(void *DestHint, size_t Length, int Protection, int Flags, int FD,
 
        ENTER("pDestHint iLength xProtection xFlags xFD XOffset", DestHint, Length, Protection, Flags, FD, Offset);
 
+       if( Flags & MMAP_MAP_ANONYMOUS )
+               Offset = (tVAddr)DestHint & 0xFFF;
+       
        npages = ((Offset & (PAGE_SIZE-1)) + Length + (PAGE_SIZE - 1)) / PAGE_SIZE;
        pagenum = Offset / PAGE_SIZE;
 
@@ -41,14 +47,19 @@ void *VFS_MMap(void *DestHint, size_t Length, int Protection, int Flags, int FD,
        if( Flags & MMAP_MAP_ANONYMOUS )
        {
                size_t  ofs = 0;
+               LOG("%i pages anonymous to %p", npages, mapping_dest);
                for( ; npages --; mapping_dest += PAGE_SIZE, ofs += PAGE_SIZE )
                {
                        if( MM_GetPhysAddr(mapping_dest) ) {
                                // TODO: Set flags to COW if needed (well, if shared)
                                MM_SetFlags(mapping_dest, MM_PFLAG_COW, MM_PFLAG_COW);
+                               LOG("clear from %p, %i bytes", (void*)(mapping_base + ofs),
+                                       PAGE_SIZE - (mapping_base & (PAGE_SIZE-1))
+                                       );
                                memset( (void*)(mapping_base + ofs), 0, PAGE_SIZE - (mapping_base & (PAGE_SIZE-1)));
                        }
                        else {
+                               LOG("New empty page");
                                // TODO: Map a COW zero page instead
                                if( !MM_Allocate(mapping_dest) ) {
                                        // TODO: Error
@@ -103,8 +114,13 @@ void *VFS_MMap(void *DestHint, size_t Length, int Protection, int Flags, int FD,
                {
                        if( pb->PhysAddrs[pagenum - pb->BaseOffset] == 0 )
                        {
-                               if( h->Node->MMap )
-                                       h->Node->MMap(h->Node, pagenum*PAGE_SIZE, PAGE_SIZE, (void*)mapping_dest);
+                               tVFS_NodeType   *nt = h->Node->Type;
+                               if( !nt ) 
+                               {
+                                       // TODO: error
+                               }
+                               else if( nt->MMap )
+                                       nt->MMap(h->Node, pagenum*PAGE_SIZE, PAGE_SIZE, (void*)mapping_dest);
                                else
                                {
                                         int    read_len;
@@ -116,7 +132,7 @@ void *VFS_MMap(void *DestHint, size_t Length, int Protection, int Flags, int FD,
                                                return NULL;
                                        }
                                        // TODO: Clip read length
-                                       read_len = h->Node->Read(h->Node, pagenum*PAGE_SIZE, PAGE_SIZE, (void*)mapping_dest);
+                                       read_len = nt->Read(h->Node, pagenum*PAGE_SIZE, PAGE_SIZE, (void*)mapping_dest);
 //                                     if( read_len != PAGE_SIZE ) {
 //                                             memset( (void*)(mapping_dest+read_len), 0, PAGE_SIZE-read_len );
 //                                     }
@@ -130,6 +146,7 @@ void *VFS_MMap(void *DestHint, size_t Length, int Protection, int Flags, int FD,
                        else
                        {
                                MM_Map( mapping_dest, pb->PhysAddrs[pagenum - pb->BaseOffset] );
+                               MM_RefPhys( pb->PhysAddrs[pagenum - pb->BaseOffset] );
                                LOG("Cached map %X to %p (%P)", pagenum*PAGE_SIZE, mapping_dest,
                                        pb->PhysAddrs[pagenum - pb->BaseOffset]);
                        }
@@ -142,6 +159,13 @@ void *VFS_MMap(void *DestHint, size_t Length, int Protection, int Flags, int FD,
                        else {
                                MM_SetFlags(mapping_dest, 0, MM_PFLAG_RO);
                        }
+                       
+                       if( Protection & MMAP_PROT_EXEC ) {
+                               MM_SetFlags(mapping_dest, MM_PFLAG_EXEC, MM_PFLAG_EXEC);
+                       }
+                       else {
+                               MM_SetFlags(mapping_dest, 0, MM_PFLAG_EXEC);
+                       }
                }
                else
                {

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