aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPhillip Lougher <phillip@squashfs.org.uk>2014-03-02 03:33:56 +0000
committerPhillip Lougher <phillip@squashfs.org.uk>2014-03-02 03:37:18 +0000
commit5172991022b8985dc81a95700e5260a49223128a (patch)
tree50935b6c473fde926e1a68f302419c9a1b876736
parentd97595caecd17c7922cf137bb5f015df16340e7a (diff)
downloadsquashfs-tools-5172991022b8985dc81a95700e5260a49223128a.tar.gz
mksquashfs: write_file_blocks_dup(), bring into line with write_file_frag_dup()
Write_file_frag() does pre duplicate checking, and calls write_file_frag_dup(). Make the behaviour of write_file_blocks() the same. Signed-off-by: Phillip Lougher <phillip@squashfs.org.uk>
-rw-r--r--squashfs-tools/mksquashfs.c173
1 files changed, 87 insertions, 86 deletions
diff --git a/squashfs-tools/mksquashfs.c b/squashfs-tools/mksquashfs.c
index ecaa3cf..e3ecc95 100644
--- a/squashfs-tools/mksquashfs.c
+++ b/squashfs-tools/mksquashfs.c
@@ -2542,42 +2542,58 @@ read_err:
}
-int write_file_blocks(squashfs_inode *inode, struct dir_ent *dir_ent,
+int write_file_blocks_dup(squashfs_inode *inode, struct dir_ent *dir_ent,
struct file_buffer *read_buffer, int *duplicate_file)
{
+ int block, thresh;
long long read_size = read_buffer->file_size;
- long long file_bytes, start;
+ long long file_bytes, dup_start, start;
struct fragment *fragment;
- unsigned int *block_list;
- int block, status;
+ struct file_info *dupl_ptr;
int blocks = (read_size + block_size - 1) >> block_log;
+ unsigned int *block_list, *block_listp;
+ struct file_buffer **buffer_list;
+ int status, num_locked_fragments;
long long sparse = 0;
struct file_buffer *fragment_buffer = NULL;
- *duplicate_file = FALSE;
-
block_list = malloc(blocks * sizeof(unsigned int));
if(block_list == NULL)
MEM_ERROR();
+ block_listp = block_list;
- lock_fragments();
+ buffer_list = malloc(blocks * sizeof(struct file_buffer *));
+ if(buffer_list == NULL)
+ MEM_ERROR();
+
+ num_locked_fragments = lock_fragments();
file_bytes = 0;
- start = bytes;
+ start = dup_start = bytes;
+ thresh = blocks > (writer_buffer_size - num_locked_fragments) ?
+ blocks - (writer_buffer_size - num_locked_fragments): 0;
+
for(block = 0; block < blocks;) {
if(read_buffer->fragment) {
block_list[block] = 0;
+ buffer_list[block] = NULL;
fragment_buffer = read_buffer;
blocks = read_size >> block_log;
} else {
block_list[block] = read_buffer->c_byte;
+
if(read_buffer->c_byte) {
read_buffer->block = bytes;
bytes += read_buffer->size;
- cache_hash(read_buffer, read_buffer->block);
file_bytes += read_buffer->size;
- queue_put(to_writer, read_buffer);
+ cache_hash(read_buffer, read_buffer->block);
+ if(block < thresh) {
+ buffer_list[block] = NULL;
+ queue_put(to_writer, read_buffer);
+ } else
+ buffer_list[block] = read_buffer;
} else {
+ buffer_list[block] = NULL;
sparse += read_buffer->size;
cache_block_put(read_buffer);
}
@@ -2591,13 +2607,37 @@ int write_file_blocks(squashfs_inode *inode, struct dir_ent *dir_ent,
}
}
+ dupl_ptr = duplicate(read_size, file_bytes, &block_listp, &dup_start,
+ &fragment, fragment_buffer, blocks, 0, 0, FALSE);
+
+ if(dupl_ptr) {
+ *duplicate_file = FALSE;
+ for(block = thresh; block < blocks; block ++)
+ if(buffer_list[block])
+ queue_put(to_writer, buffer_list[block]);
+ fragment = get_and_fill_fragment(fragment_buffer, dir_ent);
+ dupl_ptr->fragment = fragment;
+ } else {
+ *duplicate_file = TRUE;
+ for(block = thresh; block < blocks; block ++)
+ cache_block_put(buffer_list[block]);
+ bytes = start;
+ if(thresh && !block_device) {
+ int res;
+
+ queue_put(to_writer, NULL);
+ if(queue_get(from_writer) != 0)
+ EXIT_MKSQUASHFS();
+ res = ftruncate(fd, bytes);
+ if(res != 0)
+ BAD_ERROR("Failed to truncate dest file because"
+ " %s\n", strerror(errno));
+ }
+ }
+
unlock_fragments();
- fragment = get_and_fill_fragment(fragment_buffer, dir_ent);
cache_block_put(fragment_buffer);
-
- if(duplicate_checking)
- add_non_dup(read_size, file_bytes, block_list, start, fragment,
- 0, 0, FALSE);
+ free(buffer_list);
file_count ++;
total_bytes += read_size;
@@ -2612,13 +2652,11 @@ int write_file_blocks(squashfs_inode *inode, struct dir_ent *dir_ent,
if(sparse && (dir_ent->inode->buf.st_blocks << 9) >= read_size)
sparse = 0;
- create_inode(inode, NULL, dir_ent, SQUASHFS_FILE_TYPE, read_size, start,
- blocks, block_list, fragment, NULL, sparse);
+ create_inode(inode, NULL, dir_ent, SQUASHFS_FILE_TYPE, read_size,
+ dup_start, blocks, block_listp, fragment, NULL, sparse);
- if(duplicate_checking == FALSE) {
+ if(*duplicate_file == TRUE)
free(block_list);
- free_fragment(fragment);
- }
return 0;
@@ -2626,7 +2664,7 @@ read_err:
dec_progress_bar(block);
status = read_buffer->error;
bytes = start;
- if(!block_device) {
+ if(thresh && !block_device) {
int res;
queue_put(to_writer, NULL);
@@ -2638,64 +2676,54 @@ read_err:
strerror(errno));
}
unlock_fragments();
+ for(blocks = thresh; blocks < block; blocks ++)
+ cache_block_put(buffer_list[blocks]);
+ free(buffer_list);
free(block_list);
cache_block_put(read_buffer);
return status;
}
-int write_file_blocks_dup(squashfs_inode *inode, struct dir_ent *dir_ent,
- struct file_buffer *read_buffer, int *duplicate_file)
+int write_file_blocks(squashfs_inode *inode, struct dir_ent *dir_ent,
+ struct file_buffer *read_buffer, int *dup)
{
- int block, thresh;
long long read_size = read_buffer->file_size;
- long long file_bytes, dup_start, start;
+ long long file_bytes, start;
struct fragment *fragment;
- struct file_info *dupl_ptr;
+ unsigned int *block_list;
+ int block, status;
int blocks = (read_size + block_size - 1) >> block_log;
- unsigned int *block_list, *block_listp;
- struct file_buffer **buffer_list;
- int status, num_locked_fragments;
long long sparse = 0;
struct file_buffer *fragment_buffer = NULL;
+ if(pre_duplicate(read_size))
+ return write_file_blocks_dup(inode, dir_ent, read_buffer, dup);
+
+ *dup = FALSE;
+
block_list = malloc(blocks * sizeof(unsigned int));
if(block_list == NULL)
MEM_ERROR();
- block_listp = block_list;
-
- buffer_list = malloc(blocks * sizeof(struct file_buffer *));
- if(buffer_list == NULL)
- MEM_ERROR();
- num_locked_fragments = lock_fragments();
+ lock_fragments();
file_bytes = 0;
- start = dup_start = bytes;
- thresh = blocks > (writer_buffer_size - num_locked_fragments) ?
- blocks - (writer_buffer_size - num_locked_fragments): 0;
-
+ start = bytes;
for(block = 0; block < blocks;) {
if(read_buffer->fragment) {
block_list[block] = 0;
- buffer_list[block] = NULL;
fragment_buffer = read_buffer;
blocks = read_size >> block_log;
} else {
block_list[block] = read_buffer->c_byte;
-
if(read_buffer->c_byte) {
read_buffer->block = bytes;
bytes += read_buffer->size;
- file_bytes += read_buffer->size;
cache_hash(read_buffer, read_buffer->block);
- if(block < thresh) {
- buffer_list[block] = NULL;
- queue_put(to_writer, read_buffer);
- } else
- buffer_list[block] = read_buffer;
+ file_bytes += read_buffer->size;
+ queue_put(to_writer, read_buffer);
} else {
- buffer_list[block] = NULL;
sparse += read_buffer->size;
cache_block_put(read_buffer);
}
@@ -2709,37 +2737,13 @@ int write_file_blocks_dup(squashfs_inode *inode, struct dir_ent *dir_ent,
}
}
- dupl_ptr = duplicate(read_size, file_bytes, &block_listp, &dup_start,
- &fragment, fragment_buffer, blocks, 0, 0, FALSE);
-
- if(dupl_ptr) {
- *duplicate_file = FALSE;
- for(block = thresh; block < blocks; block ++)
- if(buffer_list[block])
- queue_put(to_writer, buffer_list[block]);
- fragment = get_and_fill_fragment(fragment_buffer, dir_ent);
- dupl_ptr->fragment = fragment;
- } else {
- *duplicate_file = TRUE;
- for(block = thresh; block < blocks; block ++)
- cache_block_put(buffer_list[block]);
- bytes = start;
- if(thresh && !block_device) {
- int res;
-
- queue_put(to_writer, NULL);
- if(queue_get(from_writer) != 0)
- EXIT_MKSQUASHFS();
- res = ftruncate(fd, bytes);
- if(res != 0)
- BAD_ERROR("Failed to truncate dest file because"
- " %s\n", strerror(errno));
- }
- }
-
unlock_fragments();
+ fragment = get_and_fill_fragment(fragment_buffer, dir_ent);
cache_block_put(fragment_buffer);
- free(buffer_list);
+
+ if(duplicate_checking)
+ add_non_dup(read_size, file_bytes, block_list, start, fragment,
+ 0, 0, FALSE);
file_count ++;
total_bytes += read_size;
@@ -2754,11 +2758,13 @@ int write_file_blocks_dup(squashfs_inode *inode, struct dir_ent *dir_ent,
if(sparse && (dir_ent->inode->buf.st_blocks << 9) >= read_size)
sparse = 0;
- create_inode(inode, NULL, dir_ent, SQUASHFS_FILE_TYPE, read_size,
- dup_start, blocks, block_listp, fragment, NULL, sparse);
+ create_inode(inode, NULL, dir_ent, SQUASHFS_FILE_TYPE, read_size, start,
+ blocks, block_list, fragment, NULL, sparse);
- if(*duplicate_file == TRUE)
+ if(duplicate_checking == FALSE) {
free(block_list);
+ free_fragment(fragment);
+ }
return 0;
@@ -2766,7 +2772,7 @@ read_err:
dec_progress_bar(block);
status = read_buffer->error;
bytes = start;
- if(thresh && !block_device) {
+ if(!block_device) {
int res;
queue_put(to_writer, NULL);
@@ -2778,9 +2784,6 @@ read_err:
strerror(errno));
}
unlock_fragments();
- for(blocks = thresh; blocks < block; blocks ++)
- cache_block_put(buffer_list[blocks]);
- free(buffer_list);
free(block_list);
cache_block_put(read_buffer);
return status;
@@ -2804,8 +2807,6 @@ again:
write_file_empty(inode, dir, read_buffer, dup);
else if(read_buffer->fragment && read_buffer->c_byte)
write_file_frag(inode, dir, read_buffer, dup);
- else if(pre_duplicate(read_buffer->file_size))
- status = write_file_blocks_dup(inode, dir, read_buffer, dup);
else
status = write_file_blocks(inode, dir, read_buffer, dup);