⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 filesys.c

📁 picoos源码。The RTOS and the TCP/IP stack will be built automatically.
💻 C
📖 第 1 页 / 共 4 页
字号:
      (dbl->flags & FSDIR_F_SUBDIR))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* image not writeable or file is still open or directory */
  }

  /* remove directory entry (delete the file) */
  fs_removeDirEntry(rb, b);

  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return 0;
}


/* Rename a file in a writable RAM-Drive.
 */
sint_t  fsys_rename(const char *from, const char *to)
{
  FSROOTBLOCK_t *rb;
  FSDIRBLOCK_t *dbl;
  u32_t b;
  sint_t img;
  char *fn;

  if (fsInitialized_g == 0)
    return -1;

  if (fs_containWildcard(from) || fs_containWildcard(to))
    return -1;

  SYS_MTASK_LOCK(fsTaskLock_g);

  fn = fs_validateFileName(from);
  b = fs_findFile(&img, fn);
  if (b == 0)
  {
    /* file 'from' not found */
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }
  rb = FSROOTBLOCK(img);
  dbl = fs_getDirBlock(rb, b);

  if (ISREADONLY(img) ||
      fs_isFileOpened(fn, 0))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* image not writeable or file is still open */
  }

#if FS_SUBDIRECTORIES
  if (dbl->flags & FSDIR_F_SUBDIR)
  {
    if (fs_isDirEmpty(fn, NULL) <= 0)
    {
      SYS_MTASK_UNLOCK(fsTaskLock_g);
      return -1;  /* error or directory not empty */
    }
  }
#endif /* FS_SUBDIRECTORIES */

  fn = fs_validateFileName(to);
  if ((*fn == 0) || (sysStrlen(fn) >= rb->maxFilenameLength))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  b = fs_findFile(&img, fn);
  if (b != 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* there exist already a file with the name 'to' */
  }

  sysStrcpy(dbl->filename, fn);
  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return 0;
}


/* Replace an old file by a new file.
 */
sint_t  fsys_replace(const char *oldfile, const char *newfile)
{
  FSROOTBLOCK_t *rb;
  FSDIRBLOCK_t  *dblo, *dbln;
  u32_t  b;
  sint_t img;
  char   *fn;

  if (fsInitialized_g == 0)
    return -1;

  if (fs_containWildcard(oldfile) || fs_containWildcard(newfile))
    return -1;

  SYS_MTASK_LOCK(fsTaskLock_g);

  fn = fs_validateFileName(newfile);
  if (*fn == 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  b = fs_findFile(&img, fn);
  if (b == 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* the file does not exist */
  }
  rb = FSROOTBLOCK(img);

  if (ISREADONLY(img))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* the image is not writeable */
  }

  dbln = fs_getDirBlock(rb, b);

  fn = fs_validateFileName(oldfile);
  if (*fn == 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  b = fs_findFile(&img, fn);
  if (b == 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* the file does not exist */
  }
  rb = FSROOTBLOCK(img);

  if (ISREADONLY(img))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* the image is not writeable */
  }

  dblo = fs_getDirBlock(rb, b);

  /* rename new file to the name the old file has */
  sysStrcpy(dbln->filename, dblo->filename);

  if (!fs_isFileOpened(fn, 0))
  {
    /* delete the old file */
    fs_removeDirEntry(rb, b);
  }
  else
  {
    /* The old file is yet in use.
     * We mark the old file so it will
     * be deleted as soon it is closed.
     */
    dblo->flags |= FSDIR_F_IGNORE | FSDIR_F_DELONCLOSE;
  }
  
  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return 0;
}


/* Get some status information about a file.
 */
sint_t  fsys_stat(const char *fname, struct fsys_stat *stat)
{
  FSROOTBLOCK_t *rb;
  FSDIRBLOCK_t  *dbl;
  sint_t img;
  u32_t  b;

  if (fsInitialized_g == 0)
    return -1;

  SYS_MTASK_LOCK(fsTaskLock_g);

  b = fs_findFile(&img, fs_validateFileName(fname));

  if (b == 0)
  {
    /* file not found */
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  rb = FSROOTBLOCK(img);
  dbl = fs_getDirBlock(rb, b);
  stat->st_time = dbl->time;
  stat->st_size = dbl->filesize;
  stat->st_mode = (dbl->flags & FSDIR_F_SUBDIR) ? FSS_IFDIR :
                   (FSS_IFREG|FSS_IREAD| (ISREADONLY(img) ? 0 : FSS_IWRITE));

  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return 0;
}


/* delete all files from a writeable image
 */
sint_t fsys_format(u32_t blocksize, u32_t maxFilenameLength)
{
  sint_t img, rc = -1;

  SYS_MTASK_LOCK(fsTaskLock_g);

  /* find writeable image and format it */
  img = fs_getWriteableImage();
  if (img >= 0)
  {
    fs_closeAllFiles();
    rc = fs_formatImage(img, blocksize, maxFilenameLength);
  }
  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return rc;
}


/* returns the free drive space in bytes
 */
u32_t fsys_free(void)
{
  FSROOTBLOCK_t *rb;
  sint_t        img;
  u32_t         blocks, b;

  SYS_MTASK_LOCK(fsTaskLock_g);

  img = fs_getWriteableImage();
  if (img < 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return 0;
  }

  rb = FSROOTBLOCK(img);
  b = rb->freeBlocksList;
  blocks = 0;

  while (b != 0)
  {
    blocks++;
    b = fs_getBlock(rb, b)->nextBlock;
  }

  b = FS_DATABYTESPERBLOCK(rb) * blocks;
  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return b;
}


/* shrink an image to minimum size
 */
u32_t fsys_shrinkImage(void *image)
{
  FSROOTBLOCK_t *rb = (FSROOTBLOCK_t*) image;
  u32_t   b, lb, cb, c, s;
  sint_t  f = 0;

  cb = rb->driveSize / rb->bytesPerBlock;
  s = cb * rb->bytesPerBlock;
  c = 0;

  do
  {
    cb--;
    lb = 0;
    b = rb->freeBlocksList;
    f = 0;

    while (b != 0)
    {
      if (b == cb)
      {
        if (lb == 0)
        {
          rb->freeBlocksList = fs_getBlock(rb, b)->nextBlock;
        }
        else
        {
          fs_getBlock(rb, lb)->nextBlock = fs_getBlock(rb, b)->nextBlock;
        }
        c++;
        f = 1;
        break;
      }
      lb = b;
      b = fs_getBlock(rb, b)->nextBlock;
    }

  }
  while ((cb > 2) && (f != 0));

  s -= c * rb->bytesPerBlock;
  rb->driveSize = s;
  return s;
}


/*-------------------------------------------------------------------------*/

/* find next file in the directory */
static s32_t  fs_findnext(FSSEARCH_t *fs, struct fsys_finddata *fileinfo)
{
  FSROOTBLOCK_t *rb;
  FSDIRBLOCK_t  *dbl;
  sint_t        i, joker, sl;
  s32_t         block;

  if (fs->image < 0)
  {
    fs->image = -1;
    fs->dirblock = 0;
    rb = NULL;
  }
  else
  {
    rb = FSROOTBLOCK(fs->image);
  }

  for (i = 0; (fs->mask[i] != 0) && (fs->mask[i] != '*'); i++);
  joker = (fs->mask[i] != 0) ? i : -1;

  for (;;)
  {
    while ((fs->dirblock != 0) &&
           (fs_getDirBlock(rb, fs->dirblock)->flags & FSDIR_F_DELETED))
    {
      fs->dirblock = fs_getDirBlock(rb, fs->dirblock)->firstFileBlock;
    }
    if (fs->dirblock == 0)
    {
      for (fs->image++; (fs->image < FS_MAXIMAGES) &&
             (FSROOTBLOCK(fs->image) == NULL); fs->image++);
      if (fs->image >= FS_MAXIMAGES)
      {
        fs->image = -1;
        return -1;
      }
      rb = FSROOTBLOCK(fs->image);
      fs->dirblock = rb->firstDirBlock;
      continue;
    }

    dbl = fs_getDirBlock(rb, fs->dirblock);
    block = (s32_t) fs->dirblock;
    fs->dirblock = dbl->nextBlock;

    sl = 0;
#if FS_SUBDIRECTORIES
    i = (joker >= 0) ? joker : sysStrlen(fs->mask);
    if (i < (sint_t)sysStrlen(dbl->filename))
    {
      for (; dbl->filename[i] != 0; i++)
      {
        if (dbl->filename[i] == '/')
        {
          sl = 1;
          break;
        }
      }
    }
#else /* FS_SUBDIRECTORIES */
   if (dbl->flags & FSDIR_F_SUBDIR)
     sl = 1;
#endif /* FS_SUBDIRECTORIES */

    if ((sl == 0) &&
        !(dbl->flags & FSDIR_F_IGNORE) && ((joker == 0) ||
        ((joker < 0) && (sysStricmp(dbl->filename, fs->mask) == 0)) ||
        ((joker >= 0) && (sysStrnicmp(dbl->filename, fs->mask, joker) == 0))))
      break;
  }

  sysStrcpy(fileinfo->name, dbl->filename);

#if FS_SUBDIRECTORIES
  i = sysStrlen(fileinfo->name);
  while ((i > 0) && (fileinfo->name[i-1] != '/')) i--;
  if (i > 0) sysStrcpy(fileinfo->name, fileinfo->name + i);
#endif /* FS_SUBDIRECTORIES */

  fileinfo->size = dbl->filesize;
  fileinfo->time = dbl->time;
  fileinfo->attrib = (ISREADONLY(fs->image) ? FSA_RDONLY : 0) |
                     ((dbl->flags & FSDIR_F_SUBDIR) ? FSA_SUBDIR : 0);
  return block;
}


/* find first file. returns a handle on success or -1 on error */
sint_t  fsys_findfirst(char *filespec, struct fsys_finddata *fileinfo)
{
  sint_t  i;
  char    *mask;

  if ((filespec == NULL) || (fileinfo == NULL))
    return -1;

  SYS_MTASK_LOCK(fsTaskLock_g);

  for (i = 0; (i < FS_MAXFILES) && (fsSearchList_g[i].image >= 0); i++);
  mask = fs_validateFileName(filespec);

  if ((i >= FS_MAXFILES) || (*mask == 0))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }
  
  sysStrcpy(fsSearchList_g[i].mask, mask);

  if (fs_findnext(&fsSearchList_g[i], fileinfo) < 0)
  {
    fsSearchList_g[i].image = -1;
    i = -1;
  }

  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return i;
}


/* find next file. returns zero on success or -1 on error */
sint_t  fsys_findnext(sint_t handle, struct fsys_finddata *fileinfo)
{
  s32_t rc;

  if (((uint_t) handle >= FS_MAXFILES) || (fileinfo == NULL))
    return -1;

  SYS_MTASK_LOCK(fsTaskLock_g);

  if (fsSearchList_g[handle].image < 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  rc = fs_findnext(&fsSearchList_g[handle], fileinfo);

  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return (rc < 0) ? -1 : 0;
}


/* returns zero on success or -1 when no more files are matching */
sint_t  fsys_findclose(sint_t handle)
{
  struct fsys_finddata fileinfo;
  sint_t rc;

  if ((uint_t) handle >= FS_MAXFILES)
    return -1;

  rc = fsys_findnext(handle, &fileinfo);

  SYS_MTASK_LOCK(fsTaskLock_g);
  fsSearchList_g[handle].image = -1;
  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return rc;
}


/*-------------------------------------------------------------------------*/


#if FS_SUBDIRECTORIES

/* make a new subdirectory */
sint_t fsys_mkdir(const char *pathname)
{
  FSROOTBLOCK_t *rb;
  sint_t l, img;
  u32_t  d;

  SYS_MTASK_LOCK(fsTaskLock_g);

  l = fsys_buildPathName(fnbuffer_g, pathname, "");
  if (l < 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  if ((l == 0) ||
      ((fnbuffer_g[0] == '/') && (fnbuffer_g[1] == 0)))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }

  fnbuffer_g[l-1] = 0;

  d = fs_newFile(&img, fnbuffer_g, 0);
  if (d == 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;
  }
  rb = FSROOTBLOCK(img);

  fs_getDirBlock(rb, d)->flags |= FSDIR_F_SUBDIR;
  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return 0;
}


/* remove a subdirectory */
sint_t fsys_rmdir(const char *pathname)
{
  FSROOTBLOCK_t *rb;
  char     *dirname;
  sint_t   img;
  u32_t    d;

  SYS_MTASK_LOCK(fsTaskLock_g);

  if (fs_isDirEmpty(pathname, &dirname) <= 0)
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1;  /* error or directory not empty */
  }

  d = fs_findFile(&img, dirname);
  rb = FSROOTBLOCK(img);

  if ((d == 0) ||
      !(fs_getDirBlock(rb, d)->flags & FSDIR_F_SUBDIR) ||
      ISREADONLY(img))
  {
    SYS_MTASK_UNLOCK(fsTaskLock_g);
    return -1; /* directory not valid */
  }

  fs_removeDirEntry(rb, d);

  SYS_MTASK_UNLOCK(fsTaskLock_g);
  return 0;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -