Beispiel #1
0
static BOOL counter(RDWRHandle handle, struct DirectoryPosition* pos,
                    void** buffer)
{
    struct DirectoryEntry* entry;

    struct PipeStruct* p = *((struct PipeStruct**) buffer);
    
    entry = AllocateDirectoryEntry();
    if (!entry) return FAIL;

    if (!GetDirectory(handle, pos, entry))
    {
       FreeDirectoryEntry(entry);
       return FAIL;
    }

    if (entry->attribute == LFN_ATTRIBUTES)
    {
       if (IsLFNEntry(entry))
          p->count++;
    }
    else if ((entry->attribute & p->attribute) ||
	     (p->attribute == -1))
    {
        p->count++;
    }

    FreeDirectoryEntry(entry);
    return TRUE;
}
Beispiel #2
0
BOOL GetNthDirectoryPosition(RDWRHandle handle, CLUSTER cluster,
                             unsigned long n, struct DirectoryPosition* result)
{
    int fatlabelsize;
    struct Pipe pipe, *ppipe = &pipe;
   
    pipe.n = n;
    pipe.counter = 0;
    pipe.pos = result;
    
    if (cluster == 0)
    {
       fatlabelsize = GetFatLabelSize(handle);
       switch (fatlabelsize)
       {
	  case FAT12:
	  case FAT16:
	       {
		   BOOL retVal;
		   struct DirectoryPosition pos;
		   struct DirectoryEntry* entry;

		   retVal = GetRootDirPosition(handle, (unsigned short) n,
					       &pos);
		   if (retVal)
		   {
		      entry = AllocateDirectoryEntry();
		      if (!entry) return FALSE;

		      if (!GetDirectory(handle, &pos, entry))
		      {
			 FreeDirectoryEntry(entry);
			 return FALSE;
		      }

		      if (entry->filename[0] != LASTLABEL)
		      {
			 memcpy(result, &pos, sizeof(struct DirectoryPosition));
		      }

		      FreeDirectoryEntry(entry);
		   }

		   return retVal;
	       }
	  case FAT32:
	       cluster = GetFAT32RootCluster(handle);
	       if (cluster)
		  break;
	       else
		  return FALSE;
	  default:
	       return FALSE;
       }
    }    
   
    return TraverseSubdir(handle, cluster, positiongetter, (void**) &ppipe,
                          TRUE);
}
Beispiel #3
0
BOOL GetNthSubDirectoryPosition(RDWRHandle handle, CLUSTER cluster, 
                                unsigned long n, 
                                struct DirectoryPosition* result)        
{
   int counter = 0;
   struct DirectoryPosition pos;
   struct DirectoryEntry* entry;
   
   entry = AllocateDirectoryEntry();
   if (!entry) return FALSE;

   n++;                                       /* n is 0 based */
   while (n)
   {
       pos.sector = 0;
       pos.offset = 0;
       
       if (!GetNthDirectoryPosition(handle, cluster, counter++, &pos))
       {
          FreeDirectoryEntry(entry);
          return FALSE;
       }

       if ((pos.sector == 0) && (pos.offset == 0)) /* Not found*/
       {
	  FreeDirectoryEntry(entry);
	  return TRUE;
       }
          
       if (!GetDirectory(handle, &pos, entry))
       {
          FreeDirectoryEntry(entry);
	  return TRUE;
       }

       if (!IsLFNEntry((entry))        &&
	   (entry->attribute & FA_DIREC) &&
	   (!IsDeletedLabel(*entry))     &&
	   (!IsCurrentDir(*entry))       &&
	   (!IsPreviousDir(*entry)))  
       {
          n--;
       }
   }
 
   memcpy(result, &pos, sizeof(struct DirectoryPosition));
   FreeDirectoryEntry(entry);
   return TRUE;
}
Beispiel #4
0
static BOOL VolumeGetter(RDWRHandle handle,
                         struct DirectoryPosition* pos,
                         void** structure)
{
   struct Pipe *pipe = *((struct Pipe**) structure);
   struct DirectoryEntry* entry;

   assert (pos->sector && (pos->offset < 16));
   
   entry = AllocateDirectoryEntry();
   if (!entry) RETURN_FTEERR(FAIL);

   if (!GetDirectory(handle, pos, entry))
   {
      FreeDirectoryEntry(entry);
      RETURN_FTEERR(FAIL);
   }

   if (IsLFNEntry(entry))
   {
      FreeDirectoryEntry(entry);
      return TRUE;
   }
   
   if (IsDeletedLabel(*entry))
   {
      FreeDirectoryEntry(entry);
      return TRUE;
   }
   
   if (entry->attribute & FA_LABEL)
   {
      pipe->found = TRUE;
      memcpy(pipe->pos, pos, sizeof(struct DirectoryPosition));

      FreeDirectoryEntry(entry);
       RETURN_FTEERR(FALSE);
   }

   FreeDirectoryEntry(entry);
   return TRUE;
}
Beispiel #5
0
static long CountEntriesInRootDirectory(RDWRHandle handle, char attribute)
{
    long count = 0, i;
    struct DirectoryEntry* entry;

    long rootcount = GetNumberOfRootEntries(handle);
    if (!rootcount) return FAIL;

    entry = AllocateDirectoryEntry();
    if (!entry) return FAIL;

    for (i = 0; i < rootcount; i++)
    {
	if (!ReadDirEntry(handle, i, entry))
	{
	   FreeDirectoryEntry(entry);
	   return FAIL;
        }
	if (IsLastLabel(*entry))
	{
	   FreeDirectoryEntry(entry);
	   return count;
	}
        
        if (entry->attribute == LFN_ATTRIBUTES)
        {
           if (IsLFNEntry(entry))
              count++;
        }
        else if ((entry->attribute & attribute) ||
	         (attribute == -1))
        {
	   count++;
        }
    }
    FreeDirectoryEntry(entry);
    return rootcount;
}
Beispiel #6
0
BOOL WalkDirectoryTree(RDWRHandle handle,
		      int (*func) (RDWRHandle handle,
				   struct DirectoryPosition* position,
				   void** structure),
		      void** structure)
{
    int top = 0;
    struct StackElement* stack;
    CLUSTER cluster = 0, temp;
    unsigned long current = 0;
    struct DirectoryPosition pos;
    struct DirectoryEntry* entry;
    struct StackElement element;
        
    struct PipeStruct pipe, *ppipe = &pipe;

    pipe.func      = func;
    pipe.structure = structure;
    pipe.stop      = FALSE;

    if (!TraverseRootDir(handle, ActionWalker, (void**)&ppipe, TRUE))
       return FALSE;
    if (pipe.stop)
       return TRUE;

    stack = (struct StackElement*)FTEAlloc(DIR_STACK_DEPTH * sizeof(struct StackElement));
    if (!stack)
       return FALSE;

    for (;;)
    {
         /* If there still are sub directories in this directory, 
            push the cluster of that directory. */
         pos.sector = 0;
         pos.offset = 0;
         if (!GetNthSubDirectoryPosition(handle, cluster, current, &pos))
	 {
            FTEFree(stack);
            return FALSE;
         }

	 if ((pos.sector != 0) || (pos.offset != 0))
	 {
	    entry = AllocateDirectoryEntry();
	    if (!entry)
	    {
	       FTEFree(stack);
	       return FALSE;
	    }

	    if (top < DIR_STACK_DEPTH)
	    {
	       element.cluster = cluster;
	       element.index   = current;

	       PushDirectoryEntry(stack, &top, &element);
	    }
	    else
	    {
	       FreeDirectoryEntry(entry);   /* Directory level to deep!? */
	       FTEFree(stack);
	       return FALSE;
	    }

	    if (!GetDirectory(handle, &pos, entry))
	    {
	       FreeDirectoryEntry(entry);
	       FTEFree(stack);
	       return FALSE;
	    }

	    /* Descend in the directory tree and call the function
               for every directory entry in that directory. */
            temp = GetFirstCluster(entry);
            
            /* Don't descend in any directory that is invalid. */
            if (temp && FAT_NORMAL(temp) && IsLabelValid(handle, temp))
            {
	       current = 0;
               cluster = temp;

	       if (!TraverseSubdir(handle, cluster, ActionWalker, (void**) &ppipe, TRUE))
	       {
	          FreeDirectoryEntry(entry);
	          FTEFree(stack);
                  return FALSE;
	       }

	       if (pipe.stop)
	       {
	          FreeDirectoryEntry(entry);
                  FTEFree(stack);
	          return TRUE;
	       }
            }
            else /* cluster not valid, leave this directory */
            {   
	       if (top-1 > 0) /* Be carefull when there are no sub directories
		                 in the volume. */
	       {
	          PopDirectoryEntry(stack, &top, &element);
                  PopDirectoryEntry(stack, &top, &element);

	          current = element.index+1; /* Then find the next sub directory. */
	          cluster = element.cluster;
	       }
	       else
	       {
                  FreeDirectoryEntry(entry);     
	          break;
	       }
            }
            
	    FreeDirectoryEntry(entry);
	 }
	 /* If there are no more sub directories in the current directory,
	    pop the current directory from the stack.                 */
	 else
	 {
	    if (top) /* Be carefull when there are no sub directories
			in the volume. */
	    {
	       PopDirectoryEntry(stack, &top, &element);

	       current = element.index+1; /* Then find the next sub directory. */
	       cluster = element.cluster;
	    }
	    else
	    {
	       break;
	    }
         }
    }

    FTEFree(stack);        
    return TRUE;
}