*** empty log message ***
authorcharles <charles>
Wed, 2 Oct 2002 02:11:25 +0000 (02:11 +0000)
committercharles <charles>
Wed, 2 Oct 2002 02:11:25 +0000 (02:11 +0000)
Makefile
snMakefile
utils/mkyaffs
utils/mkyaffs.c
yaffs_fs.c
yaffs_guts.c
yaffsdev.c
yaffsdev.proj

index fa4c171e209e457dc7fad46983ee3c55dadd86fd..0b6083c789de309c1b525c5ad555cab1ef3d2cc3 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -11,6 +11,9 @@
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License version 2 as
 # published by the Free Software Foundation.
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License version 2 as
 # published by the Free Software Foundation.
+#
+# $Id: Makefile,v 1.6 2002-10-02 02:11:25 charles Exp $
+#
 
 ## Change or override  KERNELDIR to your kernel
 ## comment out USE_xxxx if you don't want these features.
 
 ## Change or override  KERNELDIR to your kernel
 ## comment out USE_xxxx if you don't want these features.
index 0b9fbb904a96227a1607695bccdbb5fa0ee689b7..c2007a26da1d2a847dfdb205176547cf9d88453d 100644 (file)
@@ -1,6 +1,6 @@
 #########################################################
 # Makefile auto generated by Cygnus Source Navigator.
 #########################################################
 # Makefile auto generated by Cygnus Source Navigator.
-# Target: yaffsdev_disk Date: Sep 27 2002 Time: 09:05:11 AM
+# Target: yaffsdev_disk Date: Oct 01 2002 Time: 07:41:55 AM
 #
 
 
 #
 
 
index 94a7df35310c59073d53dd1f78cbd23f585bb5df..644ea3b8700b2469f3a9e8c111e9f5aa981e646f 100755 (executable)
Binary files a/utils/mkyaffs and b/utils/mkyaffs differ
index 91a3c9d04ac5b7a3077fc7f442b5ba1538e10329..53055b33febfac71c788a15e768ef37fd2f7bc4f 100644 (file)
@@ -34,7 +34,7 @@
 #include <linux/config.h>
 #include <linux/mtd/mtd.h>
 
 #include <linux/config.h>
 #include <linux/mtd/mtd.h>
 
-cost char *mkyaffs_c_version = "$Id: mkyaffs.c,v 1.3 2002-09-27 20:50:50 charles Exp $";
+const char *mkyaffs_c_version = "$Id: mkyaffs.c,v 1.4 2002-10-02 02:11:25 charles Exp $";
 
 // countBits is a quick way of counting the number of bits in a byte.
 // ie. countBits[n] holds the number of 1 bits in a byte with the value n.
 
 // countBits is a quick way of counting the number of bits in a byte.
 // ie. countBits[n] holds the number of 1 bits in a byte with the value n.
index b69330557865cd3918baa1252980bc9a914718dd..9be8428cad8cff648e75494dea064f36ff75a0e1 100644 (file)
@@ -27,7 +27,8 @@
  */
 
 
  */
 
 
-const char *yaffs_fs_c_version = "$Id: yaffs_fs.c,v 1.16 2002-09-27 20:50:50 charles Exp $";
+const char *yaffs_fs_c_version = "$Id: yaffs_fs.c,v 1.17 2002-10-02 02:11:25 charles Exp $";
+extern const char *yaffs_guts_c_version;
 
 #include <linux/config.h>
 #include <linux/kernel.h>
 
 #include <linux/config.h>
 #include <linux/kernel.h>
@@ -932,6 +933,9 @@ static int yaffs_rename(struct inode * old_dir, struct dentry *old_dentry, struc
 
        yaffs_GrossLock(dev);
        
 
        yaffs_GrossLock(dev);
        
+       // Unlink the target if it exists
+       yaffs_Unlink(yaffs_InodeToObject(new_dir),new_dentry->d_name.name);
+
        
        retVal =  yaffs_RenameObject(yaffs_InodeToObject(old_dir),old_dentry->d_name.name,
                                         yaffs_InodeToObject(new_dir),new_dentry->d_name.name);
        
        retVal =  yaffs_RenameObject(yaffs_InodeToObject(old_dir),old_dentry->d_name.name,
                                         yaffs_InodeToObject(new_dir),new_dentry->d_name.name);
@@ -1306,14 +1310,14 @@ static int  yaffs_proc_read(
        )
 {
 
        )
 {
 
-       char my_buffer[2000];
+       char my_buffer[3000];
        char *buf;
        buf = my_buffer;
 
        if (offset > 0) return 0;
 
        /* Fill the buffer and get its length */
        char *buf;
        buf = my_buffer;
 
        if (offset > 0) return 0;
 
        /* Fill the buffer and get its length */
-       buf +=sprintf(buf,"YAFFS built:"__DATE__ " "__TIME__"\n");
+       buf +=sprintf(buf,"YAFFS built:"__DATE__ " "__TIME__"\n%s\n%s\n", yaffs_fs_c_version,yaffs_guts_c_version);
        
        if(yaffs_dev) buf = yaffs_dump_dev(buf,yaffs_dev,"yaffs");
        if(yaffsram_dev) buf = yaffs_dump_dev(buf,yaffsram_dev,"yaffsram");
        
        if(yaffs_dev) buf = yaffs_dump_dev(buf,yaffs_dev,"yaffs");
        if(yaffsram_dev) buf = yaffs_dump_dev(buf,yaffsram_dev,"yaffsram");
index bfe10b74deb2aa6140d47fe876831f1a2b695ad2..975d7c0ad3dd28f55712290fb5ef19f380cb763c 100644 (file)
@@ -14,7 +14,7 @@
  */
  //yaffs_guts.c
 
  */
  //yaffs_guts.c
 
-const char *yaffs_guts_c_version="$Id: yaffs_guts.c,v 1.10 2002-09-27 20:50:50 charles Exp $";
+const char *yaffs_guts_c_version="$Id: yaffs_guts.c,v 1.11 2002-10-02 02:11:25 charles Exp $";
 
 #include "yportenv.h"
 
 
 #include "yportenv.h"
 
@@ -109,12 +109,8 @@ static int yaffs_CheckFileSanity(yaffs_Object *in);
 #define yaffs_CheckFileSanity(in)
 #endif
 
 #define yaffs_CheckFileSanity(in)
 #endif
 
-#ifdef CONFIG_YAFFS_SHORT_OP_CACHE
-static void yaffs_InvalidateChunkCache(yaffs_Object *in);
-#define        yaffs_INVALIDATECHUNKCACHE(in) yaffs_InvalidateChunkCache(in)
-#else
-#define yaffs_INVALIDATECHUNKCACHE(in)
-#endif
+static void yaffs_InvalidateWholeChunkCache(yaffs_Object *in);
+static void yaffs_InvalidateChunkCache(yaffs_Device *dev, int objectId, int chunkId);
 
 
 static  __inline__ yaffs_BlockInfo* yaffs_GetBlockInfo(yaffs_Device *dev, int blk)
 
 
 static  __inline__ yaffs_BlockInfo* yaffs_GetBlockInfo(yaffs_Device *dev, int blk)
@@ -1542,7 +1538,7 @@ yaffs_Object *yaffs_Link(yaffs_Object *parent, const char *name, yaffs_Object *e
 }
 
 
 }
 
 
-static int yaffs_ChangeObjectName(yaffs_Object *obj, yaffs_Object *newDir, const char *newName)
+static int yaffs_ChangeObjectName(yaffs_Object *obj, yaffs_Object *newDir, const char *newName,int force)
 {
        int unlinkOp;
 
 {
        int unlinkOp;
 
@@ -1556,9 +1552,10 @@ static int yaffs_ChangeObjectName(yaffs_Object *obj, yaffs_Object *newDir, const
        // If the object is a file going into the unlinked directory, then it is OK to just stuff it in since
        // duplicate names are allowed.
        // Otherwise only proceed if the new name does not exist and if we're putting it into a directory.
        // If the object is a file going into the unlinked directory, then it is OK to just stuff it in since
        // duplicate names are allowed.
        // Otherwise only proceed if the new name does not exist and if we're putting it into a directory.
-       if( unlinkOp||
-           (!yaffs_FindObjectByName(newDir,newName) &&
-            newDir->variantType == YAFFS_OBJECT_TYPE_DIRECTORY))
+       if( (unlinkOp|| 
+                force || 
+                !yaffs_FindObjectByName(newDir,newName))  &&
+            newDir->variantType == YAFFS_OBJECT_TYPE_DIRECTORY)
        {
                obj->sum = yaffs_CalcNameSum(newName);
                obj->dirty = 1;
        {
                obj->sum = yaffs_CalcNameSum(newName);
                obj->dirty = 1;
@@ -1580,11 +1577,22 @@ static int yaffs_ChangeObjectName(yaffs_Object *obj, yaffs_Object *newDir, const
 int yaffs_RenameObject(yaffs_Object *oldDir, const char *oldName, yaffs_Object *newDir, const char *newName)
 {
        yaffs_Object *obj;
 int yaffs_RenameObject(yaffs_Object *oldDir, const char *oldName, yaffs_Object *newDir, const char *newName)
 {
        yaffs_Object *obj;
+       int force = 0;
+       
+#if WIN32
+       // Special case for WinCE.
+       // While look-up is case insensitive, the name isn't.
+       // THerefore we might want to change x.txt to X.txt
+       if(oldDir == newDir && stricmp(oldName,newName) == 0)
+       {
+               force = 1;
+       }       
+#endif
        
        obj = yaffs_FindObjectByName(oldDir,oldName);
        if(obj && obj->renameAllowed)
        {
        
        obj = yaffs_FindObjectByName(oldDir,oldName);
        if(obj && obj->renameAllowed)
        {
-               return yaffs_ChangeObjectName(obj,newDir,newName);
+               return yaffs_ChangeObjectName(obj,newDir,newName,force);
        }
        return YAFFS_FAIL;
 }
        }
        return YAFFS_FAIL;
 }
@@ -1962,9 +1970,19 @@ static void yaffs_DoUnlinkedFileDeletion(yaffs_Device *dev)
        if(dev->unlinkedDeletion)
        {
                yaffs_Object *obj = dev->unlinkedDeletion;
        if(dev->unlinkedDeletion)
        {
                yaffs_Object *obj = dev->unlinkedDeletion;
-               int limit;
                int delresult;
                int delresult;
-               limit = 50; // Max number of chunks to delete in a file. NB this can be exceeded, but not by much.
+               int limit; // Number of chunks to delete in a file.
+                                  // NB this can be exceeded, but not by much.
+                                  
+               if(dev->nErasedBlocks <= (YAFFS_RESERVED_BLOCKS + YAFFS_GARBAGE_COLLECT_LOW_WATER))
+               {
+                       limit = 50; // Doing GC soon, so dig deeper     
+               }
+               else
+               {
+                       limit = 5;
+               }
+               
                delresult = yaffs_DeleteWorker(obj, obj->variant.fileVariant.top, obj->variant.fileVariant.topLevel, 0,&limit);
                
                if(obj->nDataChunks == 0)
                delresult = yaffs_DeleteWorker(obj, obj->variant.fileVariant.top, obj->variant.fileVariant.topLevel, 0,&limit);
                
                if(obj->nDataChunks == 0)
@@ -2563,7 +2581,7 @@ int yaffs_UpdateObjectHeader(yaffs_Object *in,const char *name, int force)
     yaffs_ObjectHeader *oh = (yaffs_ObjectHeader *)bufferNew;
     yaffs_ObjectHeader *ohOld = (yaffs_ObjectHeader *)bufferOld;
 
     yaffs_ObjectHeader *oh = (yaffs_ObjectHeader *)bufferNew;
     yaffs_ObjectHeader *ohOld = (yaffs_ObjectHeader *)bufferOld;
 
-       yaffs_INVALIDATECHUNKCACHE(in);
+    yaffs_InvalidateWholeChunkCache(in);
     
     if(!in->fake || force)
     {
     
     if(!in->fake || force)
     {
@@ -2705,23 +2723,6 @@ int yaffs_UpdateObjectHeader(yaffs_Object *in,const char *name, int force)
 
 #ifdef CONFIG_YAFFS_SHORT_OP_CACHE
 
 
 #ifdef CONFIG_YAFFS_SHORT_OP_CACHE
 
-// Invalidate all the cache pages associated with this object
-// Do this whenever ther file is modified... dumb as a rock remember!
-static void yaffs_InvalidateChunkCache(yaffs_Object *in)
-{
-       int i;
-       yaffs_Device *dev = in->myDev;
-       int id = in->objectId;
-       
-       for(i = 0; i < YAFFS_N_CACHE_CHUNKS; i++)
-       {
-               if(dev->srCache[i].objectId == id)
-               {
-                       dev->srCache[i].objectId = 0;
-               }
-       }
-}
-
 
 // Grab us a chunk for use.
 // First look for an empty one. 
 
 // Grab us a chunk for use.
 // First look for an empty one. 
@@ -2802,6 +2803,61 @@ static void yaffs_UseChunkCache(yaffs_Device *dev, yaffs_ChunkCache *cache)
 
 }
 
 
 }
 
+// Invalidate a single cache page
+static void yaffs_InvalidateChunkCache(yaffs_Device *dev, int objectId, int chunkId)
+{
+       yaffs_ChunkCache *cache = yaffs_FindChunkCache(dev,objectId,chunkId);
+
+       if(cache)
+       {
+               cache->objectId = 0;
+       }
+}
+
+
+// Invalidate all the cache pages associated with this object
+// Do this whenever ther file is modified... dumb as a rock remember!
+static void yaffs_InvalidateWholeChunkCache(yaffs_Object *in)
+{
+       int i;
+       yaffs_Device *dev = in->myDev;
+       int id = in->objectId;
+       
+       for(i = 0; i < YAFFS_N_CACHE_CHUNKS; i++)
+       {
+               if(dev->srCache[i].objectId == id)
+               {
+                       dev->srCache[i].objectId = 0;
+               }
+       }
+}
+
+
+#else
+
+static yaffs_ChunkCache *yaffs_GrabChunkCache(yaffs_Device *dev)
+{
+       return NULL;    
+}
+
+
+static yaffs_ChunkCache *yaffs_FindChunkCache(yaffs_Device *dev, int objectId, int chunkId)
+{
+       return NULL;
+}
+
+static void yaffs_UseChunkCache(yaffs_Device *dev, yaffs_ChunkCache *cache)
+{
+}
+
+static void yaffs_InvalidateChunkCache(yaffs_Device *dev, int objectId, int chunkId)
+{
+}
+
+static void yaffs_InvalidateWholeChunkCache(yaffs_Object *in)
+{
+}
+
 
 
 #endif
 
 
 #endif
@@ -2828,6 +2884,7 @@ int yaffs_ReadDataFromFile(yaffs_Object *in, __u8 * buffer, __u32 offset, int nB
 
        __u8 localBuffer[YAFFS_BYTES_PER_CHUNK];
        
 
        __u8 localBuffer[YAFFS_BYTES_PER_CHUNK];
        
+       
        int chunk;
        int start;
        int nToCopy;
        int chunk;
        int start;
        int nToCopy;
@@ -2909,8 +2966,10 @@ int yaffs_WriteDataToFile(yaffs_Object *in,const __u8 * buffer, __u32 offset, in
        int nToWriteBack;
        int endOfWrite = offset+nBytes;
        int chunkWritten = 0;
        int nToWriteBack;
        int endOfWrite = offset+nBytes;
        int chunkWritten = 0;
+       int nBytesRead;
+       
+       yaffs_InvalidateWholeChunkCache(in);
        
        
-       yaffs_INVALIDATECHUNKCACHE(in);
        
        while(n > 0 && chunkWritten >= 0)
        {
        
        while(n > 0 && chunkWritten >= 0)
        {
@@ -2920,10 +2979,23 @@ int yaffs_WriteDataToFile(yaffs_Object *in,const __u8 * buffer, __u32 offset, in
 
                // OK now check for the curveball where the start and end are in
                // the same chunk.
 
                // OK now check for the curveball where the start and end are in
                // the same chunk.
+               
                if(     (start + n) < YAFFS_BYTES_PER_CHUNK)
                {
                        nToCopy = n;
                if(     (start + n) < YAFFS_BYTES_PER_CHUNK)
                {
                        nToCopy = n;
-                       nToWriteBack = (start + n);
+                       
+                       // Now folks, to calculate how many bytes to write back....
+                       // If we're overwriting and not writing to then end of file then
+                       // we need to write back as much as was there before.
+                       
+                       nBytesRead = in->variant.fileVariant.fileSize - ((chunk -1) * YAFFS_BYTES_PER_CHUNK);
+                       
+                       if(nBytesRead > YAFFS_BYTES_PER_CHUNK)
+                       {
+                               nBytesRead = YAFFS_BYTES_PER_CHUNK;
+                       }
+                       nToWriteBack = (nBytesRead > (start + n)) ? nBytesRead : (start +n);
+                       
                }
                else
                {
                }
                else
                {
@@ -2942,7 +3014,7 @@ int yaffs_WriteDataToFile(yaffs_Object *in,const __u8 * buffer, __u32 offset, in
                        
                        chunkWritten = yaffs_WriteChunkDataToObject(in,chunk,localBuffer,nToWriteBack,0);
                        
                        
                        chunkWritten = yaffs_WriteChunkDataToObject(in,chunk,localBuffer,nToWriteBack,0);
                        
-                       //T(("Write with readback to chunk %d %d\n",chunk,chunkWritten));
+                       //T(("Write with readback to chunk %d %d  start %d  copied %d wrote back %d\n",chunk,chunkWritten,start, nToCopy, nToWriteBack));
                        
                }
                else
                        
                }
                else
@@ -2957,6 +3029,8 @@ int yaffs_WriteDataToFile(yaffs_Object *in,const __u8 * buffer, __u32 offset, in
                        // A full chunk. Write directly from the supplied buffer.
                        chunkWritten = yaffs_WriteChunkDataToObject(in,chunk,buffer,YAFFS_BYTES_PER_CHUNK,0);
 #endif
                        // A full chunk. Write directly from the supplied buffer.
                        chunkWritten = yaffs_WriteChunkDataToObject(in,chunk,buffer,YAFFS_BYTES_PER_CHUNK,0);
 #endif
+                       // Since we've overwritten the cached data, we better invalidate it.
+                       yaffs_InvalidateChunkCache(in->myDev,in->objectId,chunk);
                        //T(("Write to chunk %d %d\n",chunk,chunkWritten));
                }
                
                        //T(("Write to chunk %d %d\n",chunk,chunkWritten));
                }
                
@@ -2995,7 +3069,7 @@ int yaffs_ResizeFile(yaffs_Object *in, int newSize)
        
        __u8 localBuffer[YAFFS_BYTES_PER_CHUNK];
 
        
        __u8 localBuffer[YAFFS_BYTES_PER_CHUNK];
 
-       yaffs_INVALIDATECHUNKCACHE(in);
+       yaffs_InvalidateWholeChunkCache(in);
        
        if(in->variantType != YAFFS_OBJECT_TYPE_FILE)
        {
        
        if(in->variantType != YAFFS_OBJECT_TYPE_FILE)
        {
@@ -3099,7 +3173,7 @@ int yaffs_FlushFile(yaffs_Object *in)
 
 static int yaffs_DoGenericObjectDeletion(yaffs_Object *in)
 {
 
 static int yaffs_DoGenericObjectDeletion(yaffs_Object *in)
 {
-       yaffs_INVALIDATECHUNKCACHE(in);
+       yaffs_InvalidateWholeChunkCache(in);
        yaffs_RemoveObjectFromDirectory(in);
        yaffs_DeleteChunk(in->myDev,in->chunkId);
 #if __KERNEL__
        yaffs_RemoveObjectFromDirectory(in);
        yaffs_DeleteChunk(in->myDev,in->chunkId);
 #if __KERNEL__
@@ -3135,7 +3209,7 @@ static int yaffs_UnlinkFile(yaffs_Object *in)
 #else
        int retVal;
        int immediateDeletion=0;
 #else
        int retVal;
        int immediateDeletion=0;
-       retVal = yaffs_ChangeObjectName(in, in->myDev->unlinkedDir,NULL);
+       retVal = yaffs_ChangeObjectName(in, in->myDev->unlinkedDir,NULL,0);
        if(retVal == YAFFS_OK)
        {
                //in->unlinked = 1;
        if(retVal == YAFFS_OK)
        {
                //in->unlinked = 1;
@@ -3331,7 +3405,7 @@ static int yaffs_UnlinkWorker(yaffs_Object *obj)
                
                yaffs_GetObjectName(hl,name,YAFFS_MAX_NAME_LENGTH+1);
                
                
                yaffs_GetObjectName(hl,name,YAFFS_MAX_NAME_LENGTH+1);
                
-               retVal = yaffs_ChangeObjectName(obj, hl->parent, name);
+               retVal = yaffs_ChangeObjectName(obj, hl->parent, name,0);
                
                if(retVal == YAFFS_OK)
                {
                
                if(retVal == YAFFS_OK)
                {
index 3fb6a62e39ee13af9795f1a2b961e71dde0c84b8..ba1353f823a53d796614eb9a62beb52fb0e019e5 100644 (file)
@@ -313,14 +313,17 @@ void TestTime(yaffs_Device *dev)
        
        x = yaffs_RenameObject(yaffs_Root(dev),"Name1",NULL,"Rename");
        
        
        x = yaffs_RenameObject(yaffs_Root(dev),"Name1",NULL,"Rename");
        
-       for(i = 0; i < 100000; i+=20)
+       for(i = 0; i < 100000; i+=64)
        { 
        
                b++;
                if(b & 1)
        { 
        
                b++;
                if(b & 1)
-                       written = yaffs_WriteDataToFile(f,testStr,i,strlen(testStr));
+                       written = yaffs_WriteDataToFile(f,testStr,i,64);
                else
                else
-                       written = yaffs_WriteDataToFile(f,testStr2,i,strlen(testStr2));
+                       written = yaffs_WriteDataToFile(f,testStr2,i,64);
+               
+               written = yaffs_WriteDataToFile(f,testStr2,1,20);               
+               
        }
        // some short reads
        for(i = 1000; i < 50000; i+=2)
        }
        // some short reads
        for(i = 1000; i < 50000; i+=2)
@@ -587,7 +590,7 @@ int main(int argc,char *argv[])
        int nBlocks;
        
 #if YAFFS_FILEEM       
        int nBlocks;
        
 #if YAFFS_FILEEM       
-       nBlocks =(32 * 1024 * 1024) / (YAFFS_CHUNKS_PER_BLOCK * YAFFS_BYTES_PER_CHUNK) ;
+       nBlocks =(4 * 1024 * 1024) / (YAFFS_CHUNKS_PER_BLOCK * YAFFS_BYTES_PER_CHUNK) ;
        device.writeChunkToNAND = yaffs_FEWriteChunkToNAND;
        device.readChunkFromNAND = yaffs_FEReadChunkFromNAND;
        device.eraseBlockInNAND = yaffs_FEEraseBlockInNAND;
        device.writeChunkToNAND = yaffs_FEWriteChunkToNAND;
        device.readChunkFromNAND = yaffs_FEReadChunkFromNAND;
        device.eraseBlockInNAND = yaffs_FEEraseBlockInNAND;
@@ -616,7 +619,7 @@ int main(int argc,char *argv[])
        
        // yaffs_GutsTest();
        
        
        // yaffs_GutsTest();
        
-       TestTimeBigDeletes(&device);
+       TestTime(&device);
        
        printf("Cache hits %d\n",device.cacheHits);
        printf("Retired blocks %d\n",device.nRetiredBlocks);
        
        printf("Cache hits %d\n",device.cacheHits);
        printf("Retired blocks %d\n",device.nRetiredBlocks);
index 5a97bb6ba7ac7076510d2fb153fd637378112c9d..16a6a7db829833754c59c355689ca95ebcda78fd 100644 (file)
Binary files a/yaffsdev.proj and b/yaffsdev.proj differ