Handle "." and ".." on squashfs.
* grub-core/fs/squash4.c (grub_fshelp_node): New field stsize. Make inode numbers into stack. (grub_squash_read_symlink): Use stack. (grub_squash_iterate_dir): Use stack. Create "." and ".." nodes. (make_root_node): Fill stack. (grub_squash_open): Use stack.
This commit is contained in:
parent
1d80c62a8f
commit
20dd511c8c
2 changed files with 70 additions and 15 deletions
11
ChangeLog
11
ChangeLog
|
@ -1,3 +1,14 @@
|
||||||
|
2012-05-27 Vladimir Serbinenko <phcoder@gmail.com>
|
||||||
|
|
||||||
|
Handle "." and ".." on squashfs.
|
||||||
|
|
||||||
|
* grub-core/fs/squash4.c (grub_fshelp_node): New field stsize.
|
||||||
|
Make inode numbers into stack.
|
||||||
|
(grub_squash_read_symlink): Use stack.
|
||||||
|
(grub_squash_iterate_dir): Use stack. Create "." and ".." nodes.
|
||||||
|
(make_root_node): Fill stack.
|
||||||
|
(grub_squash_open): Use stack.
|
||||||
|
|
||||||
2012-05-27 Vladimir Serbinenko <phcoder@gmail.com>
|
2012-05-27 Vladimir Serbinenko <phcoder@gmail.com>
|
||||||
|
|
||||||
* grub-core/kern/emu/hostdisk.c (open_device): Set dest->dev to 0 after
|
* grub-core/kern/emu/hostdisk.c (open_device): Set dest->dev to 0 after
|
||||||
|
|
|
@ -208,8 +208,12 @@ struct grub_fshelp_node
|
||||||
{
|
{
|
||||||
struct grub_squash_data *data;
|
struct grub_squash_data *data;
|
||||||
struct grub_squash_inode ino;
|
struct grub_squash_inode ino;
|
||||||
|
grub_size_t stsize;
|
||||||
|
struct
|
||||||
|
{
|
||||||
grub_disk_addr_t ino_chunk;
|
grub_disk_addr_t ino_chunk;
|
||||||
grub_uint16_t ino_offset;
|
grub_uint16_t ino_offset;
|
||||||
|
} stack[1];
|
||||||
};
|
};
|
||||||
|
|
||||||
static grub_err_t
|
static grub_err_t
|
||||||
|
@ -460,9 +464,9 @@ grub_squash_read_symlink (grub_fshelp_node_t node)
|
||||||
err = read_chunk (node->data, ret,
|
err = read_chunk (node->data, ret,
|
||||||
grub_le_to_cpu32 (node->ino.symlink.namelen),
|
grub_le_to_cpu32 (node->ino.symlink.namelen),
|
||||||
grub_le_to_cpu64 (node->data->sb.inodeoffset)
|
grub_le_to_cpu64 (node->data->sb.inodeoffset)
|
||||||
+ node->ino_chunk,
|
+ node->stack[node->stsize - 1].ino_chunk,
|
||||||
node->ino_offset + (node->ino.symlink.name
|
node->stack[node->stsize - 1].ino_offset
|
||||||
- (char *) &node->ino));
|
+ (node->ino.symlink.name - (char *) &node->ino));
|
||||||
if (err)
|
if (err)
|
||||||
{
|
{
|
||||||
grub_free (ret);
|
grub_free (ret);
|
||||||
|
@ -503,6 +507,40 @@ grub_squash_iterate_dir (grub_fshelp_node_t dir,
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
grub_fshelp_node_t node;
|
||||||
|
node = grub_malloc (sizeof (*node) + dir->stsize * sizeof (dir->stack[0]));
|
||||||
|
if (!node)
|
||||||
|
return 0;
|
||||||
|
grub_memcpy (node, dir,
|
||||||
|
sizeof (*node) + dir->stsize * sizeof (dir->stack[0]));
|
||||||
|
if (hook (".", GRUB_FSHELP_DIR, node))
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
if (dir->stsize != 1)
|
||||||
|
{
|
||||||
|
grub_err_t err;
|
||||||
|
|
||||||
|
node = grub_malloc (sizeof (*node) + dir->stsize * sizeof (dir->stack[0]));
|
||||||
|
if (!node)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
grub_memcpy (node, dir,
|
||||||
|
sizeof (*node) + dir->stsize * sizeof (dir->stack[0]));
|
||||||
|
|
||||||
|
node->stsize--;
|
||||||
|
err = read_chunk (dir->data, &node->ino, sizeof (node->ino),
|
||||||
|
grub_le_to_cpu64 (dir->data->sb.inodeoffset)
|
||||||
|
+ node->stack[node->stsize - 1].ino_chunk,
|
||||||
|
node->stack[node->stsize - 1].ino_offset);
|
||||||
|
if (err)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if (hook ("..", GRUB_FSHELP_DIR, node))
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
while (off < endoff)
|
while (off < endoff)
|
||||||
{
|
{
|
||||||
struct grub_squash_dirent_header dh;
|
struct grub_squash_dirent_header dh;
|
||||||
|
@ -554,14 +592,18 @@ grub_squash_iterate_dir (grub_fshelp_node_t dir,
|
||||||
if (grub_le_to_cpu16 (di.type) == SQUASH_TYPE_SYMLINK)
|
if (grub_le_to_cpu16 (di.type) == SQUASH_TYPE_SYMLINK)
|
||||||
filetype = GRUB_FSHELP_SYMLINK;
|
filetype = GRUB_FSHELP_SYMLINK;
|
||||||
|
|
||||||
node = grub_malloc (sizeof (*node));
|
node = grub_malloc (sizeof (*node)
|
||||||
|
+ (dir->stsize + 1) * sizeof (dir->stack[0]));
|
||||||
if (! node)
|
if (! node)
|
||||||
return 0;
|
return 0;
|
||||||
*node = *dir;
|
|
||||||
node->ino = ino;
|
|
||||||
node->ino_chunk = grub_le_to_cpu32 (dh.ino_chunk);
|
|
||||||
node->ino_offset = grub_le_to_cpu16 (di.ino_offset);
|
|
||||||
|
|
||||||
|
grub_memcpy (node, dir,
|
||||||
|
sizeof (*node) + dir->stsize * sizeof (dir->stack[0]));
|
||||||
|
|
||||||
|
node->ino = ino;
|
||||||
|
node->stack[node->stsize].ino_chunk = grub_le_to_cpu32 (dh.ino_chunk);
|
||||||
|
node->stack[node->stsize].ino_offset = grub_le_to_cpu16 (di.ino_offset);
|
||||||
|
node->stsize++;
|
||||||
r = hook (buf, filetype, node);
|
r = hook (buf, filetype, node);
|
||||||
|
|
||||||
grub_free (buf);
|
grub_free (buf);
|
||||||
|
@ -577,11 +619,13 @@ make_root_node (struct grub_squash_data *data, struct grub_fshelp_node *root)
|
||||||
{
|
{
|
||||||
grub_memset (root, 0, sizeof (*root));
|
grub_memset (root, 0, sizeof (*root));
|
||||||
root->data = data;
|
root->data = data;
|
||||||
|
root->stsize = 1;
|
||||||
|
root->stack[0].ino_chunk = grub_le_to_cpu32 (data->sb.root_ino_chunk);
|
||||||
|
root->stack[0].ino_offset = grub_cpu_to_le16 (data->sb.root_ino_offset);
|
||||||
return read_chunk (data, &root->ino, sizeof (root->ino),
|
return read_chunk (data, &root->ino, sizeof (root->ino),
|
||||||
grub_le_to_cpu64 (data->sb.inodeoffset)
|
grub_le_to_cpu64 (data->sb.inodeoffset)
|
||||||
+ grub_le_to_cpu32 (data->sb.root_ino_chunk),
|
+ root->stack[0].ino_chunk,
|
||||||
grub_cpu_to_le16 (data->sb.root_ino_offset));
|
root->stack[0].ino_offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -669,8 +713,8 @@ grub_squash_open (struct grub_file *file, const char *name)
|
||||||
data->ino.ino = fdiro->ino;
|
data->ino.ino = fdiro->ino;
|
||||||
data->ino.block_sizes = NULL;
|
data->ino.block_sizes = NULL;
|
||||||
data->ino.cumulated_block_sizes = NULL;
|
data->ino.cumulated_block_sizes = NULL;
|
||||||
data->ino.ino_chunk = fdiro->ino_chunk;
|
data->ino.ino_chunk = fdiro->stack[fdiro->stsize - 1].ino_chunk;
|
||||||
data->ino.ino_offset = fdiro->ino_offset;
|
data->ino.ino_offset = fdiro->stack[fdiro->stsize - 1].ino_offset;
|
||||||
|
|
||||||
switch (fdiro->ino.type)
|
switch (fdiro->ino.type)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue