Browse Source

fs/squashfs: implement exists() function

This permits to find a file and use the distro_bootcmd

Reviewed-by: Joao Marcos Costa <jmcosta944@gmail.com>
Signed-off-by: Richard Genoud <richard.genoud@posteo.net>
Richard Genoud 3 years ago
parent
commit
dd4866b437
3 changed files with 40 additions and 1 deletions
  1. 1 1
      fs/fs.c
  2. 38 0
      fs/squashfs/sqfs.c
  3. 1 0
      include/squashfs.h

+ 1 - 1
fs/fs.c

@@ -296,7 +296,7 @@ static struct fstype_info fstypes[] = {
 		.size = sqfs_size,
 		.close = sqfs_close,
 		.closedir = sqfs_closedir,
-		.exists = fs_exists_unsupported,
+		.exists = sqfs_exists,
 		.uuid = fs_uuid_unsupported,
 		.write = fs_write_unsupported,
 		.ln = fs_ln_unsupported,

+ 38 - 0
fs/squashfs/sqfs.c

@@ -1649,6 +1649,44 @@ free_strings:
 	return ret;
 }
 
+int sqfs_exists(const char *filename)
+{
+	struct fs_dir_stream *dirsp = NULL;
+	struct squashfs_dir_stream *dirs;
+	char *dir, *file;
+	struct fs_dirent *dent;
+	int ret;
+
+	sqfs_split_path(&file, &dir, filename);
+	/*
+	 * sqfs_opendir will uncompress inode and directory tables, and will
+	 * return a pointer to the directory that contains the requested file.
+	 */
+	ret = sqfs_opendir(dir, &dirsp);
+	if (ret) {
+		ret = -EINVAL;
+		goto free_strings;
+	}
+
+	dirs = (struct squashfs_dir_stream *)dirsp;
+
+	while (!sqfs_readdir(dirsp, &dent)) {
+		ret = strcmp(dent->name, file);
+		if (!ret)
+			break;
+		free(dirs->entry);
+		dirs->entry = NULL;
+	}
+
+	sqfs_closedir(dirsp);
+
+free_strings:
+	free(dir);
+	free(file);
+
+	return ret == 0;
+}
+
 void sqfs_close(void)
 {
 	free(ctxt.sblk);

+ 1 - 0
include/squashfs.h

@@ -19,6 +19,7 @@ int sqfs_probe(struct blk_desc *fs_dev_desc,
 int sqfs_read(const char *filename, void *buf, loff_t offset,
 	      loff_t len, loff_t *actread);
 int sqfs_size(const char *filename, loff_t *size);
+int sqfs_exists(const char *filename);
 void sqfs_close(void);
 void sqfs_closedir(struct fs_dir_stream *dirs);