[patch 3/3] squashfs: Switch from zlib/inflate to "zlib" crypto module

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



From: Geert Uytterhoeven <Geert.Uytterhoeven@xxxxxxxxxxx>

Modify SquashFS 3.4 to use the "zlib" crypto module instead of making direct
calls to the zlib/inflate library

Signed-off-by: Geert Uytterhoeven <Geert.Uytterhoeven@xxxxxxxxxxx>
---
 fs/Kconfig                     |    3 +
 fs/squashfs/inode.c            |   65 +++++++++++++++++++++--------------------
 include/linux/squashfs_fs_sb.h |    3 +
 3 files changed, 38 insertions(+), 33 deletions(-)

--- a/fs/Kconfig
+++ b/fs/Kconfig
@@ -1350,7 +1350,8 @@ config CRAMFS
 
 config SQUASHFS
 	tristate "SquashFS 3.4 - Squashed file system support"
-	select ZLIB_INFLATE
+	select CRYPTO
+	select CRYPTO_ZLIB
 	help
 	  Saying Y here includes support for SquashFS 3.4 (a Compressed
 	  Read-Only File System).  Squashfs is a highly compressed read-only
--- a/fs/squashfs/inode.c
+++ b/fs/squashfs/inode.c
@@ -23,7 +23,6 @@
 
 #include <linux/squashfs_fs.h>
 #include <linux/module.h>
-#include <linux/zlib.h>
 #include <linux/fs.h>
 #include <linux/squashfs_fs_sb.h>
 #include <linux/squashfs_fs_i.h>
@@ -36,6 +35,9 @@
 
 #include "squashfs.h"
 
+#define SQUASHFS_CRYPTO_ALG	"zlib"
+
+
 static struct dentry *squashfs_fh_to_dentry(struct super_block *s,
 		struct fid *fid, int fh_len, int fh_type);
 static struct dentry *squashfs_fh_to_parent(struct super_block *s,
@@ -236,7 +238,10 @@ SQSH_EXTERN unsigned int squashfs_read_d
 	}
 
 	if (compressed) {
-		int zlib_err = 0;
+		int error = 0;
+		void *next_out;
+		int avail_out;
+		unsigned int total_out = 0, dlen;
 
 		/*
 	 	* uncompress block
@@ -244,8 +249,8 @@ SQSH_EXTERN unsigned int squashfs_read_d
 
 		mutex_lock(&msblk->read_data_mutex);
 
-		msblk->stream.next_out = buffer;
-		msblk->stream.avail_out = srclength;
+		next_out = buffer;
+		avail_out = srclength;
 
 		for (bytes = 0; k < b; k++) {
 			avail_bytes = min(c_byte - bytes, msblk->devblksize - offset);
@@ -254,16 +259,8 @@ SQSH_EXTERN unsigned int squashfs_read_d
 			if (!buffer_uptodate(bh[k]))
 				goto release_mutex;
 
-			msblk->stream.next_in = bh[k]->b_data + offset;
-			msblk->stream.avail_in = avail_bytes;
-
 			if (k == 0) {
-				zlib_err = zlib_inflateInit(&msblk->stream);
-				if (zlib_err != Z_OK) {
-					ERROR("zlib_inflateInit returned unexpected result 0x%x,"
-						" srclength %d\n", zlib_err, srclength);
-					goto release_mutex;
-				}
+				total_out = 0;
 
 				if (avail_bytes == 0) {
 					offset = 0;
@@ -272,29 +269,32 @@ SQSH_EXTERN unsigned int squashfs_read_d
 				}
 			}
 
-			zlib_err = zlib_inflate(&msblk->stream, Z_NO_FLUSH);
-			if (zlib_err != Z_OK && zlib_err != Z_STREAM_END) {
-				ERROR("zlib_inflate returned unexpected result 0x%x,"
-					" srclength %d, avail_in %d, avail_out %d\n", zlib_err,
-					srclength, msblk->stream.avail_in, msblk->stream.avail_out);
+			dlen = avail_out;
+			error = crypto_comp_decompress(msblk->tfm,
+						       bh[k]->b_data + offset,
+						       avail_bytes, next_out,
+						       &dlen);
+			if (error && error != -EAGAIN) {
+				ERROR("crypto_comp_decompress returned "
+				      "unexpected result %d, srclength %d, "
+				      "avail_bytes %d, avail_out %d\n",
+				      error, srclength, avail_bytes,
+				      avail_out);
 				goto release_mutex;
 			}
+			next_out += dlen;
+			avail_out -= dlen;
+			total_out += dlen;
 
 			bytes += avail_bytes;
 			offset = 0;
 			brelse(bh[k]);
 		}
 
-		if (zlib_err != Z_STREAM_END)
+		if (error)
 			goto release_mutex;
 
-		zlib_err = zlib_inflateEnd(&msblk->stream);
-		if (zlib_err != Z_OK) {
-			ERROR("zlib_inflateEnd returned unexpected result 0x%x,"
-				" srclength %d\n", zlib_err, srclength);
-			goto release_mutex;
-		}
-		bytes = msblk->stream.total_out;
+		bytes = total_out;
 		mutex_unlock(&msblk->read_data_mutex);
 	} else {
 		int i;
@@ -1104,9 +1104,12 @@ static int squashfs_fill_super(struct su
 	}
 	msblk = s->s_fs_info;
 
-	msblk->stream.workspace = vmalloc(zlib_inflate_workspacesize());
-	if (msblk->stream.workspace == NULL) {
-		ERROR("Failed to allocate zlib workspace\n");
+	msblk->tfm = crypto_alloc_comp(SQUASHFS_CRYPTO_ALG, 0,
+				       CRYPTO_ALG_ASYNC);
+	if (IS_ERR(msblk->tfm)) {
+		ERROR("Failed to load %s crypto module\n",
+		      SQUASHFS_CRYPTO_ALG);
+		msblk->tfm = NULL;
 		goto failure;
 	}
 	sblk = &msblk->sblk;
@@ -1273,7 +1276,7 @@ failed_mount:
 	vfree(msblk->read_page);
 	squashfs_cache_delete(msblk->block_cache);
 	kfree(msblk->fragment_index_2);
-	vfree(msblk->stream.workspace);
+	crypto_free_comp(msblk->tfm);
 	kfree(s->s_fs_info);
 	s->s_fs_info = NULL;
 	return -EINVAL;
@@ -2084,7 +2087,7 @@ static void squashfs_put_super(struct su
 		kfree(sbi->fragment_index);
 		kfree(sbi->fragment_index_2);
 		kfree(sbi->meta_index);
-		vfree(sbi->stream.workspace);
+		crypto_free_comp(sbi->tfm);
 		kfree(s->s_fs_info);
 		s->s_fs_info = NULL;
 	}
--- a/include/linux/squashfs_fs_sb.h
+++ b/include/linux/squashfs_fs_sb.h
@@ -24,6 +24,7 @@
  */
 
 #include <linux/squashfs_fs.h>
+#include <linux/crypto.h>
 
 struct squashfs_cache_entry {
 	long long	block;
@@ -67,7 +68,7 @@ struct squashfs_sb_info {
 	struct mutex		read_page_mutex;
 	struct mutex		meta_index_mutex;
 	struct meta_index	*meta_index;
-	z_stream		stream;
+	struct crypto_comp	*tfm;
 	long long		*inode_lookup_table;
 	int			(*read_inode)(struct inode *i,  squashfs_inode_t \
 				inode);

-- 
With kind regards,

Geert Uytterhoeven
Software Architect

Sony Techsoft Centre Europe
The Corporate Village · Da Vincilaan 7-D1 · B-1935 Zaventem · Belgium

Phone:    +32 (0)2 700 8453
Fax:      +32 (0)2 700 8622
E-mail:   Geert.Uytterhoeven@xxxxxxxxxxx
Internet: http://www.sony-europe.com/

A division of Sony Europe (Belgium) N.V.
VAT BE 0413.825.160 · RPR Brussels
Fortis · BIC GEBABEBB · IBAN BE41293037680010

--
To unsubscribe from this list: send the line "unsubscribe linux-crypto" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Kernel]     [Gnu Classpath]     [Gnu Crypto]     [DM Crypt]     [Netfilter]     [Bugtraq]

  Powered by Linux