wok-stable annotate linux/stuff/linux-squashfs-lzma-2.6.33.2.u @ rev 5271

linux: increase gzip compression
author Pascal Bellard <pascal.bellard@slitaz.org>
date Thu Apr 15 18:22:14 2010 +0200 (2010-04-15)
parents
children
rev   line source
pankso@5245 1 --- linux-2.6.30.6/fs/squashfs/Kconfig
pankso@5245 2 +++ linux-2.6.30.6/fs/squashfs/Kconfig
pankso@5245 3 @@ -26,6 +26,12 @@
pankso@5245 4
pankso@5245 5 If unsure, say N.
pankso@5245 6
pankso@5245 7 +config SQUASHFS_LZMA
pankso@5245 8 + bool "Include support for LZMA compressed file systems"
pankso@5245 9 + depends on SQUASHFS
pankso@5245 10 + select DECOMPRESS_LZMA
pankso@5245 11 + select DECOMPRESS_LZMA_NEEDED
pankso@5245 12 +
pankso@5245 13 config SQUASHFS_EMBEDDED
pankso@5245 14
pankso@5245 15 bool "Additional option for memory-constrained systems"
pankso@5245 16
pankso@5245 17 --- linux-2.6.30.6/fs/squashfs/Makefile
pankso@5245 18 +++ linux-2.6.30.6/fs/squashfs/Makefile
pankso@5245 19 @@ -4,4 +4,5 @@
pankso@5245 20
pankso@5245 21 obj-$(CONFIG_SQUASHFS) += squashfs.o
pankso@5245 22 squashfs-y += block.o cache.o dir.o export.o file.o fragment.o id.o inode.o
pankso@5245 23 -squashfs-y += namei.o super.o symlink.o
pankso@5245 24 +squashfs-y += namei.o super.o symlink.o zlib_wrapper.o decompressor.o
pankso@5245 25 +squashfs-$(CONFIG_SQUASHFS_LZMA) += lzma_wrapper.o
pankso@5245 26
pankso@5245 27 --- linux-2.6.30.6/fs/squashfs/block.c
pankso@5245 28 +++ linux-2.6.30.6/fs/squashfs/block.c
pankso@5245 29 @@ -29,15 +29,14 @@
pankso@5245 30 #include <linux/fs.h>
pankso@5245 31 #include <linux/vfs.h>
pankso@5245 32 #include <linux/slab.h>
pankso@5245 33 -#include <linux/mutex.h>
pankso@5245 34 #include <linux/string.h>
pankso@5245 35 #include <linux/buffer_head.h>
pankso@5245 36 -#include <linux/zlib.h>
pankso@5245 37
pankso@5245 38 #include "squashfs_fs.h"
pankso@5245 39 #include "squashfs_fs_sb.h"
pankso@5245 40 #include "squashfs_fs_i.h"
pankso@5245 41 #include "squashfs.h"
pankso@5245 42 +#include "decompressor.h"
pankso@5245 43
pankso@5245 44 /*
pankso@5245 45 * Read the metadata block length, this is stored in the first two
pankso@5245 46 @@ -153,72 +152,10 @@
pankso@5245 47 }
pankso@5245 48
pankso@5245 49 if (compressed) {
pankso@5245 50 - int zlib_err = 0, zlib_init = 0;
pankso@5245 51 -
pankso@5245 52 - /*
pankso@5245 53 - * Uncompress block.
pankso@5245 54 - */
pankso@5245 55 -
pankso@5245 56 - mutex_lock(&msblk->read_data_mutex);
pankso@5245 57 -
pankso@5245 58 - msblk->stream.avail_out = 0;
pankso@5245 59 - msblk->stream.avail_in = 0;
pankso@5245 60 -
pankso@5245 61 - bytes = length;
pankso@5245 62 - do {
pankso@5245 63 - if (msblk->stream.avail_in == 0 && k < b) {
pankso@5245 64 - avail = min(bytes, msblk->devblksize - offset);
pankso@5245 65 - bytes -= avail;
pankso@5245 66 - wait_on_buffer(bh[k]);
pankso@5245 67 - if (!buffer_uptodate(bh[k]))
pankso@5245 68 - goto release_mutex;
pankso@5245 69 -
pankso@5245 70 - if (avail == 0) {
pankso@5245 71 - offset = 0;
pankso@5245 72 - put_bh(bh[k++]);
pankso@5245 73 - continue;
pankso@5245 74 - }
pankso@5245 75 -
pankso@5245 76 - msblk->stream.next_in = bh[k]->b_data + offset;
pankso@5245 77 - msblk->stream.avail_in = avail;
pankso@5245 78 - offset = 0;
pankso@5245 79 - }
pankso@5245 80 -
pankso@5245 81 - if (msblk->stream.avail_out == 0 && page < pages) {
pankso@5245 82 - msblk->stream.next_out = buffer[page++];
pankso@5245 83 - msblk->stream.avail_out = PAGE_CACHE_SIZE;
pankso@5245 84 - }
pankso@5245 85 -
pankso@5245 86 - if (!zlib_init) {
pankso@5245 87 - zlib_err = zlib_inflateInit(&msblk->stream);
pankso@5245 88 - if (zlib_err != Z_OK) {
pankso@5245 89 - ERROR("zlib_inflateInit returned"
pankso@5245 90 - " unexpected result 0x%x,"
pankso@5245 91 - " srclength %d\n", zlib_err,
pankso@5245 92 - srclength);
pankso@5245 93 - goto release_mutex;
pankso@5245 94 - }
pankso@5245 95 - zlib_init = 1;
pankso@5245 96 - }
pankso@5245 97 -
pankso@5245 98 - zlib_err = zlib_inflate(&msblk->stream, Z_SYNC_FLUSH);
pankso@5245 99 -
pankso@5245 100 - if (msblk->stream.avail_in == 0 && k < b)
pankso@5245 101 - put_bh(bh[k++]);
pankso@5245 102 - } while (zlib_err == Z_OK);
pankso@5245 103 -
pankso@5245 104 - if (zlib_err != Z_STREAM_END) {
pankso@5245 105 - ERROR("zlib_inflate error, data probably corrupt\n");
pankso@5245 106 - goto release_mutex;
pankso@5245 107 - }
pankso@5245 108 -
pankso@5245 109 - zlib_err = zlib_inflateEnd(&msblk->stream);
pankso@5245 110 - if (zlib_err != Z_OK) {
pankso@5245 111 - ERROR("zlib_inflate error, data probably corrupt\n");
pankso@5245 112 - goto release_mutex;
pankso@5245 113 - }
pankso@5245 114 - length = msblk->stream.total_out;
pankso@5245 115 - mutex_unlock(&msblk->read_data_mutex);
pankso@5245 116 + length = squashfs_decompress(msblk, buffer, bh, b, offset,
pankso@5245 117 + length, srclength, pages);
pankso@5245 118 + if (length < 0)
pankso@5245 119 + goto read_failure;
pankso@5245 120 } else {
pankso@5245 121 /*
pankso@5245 122 * Block is uncompressed.
pankso@5245 123 @@ -254,9 +191,6 @@
pankso@5245 124
pankso@5245 125 kfree(bh);
pankso@5245 126 return length;
pankso@5245 127 -
pankso@5245 128 -release_mutex:
pankso@5245 129 - mutex_unlock(&msblk->read_data_mutex);
pankso@5245 130
pankso@5245 131 block_release:
pankso@5245 132 for (; k < b; k++)
pankso@5245 133
pankso@5245 134 --- linux-2.6.30.6/fs/squashfs/cache.c
pankso@5245 135 +++ linux-2.6.30.6/fs/squashfs/cache.c
pankso@5245 136 @@ -51,7 +51,6 @@
pankso@5245 137 #include <linux/sched.h>
pankso@5245 138 #include <linux/spinlock.h>
pankso@5245 139 #include <linux/wait.h>
pankso@5245 140 -#include <linux/zlib.h>
pankso@5245 141 #include <linux/pagemap.h>
pankso@5245 142
pankso@5245 143 #include "squashfs_fs.h"
pankso@5245 144
pankso@5245 145 --- linux-2.6.30.6/fs/squashfs/decompressor.c
pankso@5245 146 +++ linux-2.6.30.6/fs/squashfs/decompressor.c
pankso@5245 147 @@ -0,0 +1,72 @@
pankso@5245 148 +/*
pankso@5245 149 + * Squashfs - a compressed read only filesystem for Linux
pankso@5245 150 + *
pankso@5245 151 + * Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
pankso@5245 152 + * Phillip Lougher <phillip@lougher.demon.co.uk>
pankso@5245 153 + *
pankso@5245 154 + * This program is free software; you can redistribute it and/or
pankso@5245 155 + * modify it under the terms of the GNU General Public License
pankso@5245 156 + * as published by the Free Software Foundation; either version 2,
pankso@5245 157 + * or (at your option) any later version.
pankso@5245 158 + *
pankso@5245 159 + * This program is distributed in the hope that it will be useful,
pankso@5245 160 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
pankso@5245 161 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
pankso@5245 162 + * GNU General Public License for more details.
pankso@5245 163 + *
pankso@5245 164 + * You should have received a copy of the GNU General Public License
pankso@5245 165 + * along with this program; if not, write to the Free Software
pankso@5245 166 + * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
pankso@5245 167 + *
pankso@5245 168 + * decompressor.c
pankso@5245 169 + */
pankso@5245 170 +
pankso@5245 171 +#include <linux/types.h>
pankso@5245 172 +#include <linux/mutex.h>
pankso@5245 173 +#include <linux/buffer_head.h>
pankso@5245 174 +
pankso@5245 175 +#include "squashfs_fs.h"
pankso@5245 176 +#include "squashfs_fs_sb.h"
pankso@5245 177 +#include "squashfs_fs_i.h"
pankso@5245 178 +#include "decompressor.h"
pankso@5245 179 +#include "squashfs.h"
pankso@5245 180 +
pankso@5245 181 +/*
pankso@5245 182 + * This file (and decompressor.h) implements a decompressor framework for
pankso@5245 183 + * Squashfs, allowing multiple decompressors to be easily supported
pankso@5245 184 + */
pankso@5245 185 +
pankso@5245 186 +static const struct squashfs_decompressor squashfs_lzma_unsupported_comp_ops = {
pankso@5245 187 + NULL, NULL, NULL, LZMA_COMPRESSION, "lzma", 0
pankso@5245 188 +};
pankso@5245 189 +
pankso@5245 190 +static const struct squashfs_decompressor squashfs_lzo_unsupported_comp_ops = {
pankso@5245 191 + NULL, NULL, NULL, LZO_COMPRESSION, "lzo", 0
pankso@5245 192 +};
pankso@5245 193 +
pankso@5245 194 +static const struct squashfs_decompressor squashfs_unknown_comp_ops = {
pankso@5245 195 + NULL, NULL, NULL, 0, "unknown", 0
pankso@5245 196 +};
pankso@5245 197 +
pankso@5245 198 +static const struct squashfs_decompressor *decompressor[] = {
pankso@5245 199 + &squashfs_zlib_comp_ops,
pankso@5245 200 +#ifdef CONFIG_SQUASHFS_LZMA
pankso@5245 201 + &squashfs_lzma_comp_ops,
pankso@5245 202 +#else
pankso@5245 203 + &squashfs_lzma_unsupported_comp_ops,
pankso@5245 204 +#endif
pankso@5245 205 + &squashfs_lzo_unsupported_comp_ops,
pankso@5245 206 + &squashfs_unknown_comp_ops
pankso@5245 207 +};
pankso@5245 208 +
pankso@5245 209 +
pankso@5245 210 +const struct squashfs_decompressor *squashfs_lookup_decompressor(int id)
pankso@5245 211 +{
pankso@5245 212 + int i;
pankso@5245 213 +
pankso@5245 214 + for (i = 0; decompressor[i]->id; i++)
pankso@5245 215 + if (id == decompressor[i]->id)
pankso@5245 216 + break;
pankso@5245 217 +
pankso@5245 218 + return decompressor[i];
pankso@5245 219 +}
pankso@5245 220
pankso@5245 221 --- linux-2.6.30.6/fs/squashfs/decompressor.h
pankso@5245 222 +++ linux-2.6.30.6/fs/squashfs/decompressor.h
pankso@5245 223 @@ -0,0 +1,55 @@
pankso@5245 224 +#ifndef DECOMPRESSOR_H
pankso@5245 225 +#define DECOMPRESSOR_H
pankso@5245 226 +/*
pankso@5245 227 + * Squashfs - a compressed read only filesystem for Linux
pankso@5245 228 + *
pankso@5245 229 + * Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
pankso@5245 230 + * Phillip Lougher <phillip@lougher.demon.co.uk>
pankso@5245 231 + *
pankso@5245 232 + * This program is free software; you can redistribute it and/or
pankso@5245 233 + * modify it under the terms of the GNU General Public License
pankso@5245 234 + * as published by the Free Software Foundation; either version 2,
pankso@5245 235 + * or (at your option) any later version.
pankso@5245 236 + *
pankso@5245 237 + * This program is distributed in the hope that it will be useful,
pankso@5245 238 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
pankso@5245 239 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
pankso@5245 240 + * GNU General Public License for more details.
pankso@5245 241 + *
pankso@5245 242 + * You should have received a copy of the GNU General Public License
pankso@5245 243 + * along with this program; if not, write to the Free Software
pankso@5245 244 + * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
pankso@5245 245 + *
pankso@5245 246 + * decompressor.h
pankso@5245 247 + */
pankso@5245 248 +
pankso@5245 249 +struct squashfs_decompressor {
pankso@5245 250 + void *(*init)(struct squashfs_sb_info *);
pankso@5245 251 + void (*free)(void *);
pankso@5245 252 + int (*decompress)(struct squashfs_sb_info *, void **,
pankso@5245 253 + struct buffer_head **, int, int, int, int, int);
pankso@5245 254 + int id;
pankso@5245 255 + char *name;
pankso@5245 256 + int supported;
pankso@5245 257 +};
pankso@5245 258 +
pankso@5245 259 +static inline void *squashfs_decompressor_init(struct squashfs_sb_info *msblk)
pankso@5245 260 +{
pankso@5245 261 + return msblk->decompressor->init(msblk);
pankso@5245 262 +}
pankso@5245 263 +
pankso@5245 264 +static inline void squashfs_decompressor_free(struct squashfs_sb_info *msblk,
pankso@5245 265 + void *s)
pankso@5245 266 +{
pankso@5245 267 + if (msblk->decompressor)
pankso@5245 268 + msblk->decompressor->free(s);
pankso@5245 269 +}
pankso@5245 270 +
pankso@5245 271 +static inline int squashfs_decompress(struct squashfs_sb_info *msblk,
pankso@5245 272 + void **buffer, struct buffer_head **bh, int b, int offset, int length,
pankso@5245 273 + int srclength, int pages)
pankso@5245 274 +{
pankso@5245 275 + return msblk->decompressor->decompress(msblk, buffer, bh, b, offset,
pankso@5245 276 + length, srclength, pages);
pankso@5245 277 +}
pankso@5245 278 +#endif
pankso@5245 279
pankso@5245 280 --- linux-2.6.30.6/fs/squashfs/dir.c
pankso@5245 281 +++ linux-2.6.30.6/fs/squashfs/dir.c
pankso@5245 282 @@ -30,7 +30,6 @@
pankso@5245 283 #include <linux/fs.h>
pankso@5245 284 #include <linux/vfs.h>
pankso@5245 285 #include <linux/slab.h>
pankso@5245 286 -#include <linux/zlib.h>
pankso@5245 287
pankso@5245 288 #include "squashfs_fs.h"
pankso@5245 289 #include "squashfs_fs_sb.h"
pankso@5245 290
pankso@5245 291 --- linux-2.6.30.6/fs/squashfs/export.c
pankso@5245 292 +++ linux-2.6.30.6/fs/squashfs/export.c
pankso@5245 293 @@ -39,7 +39,6 @@
pankso@5245 294 #include <linux/vfs.h>
pankso@5245 295 #include <linux/dcache.h>
pankso@5245 296 #include <linux/exportfs.h>
pankso@5245 297 -#include <linux/zlib.h>
pankso@5245 298 #include <linux/slab.h>
pankso@5245 299
pankso@5245 300 #include "squashfs_fs.h"
pankso@5245 301
pankso@5245 302 --- linux-2.6.30.6/fs/squashfs/file.c
pankso@5245 303 +++ linux-2.6.30.6/fs/squashfs/file.c
pankso@5245 304 @@ -47,7 +47,6 @@
pankso@5245 305 #include <linux/string.h>
pankso@5245 306 #include <linux/pagemap.h>
pankso@5245 307 #include <linux/mutex.h>
pankso@5245 308 -#include <linux/zlib.h>
pankso@5245 309
pankso@5245 310 #include "squashfs_fs.h"
pankso@5245 311 #include "squashfs_fs_sb.h"
pankso@5245 312
pankso@5245 313 --- linux-2.6.30.6/fs/squashfs/fragment.c
pankso@5245 314 +++ linux-2.6.30.6/fs/squashfs/fragment.c
pankso@5245 315 @@ -36,7 +36,6 @@
pankso@5245 316 #include <linux/fs.h>
pankso@5245 317 #include <linux/vfs.h>
pankso@5245 318 #include <linux/slab.h>
pankso@5245 319 -#include <linux/zlib.h>
pankso@5245 320
pankso@5245 321 #include "squashfs_fs.h"
pankso@5245 322 #include "squashfs_fs_sb.h"
pankso@5245 323
pankso@5245 324 --- linux-2.6.30.6/fs/squashfs/id.c
pankso@5245 325 +++ linux-2.6.30.6/fs/squashfs/id.c
pankso@5245 326 @@ -34,7 +34,6 @@
pankso@5245 327 #include <linux/fs.h>
pankso@5245 328 #include <linux/vfs.h>
pankso@5245 329 #include <linux/slab.h>
pankso@5245 330 -#include <linux/zlib.h>
pankso@5245 331
pankso@5245 332 #include "squashfs_fs.h"
pankso@5245 333 #include "squashfs_fs_sb.h"
pankso@5245 334
pankso@5245 335 --- linux-2.6.30.6/fs/squashfs/inode.c
pankso@5245 336 +++ linux-2.6.30.6/fs/squashfs/inode.c
pankso@5245 337 @@ -40,7 +40,6 @@
pankso@5245 338
pankso@5245 339 #include <linux/fs.h>
pankso@5245 340 #include <linux/vfs.h>
pankso@5245 341 -#include <linux/zlib.h>
pankso@5245 342
pankso@5245 343 #include "squashfs_fs.h"
pankso@5245 344 #include "squashfs_fs_sb.h"
pankso@5245 345
pankso@5245 346 --- linux-2.6.30.6/fs/squashfs/lzma_wrapper.c
pankso@5245 347 +++ linux-2.6.30.6/fs/squashfs/lzma_wrapper.c
pankso@5245 348 @@ -0,0 +1,151 @@
pankso@5245 349 +/*
pankso@5245 350 + * Squashfs - a compressed read only filesystem for Linux
pankso@5245 351 + *
pankso@5245 352 + * Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
pankso@5245 353 + * Phillip Lougher <phillip@lougher.demon.co.uk>
pankso@5245 354 + *
pankso@5245 355 + * This program is free software; you can redistribute it and/or
pankso@5245 356 + * modify it under the terms of the GNU General Public License
pankso@5245 357 + * as published by the Free Software Foundation; either version 2,
pankso@5245 358 + * or (at your option) any later version.
pankso@5245 359 + *
pankso@5245 360 + * This program is distributed in the hope that it will be useful,
pankso@5245 361 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
pankso@5245 362 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
pankso@5245 363 + * GNU General Public License for more details.
pankso@5245 364 + *
pankso@5245 365 + * You should have received a copy of the GNU General Public License
pankso@5245 366 + * along with this program; if not, write to the Free Software
pankso@5245 367 + * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
pankso@5245 368 + *
pankso@5245 369 + * lzma_wrapper.c
pankso@5245 370 + */
pankso@5245 371 +
pankso@5245 372 +#include <asm/unaligned.h>
pankso@5245 373 +#include <linux/buffer_head.h>
pankso@5245 374 +#include <linux/mutex.h>
pankso@5245 375 +#include <linux/vmalloc.h>
pankso@5245 376 +#include <linux/decompress/unlzma.h>
pankso@5245 377 +
pankso@5245 378 +#include "squashfs_fs.h"
pankso@5245 379 +#include "squashfs_fs_sb.h"
pankso@5245 380 +#include "squashfs_fs_i.h"
pankso@5245 381 +#include "squashfs.h"
pankso@5245 382 +#include "decompressor.h"
pankso@5245 383 +
pankso@5245 384 +struct squashfs_lzma {
pankso@5245 385 + void *input;
pankso@5245 386 + void *output;
pankso@5245 387 +};
pankso@5245 388 +
pankso@5245 389 +/* decompress_unlzma.c is currently non re-entrant... */
pankso@5245 390 +DEFINE_MUTEX(lzma_mutex);
pankso@5245 391 +
pankso@5245 392 +/* decompress_unlzma.c doesn't provide any context in its callbacks... */
pankso@5245 393 +static int lzma_error;
pankso@5245 394 +
pankso@5245 395 +static void error(char *m)
pankso@5245 396 +{
pankso@5245 397 + ERROR("unlzma error: %s\n", m);
pankso@5245 398 + lzma_error = 1;
pankso@5245 399 +}
pankso@5245 400 +
pankso@5245 401 +
pankso@5245 402 +static void *lzma_init(struct squashfs_sb_info *msblk)
pankso@5245 403 +{
pankso@5245 404 + struct squashfs_lzma *stream = kzalloc(sizeof(*stream), GFP_KERNEL);
pankso@5245 405 + if (stream == NULL)
pankso@5245 406 + goto failed;
pankso@5245 407 + stream->input = vmalloc(msblk->block_size);
pankso@5245 408 + if (stream->input == NULL)
pankso@5245 409 + goto failed;
pankso@5245 410 + stream->output = vmalloc(msblk->block_size);
pankso@5245 411 + if (stream->output == NULL)
pankso@5245 412 + goto failed2;
pankso@5245 413 +
pankso@5245 414 + return stream;
pankso@5245 415 +
pankso@5245 416 +failed2:
pankso@5245 417 + vfree(stream->input);
pankso@5245 418 +failed:
pankso@5245 419 + ERROR("failed to allocate lzma workspace\n");
pankso@5245 420 + kfree(stream);
pankso@5245 421 + return NULL;
pankso@5245 422 +}
pankso@5245 423 +
pankso@5245 424 +
pankso@5245 425 +static void lzma_free(void *strm)
pankso@5245 426 +{
pankso@5245 427 + struct squashfs_lzma *stream = strm;
pankso@5245 428 +
pankso@5245 429 + if (stream) {
pankso@5245 430 + vfree(stream->input);
pankso@5245 431 + vfree(stream->output);
pankso@5245 432 + }
pankso@5245 433 + kfree(stream);
pankso@5245 434 +}
pankso@5245 435 +
pankso@5245 436 +
pankso@5245 437 +static int lzma_uncompress(struct squashfs_sb_info *msblk, void **buffer,
pankso@5245 438 + struct buffer_head **bh, int b, int offset, int length, int srclength,
pankso@5245 439 + int pages)
pankso@5245 440 +{
pankso@5245 441 + struct squashfs_lzma *stream = msblk->stream;
pankso@5245 442 + void *buff = stream->input;
pankso@5245 443 + int avail, i, bytes = length, res;
pankso@5245 444 +
pankso@5245 445 + mutex_lock(&lzma_mutex);
pankso@5245 446 +
pankso@5245 447 + for (i = 0; i < b; i++) {
pankso@5245 448 + wait_on_buffer(bh[i]);
pankso@5245 449 + if (!buffer_uptodate(bh[i]))
pankso@5245 450 + goto block_release;
pankso@5245 451 +
pankso@5245 452 + avail = min(bytes, msblk->devblksize - offset);
pankso@5245 453 + memcpy(buff, bh[i]->b_data + offset, avail);
pankso@5245 454 + buff += avail;
pankso@5245 455 + bytes -= avail;
pankso@5245 456 + offset = 0;
pankso@5245 457 + put_bh(bh[i]);
pankso@5245 458 + }
pankso@5245 459 +
pankso@5245 460 + lzma_error = 0;
pankso@5245 461 + res = unlzma(stream->input, length, NULL, NULL, stream->output, NULL,
pankso@5245 462 + error);
pankso@5245 463 + if (res || lzma_error)
pankso@5245 464 + goto failed;
pankso@5245 465 +
pankso@5245 466 + /* uncompressed size is stored in the LZMA header (5 byte offset) */
pankso@5245 467 + res = bytes = get_unaligned_le32(stream->input + 5);
pankso@5245 468 + for (i = 0, buff = stream->output; bytes && i < pages; i++) {
pankso@5245 469 + avail = min_t(int, bytes, PAGE_CACHE_SIZE);
pankso@5245 470 + memcpy(buffer[i], buff, avail);
pankso@5245 471 + buff += avail;
pankso@5245 472 + bytes -= avail;
pankso@5245 473 + }
pankso@5245 474 + if (bytes)
pankso@5245 475 + goto failed;
pankso@5245 476 +
pankso@5245 477 + mutex_unlock(&lzma_mutex);
pankso@5245 478 + return res;
pankso@5245 479 +
pankso@5245 480 +block_release:
pankso@5245 481 + for (; i < b; i++)
pankso@5245 482 + put_bh(bh[i]);
pankso@5245 483 +
pankso@5245 484 +failed:
pankso@5245 485 + mutex_unlock(&lzma_mutex);
pankso@5245 486 +
pankso@5245 487 + ERROR("lzma decompression failed, data probably corrupt\n");
pankso@5245 488 + return -EIO;
pankso@5245 489 +}
pankso@5245 490 +
pankso@5245 491 +const struct squashfs_decompressor squashfs_lzma_comp_ops = {
pankso@5245 492 + .init = lzma_init,
pankso@5245 493 + .free = lzma_free,
pankso@5245 494 + .decompress = lzma_uncompress,
pankso@5245 495 + .id = LZMA_COMPRESSION,
pankso@5245 496 + .name = "lzma",
pankso@5245 497 + .supported = 1
pankso@5245 498 +};
pankso@5245 499 +
pankso@5245 500
pankso@5245 501 --- linux-2.6.30.6/fs/squashfs/namei.c
pankso@5245 502 +++ linux-2.6.30.6/fs/squashfs/namei.c
pankso@5245 503 @@ -57,7 +57,6 @@
pankso@5245 504 #include <linux/slab.h>
pankso@5245 505 #include <linux/string.h>
pankso@5245 506 #include <linux/dcache.h>
pankso@5245 507 -#include <linux/zlib.h>
pankso@5245 508
pankso@5245 509 #include "squashfs_fs.h"
pankso@5245 510 #include "squashfs_fs_sb.h"
pankso@5245 511
pankso@5245 512 --- linux-2.6.30.6/fs/squashfs/squashfs.h
pankso@5245 513 +++ linux-2.6.30.6/fs/squashfs/squashfs.h
pankso@5245 514 @@ -51,6 +51,9 @@
pankso@5245 515 u64, int);
pankso@5245 516 extern int squashfs_read_table(struct super_block *, void *, u64, int);
pankso@5245 517
pankso@5245 518 +/* decompressor.c */
pankso@5245 519 +extern const struct squashfs_decompressor *squashfs_lookup_decompressor(int);
pankso@5245 520 +
pankso@5245 521 /* export.c */
pankso@5245 522 extern __le64 *squashfs_read_inode_lookup_table(struct super_block *, u64,
pankso@5245 523 unsigned int);
pankso@5245 524 @@ -71,7 +74,7 @@
pankso@5245 525 extern int squashfs_read_inode(struct inode *, long long);
pankso@5245 526
pankso@5245 527 /*
pankso@5245 528 - * Inodes and files operations
pankso@5245 529 + * Inodes, files and decompressor operations
pankso@5245 530 */
pankso@5245 531
pankso@5245 532 /* dir.c */
pankso@5245 533 @@ -88,3 +91,9 @@
pankso@5245 534
pankso@5245 535 /* symlink.c */
pankso@5245 536 extern const struct address_space_operations squashfs_symlink_aops;
pankso@5245 537 +
pankso@5245 538 +/* zlib_wrapper.c */
pankso@5245 539 +extern const struct squashfs_decompressor squashfs_zlib_comp_ops;
pankso@5245 540 +
pankso@5245 541 +/* lzma wrapper.c */
pankso@5245 542 +extern const struct squashfs_decompressor squashfs_lzma_comp_ops;
pankso@5245 543
pankso@5245 544 --- linux-2.6.30.6/fs/squashfs/squashfs_fs.h
pankso@5245 545 +++ linux-2.6.30.6/fs/squashfs/squashfs_fs.h
pankso@5245 546 @@ -211,7 +211,9 @@
pankso@5245 547 /*
pankso@5245 548 * definitions for structures on disk
pankso@5245 549 */
pankso@5245 550 -#define ZLIB_COMPRESSION 1
pankso@5245 551 +#define ZLIB_COMPRESSION 1
pankso@5245 552 +#define LZMA_COMPRESSION 2
pankso@5245 553 +#define LZO_COMPRESSION 3
pankso@5245 554
pankso@5245 555 struct squashfs_super_block {
pankso@5245 556 __le32 s_magic;
pankso@5245 557
pankso@5245 558 --- linux-2.6.30.6/fs/squashfs/squashfs_fs_sb.h
pankso@5245 559 +++ linux-2.6.30.6/fs/squashfs/squashfs_fs_sb.h
pankso@5245 560 @@ -52,25 +52,26 @@
pankso@5245 561 };
pankso@5245 562
pankso@5245 563 struct squashfs_sb_info {
pankso@5245 564 - int devblksize;
pankso@5245 565 - int devblksize_log2;
pankso@5245 566 - struct squashfs_cache *block_cache;
pankso@5245 567 - struct squashfs_cache *fragment_cache;
pankso@5245 568 - struct squashfs_cache *read_page;
pankso@5245 569 - int next_meta_index;
pankso@5245 570 - __le64 *id_table;
pankso@5245 571 - __le64 *fragment_index;
pankso@5245 572 - unsigned int *fragment_index_2;
pankso@5245 573 - struct mutex read_data_mutex;
pankso@5245 574 - struct mutex meta_index_mutex;
pankso@5245 575 - struct meta_index *meta_index;
pankso@5245 576 - z_stream stream;
pankso@5245 577 - __le64 *inode_lookup_table;
pankso@5245 578 - u64 inode_table;
pankso@5245 579 - u64 directory_table;
pankso@5245 580 - unsigned int block_size;
pankso@5245 581 - unsigned short block_log;
pankso@5245 582 - long long bytes_used;
pankso@5245 583 - unsigned int inodes;
pankso@5245 584 + const struct squashfs_decompressor *decompressor;
pankso@5245 585 + int devblksize;
pankso@5245 586 + int devblksize_log2;
pankso@5245 587 + struct squashfs_cache *block_cache;
pankso@5245 588 + struct squashfs_cache *fragment_cache;
pankso@5245 589 + struct squashfs_cache *read_page;
pankso@5245 590 + int next_meta_index;
pankso@5245 591 + __le64 *id_table;
pankso@5245 592 + __le64 *fragment_index;
pankso@5245 593 + unsigned int *fragment_index_2;
pankso@5245 594 + struct mutex read_data_mutex;
pankso@5245 595 + struct mutex meta_index_mutex;
pankso@5245 596 + struct meta_index *meta_index;
pankso@5245 597 + void *stream;
pankso@5245 598 + __le64 *inode_lookup_table;
pankso@5245 599 + u64 inode_table;
pankso@5245 600 + u64 directory_table;
pankso@5245 601 + unsigned int block_size;
pankso@5245 602 + unsigned short block_log;
pankso@5245 603 + long long bytes_used;
pankso@5245 604 + unsigned int inodes;
pankso@5245 605 };
pankso@5245 606 #endif
pankso@5245 607
pankso@5245 608 --- linux-2.6.30.6/fs/squashfs/super.c
pankso@5245 609 +++ linux-2.6.30.6/fs/squashfs/super.c
pankso@5245 610 @@ -30,38 +30,46 @@
pankso@5245 611 #include <linux/fs.h>
pankso@5245 612 #include <linux/vfs.h>
pankso@5245 613 #include <linux/slab.h>
pankso@5245 614 +#include <linux/smp_lock.h>
pankso@5245 615 #include <linux/mutex.h>
pankso@5245 616 #include <linux/pagemap.h>
pankso@5245 617 #include <linux/init.h>
pankso@5245 618 #include <linux/module.h>
pankso@5245 619 -#include <linux/zlib.h>
pankso@5245 620 #include <linux/magic.h>
pankso@5245 621
pankso@5245 622 #include "squashfs_fs.h"
pankso@5245 623 #include "squashfs_fs_sb.h"
pankso@5245 624 #include "squashfs_fs_i.h"
pankso@5245 625 #include "squashfs.h"
pankso@5245 626 +#include "decompressor.h"
pankso@5245 627
pankso@5245 628 static struct file_system_type squashfs_fs_type;
pankso@5245 629 -static struct super_operations squashfs_super_ops;
pankso@5245 630 +static const struct super_operations squashfs_super_ops;
pankso@5245 631
pankso@5245 632 -static int supported_squashfs_filesystem(short major, short minor, short comp)
pankso@5245 633 +static const struct squashfs_decompressor *supported_squashfs_filesystem(short
pankso@5245 634 + major, short minor, short id)
pankso@5245 635 {
pankso@5245 636 + const struct squashfs_decompressor *decompressor;
pankso@5245 637 +
pankso@5245 638 if (major < SQUASHFS_MAJOR) {
pankso@5245 639 ERROR("Major/Minor mismatch, older Squashfs %d.%d "
pankso@5245 640 "filesystems are unsupported\n", major, minor);
pankso@5245 641 - return -EINVAL;
pankso@5245 642 + return NULL;
pankso@5245 643 } else if (major > SQUASHFS_MAJOR || minor > SQUASHFS_MINOR) {
pankso@5245 644 ERROR("Major/Minor mismatch, trying to mount newer "
pankso@5245 645 "%d.%d filesystem\n", major, minor);
pankso@5245 646 ERROR("Please update your kernel\n");
pankso@5245 647 - return -EINVAL;
pankso@5245 648 + return NULL;
pankso@5245 649 }
pankso@5245 650
pankso@5245 651 - if (comp != ZLIB_COMPRESSION)
pankso@5245 652 - return -EINVAL;
pankso@5245 653 + decompressor = squashfs_lookup_decompressor(id);
pankso@5245 654 + if (!decompressor->supported) {
pankso@5245 655 + ERROR("Filesystem uses \"%s\" compression. This is not "
pankso@5245 656 + "supported\n", decompressor->name);
pankso@5245 657 + return NULL;
pankso@5245 658 + }
pankso@5245 659
pankso@5245 660 - return 0;
pankso@5245 661 + return decompressor;
pankso@5245 662 }
pankso@5245 663
pankso@5245 664
pankso@5245 665 @@ -86,13 +94,6 @@
pankso@5245 666 }
pankso@5245 667 msblk = sb->s_fs_info;
pankso@5245 668
pankso@5245 669 - msblk->stream.workspace = kmalloc(zlib_inflate_workspacesize(),
pankso@5245 670 - GFP_KERNEL);
pankso@5245 671 - if (msblk->stream.workspace == NULL) {
pankso@5245 672 - ERROR("Failed to allocate zlib workspace\n");
pankso@5245 673 - goto failure;
pankso@5245 674 - }
pankso@5245 675 -
pankso@5245 676 sblk = kzalloc(sizeof(*sblk), GFP_KERNEL);
pankso@5245 677 if (sblk == NULL) {
pankso@5245 678 ERROR("Failed to allocate squashfs_super_block\n");
pankso@5245 679 @@ -119,25 +120,25 @@
pankso@5245 680 goto failed_mount;
pankso@5245 681 }
pankso@5245 682
pankso@5245 683 + err = -EINVAL;
pankso@5245 684 +
pankso@5245 685 /* Check it is a SQUASHFS superblock */
pankso@5245 686 sb->s_magic = le32_to_cpu(sblk->s_magic);
pankso@5245 687 if (sb->s_magic != SQUASHFS_MAGIC) {
pankso@5245 688 if (!silent)
pankso@5245 689 ERROR("Can't find a SQUASHFS superblock on %s\n",
pankso@5245 690 bdevname(sb->s_bdev, b));
pankso@5245 691 - err = -EINVAL;
pankso@5245 692 goto failed_mount;
pankso@5245 693 }
pankso@5245 694
pankso@5245 695 - /* Check the MAJOR & MINOR versions and compression type */
pankso@5245 696 - err = supported_squashfs_filesystem(le16_to_cpu(sblk->s_major),
pankso@5245 697 + /* Check the MAJOR & MINOR versions and lookup compression type */
pankso@5245 698 + msblk->decompressor = supported_squashfs_filesystem(
pankso@5245 699 + le16_to_cpu(sblk->s_major),
pankso@5245 700 le16_to_cpu(sblk->s_minor),
pankso@5245 701 le16_to_cpu(sblk->compression));
pankso@5245 702 - if (err < 0)
pankso@5245 703 + if (msblk->decompressor == NULL)
pankso@5245 704 goto failed_mount;
pankso@5245 705
pankso@5245 706 - err = -EINVAL;
pankso@5245 707 -
pankso@5245 708 /*
pankso@5245 709 * Check if there's xattrs in the filesystem. These are not
pankso@5245 710 * supported in this version, so warn that they will be ignored.
pankso@5245 711 @@ -204,6 +205,10 @@
pankso@5245 712
pankso@5245 713 err = -ENOMEM;
pankso@5245 714
pankso@5245 715 + msblk->stream = squashfs_decompressor_init(msblk);
pankso@5245 716 + if (msblk->stream == NULL)
pankso@5245 717 + goto failed_mount;
pankso@5245 718 +
pankso@5245 719 msblk->block_cache = squashfs_cache_init("metadata",
pankso@5245 720 SQUASHFS_CACHED_BLKS, SQUASHFS_METADATA_SIZE);
pankso@5245 721 if (msblk->block_cache == NULL)
pankso@5245 722 @@ -291,17 +296,16 @@
pankso@5245 723 squashfs_cache_delete(msblk->block_cache);
pankso@5245 724 squashfs_cache_delete(msblk->fragment_cache);
pankso@5245 725 squashfs_cache_delete(msblk->read_page);
pankso@5245 726 + squashfs_decompressor_free(msblk, msblk->stream);
pankso@5245 727 kfree(msblk->inode_lookup_table);
pankso@5245 728 kfree(msblk->fragment_index);
pankso@5245 729 kfree(msblk->id_table);
pankso@5245 730 - kfree(msblk->stream.workspace);
pankso@5245 731 kfree(sb->s_fs_info);
pankso@5245 732 sb->s_fs_info = NULL;
pankso@5245 733 kfree(sblk);
pankso@5245 734 return err;
pankso@5245 735
pankso@5245 736 failure:
pankso@5245 737 - kfree(msblk->stream.workspace);
pankso@5245 738 kfree(sb->s_fs_info);
pankso@5245 739 sb->s_fs_info = NULL;
pankso@5245 740 return -ENOMEM;
pankso@5245 741 @@ -338,18 +342,22 @@
pankso@5245 742
pankso@5245 743 static void squashfs_put_super(struct super_block *sb)
pankso@5245 744 {
pankso@5245 745 + lock_kernel();
pankso@5245 746 +
pankso@5245 747 if (sb->s_fs_info) {
pankso@5245 748 struct squashfs_sb_info *sbi = sb->s_fs_info;
pankso@5245 749 squashfs_cache_delete(sbi->block_cache);
pankso@5245 750 squashfs_cache_delete(sbi->fragment_cache);
pankso@5245 751 squashfs_cache_delete(sbi->read_page);
pankso@5245 752 + squashfs_decompressor_free(sbi, sbi->stream);
pankso@5245 753 kfree(sbi->id_table);
pankso@5245 754 kfree(sbi->fragment_index);
pankso@5245 755 kfree(sbi->meta_index);
pankso@5245 756 - kfree(sbi->stream.workspace);
pankso@5245 757 kfree(sb->s_fs_info);
pankso@5245 758 sb->s_fs_info = NULL;
pankso@5245 759 }
pankso@5245 760 +
pankso@5245 761 + unlock_kernel();
pankso@5245 762 }
pankso@5245 763
pankso@5245 764
pankso@5245 765 @@ -439,7 +447,7 @@
pankso@5245 766 .fs_flags = FS_REQUIRES_DEV
pankso@5245 767 };
pankso@5245 768
pankso@5245 769 -static struct super_operations squashfs_super_ops = {
pankso@5245 770 +static const struct super_operations squashfs_super_ops = {
pankso@5245 771 .alloc_inode = squashfs_alloc_inode,
pankso@5245 772 .destroy_inode = squashfs_destroy_inode,
pankso@5245 773 .statfs = squashfs_statfs,
pankso@5245 774
pankso@5245 775 --- linux-2.6.30.6/fs/squashfs/symlink.c
pankso@5245 776 +++ linux-2.6.30.6/fs/squashfs/symlink.c
pankso@5245 777 @@ -36,7 +36,6 @@
pankso@5245 778 #include <linux/slab.h>
pankso@5245 779 #include <linux/string.h>
pankso@5245 780 #include <linux/pagemap.h>
pankso@5245 781 -#include <linux/zlib.h>
pankso@5245 782
pankso@5245 783 #include "squashfs_fs.h"
pankso@5245 784 #include "squashfs_fs_sb.h"
pankso@5245 785
pankso@5245 786 --- linux-2.6.30.6/fs/squashfs/zlib_wrapper.c
pankso@5245 787 +++ linux-2.6.30.6/fs/squashfs/zlib_wrapper.c
pankso@5245 788 @@ -0,0 +1,150 @@
pankso@5245 789 +/*
pankso@5245 790 + * Squashfs - a compressed read only filesystem for Linux
pankso@5245 791 + *
pankso@5245 792 + * Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
pankso@5245 793 + * Phillip Lougher <phillip@lougher.demon.co.uk>
pankso@5245 794 + *
pankso@5245 795 + * This program is free software; you can redistribute it and/or
pankso@5245 796 + * modify it under the terms of the GNU General Public License
pankso@5245 797 + * as published by the Free Software Foundation; either version 2,
pankso@5245 798 + * or (at your option) any later version.
pankso@5245 799 + *
pankso@5245 800 + * This program is distributed in the hope that it will be useful,
pankso@5245 801 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
pankso@5245 802 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
pankso@5245 803 + * GNU General Public License for more details.
pankso@5245 804 + *
pankso@5245 805 + * You should have received a copy of the GNU General Public License
pankso@5245 806 + * along with this program; if not, write to the Free Software
pankso@5245 807 + * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
pankso@5245 808 + *
pankso@5245 809 + * zlib_wrapper.c
pankso@5245 810 + */
pankso@5245 811 +
pankso@5245 812 +
pankso@5245 813 +#include <linux/mutex.h>
pankso@5245 814 +#include <linux/buffer_head.h>
pankso@5245 815 +#include <linux/zlib.h>
pankso@5245 816 +
pankso@5245 817 +#include "squashfs_fs.h"
pankso@5245 818 +#include "squashfs_fs_sb.h"
pankso@5245 819 +#include "squashfs_fs_i.h"
pankso@5245 820 +#include "squashfs.h"
pankso@5245 821 +#include "decompressor.h"
pankso@5245 822 +
pankso@5245 823 +static void *zlib_init(struct squashfs_sb_info *dummy)
pankso@5245 824 +{
pankso@5245 825 + z_stream *stream = kmalloc(sizeof(z_stream), GFP_KERNEL);
pankso@5245 826 + if (stream == NULL)
pankso@5245 827 + goto failed;
pankso@5245 828 + stream->workspace = kmalloc(zlib_inflate_workspacesize(),
pankso@5245 829 + GFP_KERNEL);
pankso@5245 830 + if (stream->workspace == NULL)
pankso@5245 831 + goto failed;
pankso@5245 832 +
pankso@5245 833 + return stream;
pankso@5245 834 +
pankso@5245 835 +failed:
pankso@5245 836 + ERROR("Failed to allocate zlib workspace\n");
pankso@5245 837 + kfree(stream);
pankso@5245 838 + return NULL;
pankso@5245 839 +}
pankso@5245 840 +
pankso@5245 841 +
pankso@5245 842 +static void zlib_free(void *strm)
pankso@5245 843 +{
pankso@5245 844 + z_stream *stream = strm;
pankso@5245 845 +
pankso@5245 846 + if (stream)
pankso@5245 847 + kfree(stream->workspace);
pankso@5245 848 + kfree(stream);
pankso@5245 849 +}
pankso@5245 850 +
pankso@5245 851 +
pankso@5245 852 +static int zlib_uncompress(struct squashfs_sb_info *msblk, void **buffer,
pankso@5245 853 + struct buffer_head **bh, int b, int offset, int length, int srclength,
pankso@5245 854 + int pages)
pankso@5245 855 +{
pankso@5245 856 + int zlib_err = 0, zlib_init = 0;
pankso@5245 857 + int avail, bytes, k = 0, page = 0;
pankso@5245 858 + z_stream *stream = msblk->stream;
pankso@5245 859 +
pankso@5245 860 + mutex_lock(&msblk->read_data_mutex);
pankso@5245 861 +
pankso@5245 862 + stream->avail_out = 0;
pankso@5245 863 + stream->avail_in = 0;
pankso@5245 864 +
pankso@5245 865 + bytes = length;
pankso@5245 866 + do {
pankso@5245 867 + if (stream->avail_in == 0 && k < b) {
pankso@5245 868 + avail = min(bytes, msblk->devblksize - offset);
pankso@5245 869 + bytes -= avail;
pankso@5245 870 + wait_on_buffer(bh[k]);
pankso@5245 871 + if (!buffer_uptodate(bh[k]))
pankso@5245 872 + goto release_mutex;
pankso@5245 873 +
pankso@5245 874 + if (avail == 0) {
pankso@5245 875 + offset = 0;
pankso@5245 876 + put_bh(bh[k++]);
pankso@5245 877 + continue;
pankso@5245 878 + }
pankso@5245 879 +
pankso@5245 880 + stream->next_in = bh[k]->b_data + offset;
pankso@5245 881 + stream->avail_in = avail;
pankso@5245 882 + offset = 0;
pankso@5245 883 + }
pankso@5245 884 +
pankso@5245 885 + if (stream->avail_out == 0 && page < pages) {
pankso@5245 886 + stream->next_out = buffer[page++];
pankso@5245 887 + stream->avail_out = PAGE_CACHE_SIZE;
pankso@5245 888 + }
pankso@5245 889 +
pankso@5245 890 + if (!zlib_init) {
pankso@5245 891 + zlib_err = zlib_inflateInit(stream);
pankso@5245 892 + if (zlib_err != Z_OK) {
pankso@5245 893 + ERROR("zlib_inflateInit returned unexpected "
pankso@5245 894 + "result 0x%x, srclength %d\n",
pankso@5245 895 + zlib_err, srclength);
pankso@5245 896 + goto release_mutex;
pankso@5245 897 + }
pankso@5245 898 + zlib_init = 1;
pankso@5245 899 + }
pankso@5245 900 +
pankso@5245 901 + zlib_err = zlib_inflate(stream, Z_SYNC_FLUSH);
pankso@5245 902 +
pankso@5245 903 + if (stream->avail_in == 0 && k < b)
pankso@5245 904 + put_bh(bh[k++]);
pankso@5245 905 + } while (zlib_err == Z_OK);
pankso@5245 906 +
pankso@5245 907 + if (zlib_err != Z_STREAM_END) {
pankso@5245 908 + ERROR("zlib_inflate error, data probably corrupt\n");
pankso@5245 909 + goto release_mutex;
pankso@5245 910 + }
pankso@5245 911 +
pankso@5245 912 + zlib_err = zlib_inflateEnd(stream);
pankso@5245 913 + if (zlib_err != Z_OK) {
pankso@5245 914 + ERROR("zlib_inflate error, data probably corrupt\n");
pankso@5245 915 + goto release_mutex;
pankso@5245 916 + }
pankso@5245 917 +
pankso@5245 918 + mutex_unlock(&msblk->read_data_mutex);
pankso@5245 919 + return stream->total_out;
pankso@5245 920 +
pankso@5245 921 +release_mutex:
pankso@5245 922 + mutex_unlock(&msblk->read_data_mutex);
pankso@5245 923 +
pankso@5245 924 + for (; k < b; k++)
pankso@5245 925 + put_bh(bh[k]);
pankso@5245 926 +
pankso@5245 927 + return -EIO;
pankso@5245 928 +}
pankso@5245 929 +
pankso@5245 930 +const struct squashfs_decompressor squashfs_zlib_comp_ops = {
pankso@5245 931 + .init = zlib_init,
pankso@5245 932 + .free = zlib_free,
pankso@5245 933 + .decompress = zlib_uncompress,
pankso@5245 934 + .id = ZLIB_COMPRESSION,
pankso@5245 935 + .name = "zlib",
pankso@5245 936 + .supported = 1
pankso@5245 937 +};
pankso@5245 938 +
pankso@5245 939
pankso@5245 940 --- linux-2.6.30.6/include/linux/decompress/bunzip2_mm.h
pankso@5245 941 +++ linux-2.6.30.6/include/linux/decompress/bunzip2_mm.h
pankso@5245 942 @@ -0,0 +1,13 @@
pankso@5245 943 +#ifndef BUNZIP2_MM_H
pankso@5245 944 +#define BUNZIP2_MM_H
pankso@5245 945 +
pankso@5245 946 +#ifdef STATIC
pankso@5245 947 +/* Code active when included from pre-boot environment: */
pankso@5245 948 +#define INIT
pankso@5245 949 +#else
pankso@5245 950 +/* Compile for initramfs/initrd code only */
pankso@5245 951 +#define INIT __init
pankso@5245 952 +static void(*error)(char *m);
pankso@5245 953 +#endif
pankso@5245 954 +
pankso@5245 955 +#endif
pankso@5245 956
pankso@5245 957 --- linux-2.6.30.6/include/linux/decompress/inflate_mm.h
pankso@5245 958 +++ linux-2.6.30.6/include/linux/decompress/inflate_mm.h
pankso@5245 959 @@ -0,0 +1,13 @@
pankso@5245 960 +#ifndef INFLATE_MM_H
pankso@5245 961 +#define INFLATE_MM_H
pankso@5245 962 +
pankso@5245 963 +#ifdef STATIC
pankso@5245 964 +/* Code active when included from pre-boot environment: */
pankso@5245 965 +#define INIT
pankso@5245 966 +#else
pankso@5245 967 +/* Compile for initramfs/initrd code only */
pankso@5245 968 +#define INIT __init
pankso@5245 969 +static void(*error)(char *m);
pankso@5245 970 +#endif
pankso@5245 971 +
pankso@5245 972 +#endif
pankso@5245 973
pankso@5245 974 --- linux-2.6.30.6/include/linux/decompress/mm.h
pankso@5245 975 +++ linux-2.6.30.6/include/linux/decompress/mm.h
pankso@5245 976 @@ -25,7 +25,7 @@
pankso@5245 977 void *p;
pankso@5245 978
pankso@5245 979 if (size < 0)
pankso@5245 980 - error("Malloc error");
pankso@5245 981 + return NULL;
pankso@5245 982 if (!malloc_ptr)
pankso@5245 983 malloc_ptr = free_mem_ptr;
pankso@5245 984
pankso@5245 985 @@ -35,7 +35,7 @@
pankso@5245 986 malloc_ptr += size;
pankso@5245 987
pankso@5245 988 if (free_mem_end_ptr && malloc_ptr >= free_mem_end_ptr)
pankso@5245 989 - error("Out of memory");
pankso@5245 990 + return NULL;
pankso@5245 991
pankso@5245 992 malloc_count++;
pankso@5245 993 return p;
pankso@5245 994 @@ -53,8 +53,6 @@
pankso@5245 995
pankso@5245 996 #define set_error_fn(x)
pankso@5245 997
pankso@5245 998 -#define INIT
pankso@5245 999 -
pankso@5245 1000 #else /* STATIC */
pankso@5245 1001
pankso@5245 1002 /* Code active when compiled standalone for use when loading ramdisk: */
pankso@5245 1003 @@ -74,10 +72,8 @@
pankso@5245 1004 #define large_malloc(a) vmalloc(a)
pankso@5245 1005 #define large_free(a) vfree(a)
pankso@5245 1006
pankso@5245 1007 -static void(*error)(char *m);
pankso@5245 1008 #define set_error_fn(x) error = x;
pankso@5245 1009
pankso@5245 1010 -#define INIT __init
pankso@5245 1011 #define STATIC
pankso@5245 1012
pankso@5245 1013 #include <linux/init.h>
pankso@5245 1014
pankso@5245 1015 --- linux-2.6.30.6/include/linux/decompress/unlzma_mm.h
pankso@5245 1016 +++ linux-2.6.30.6/include/linux/decompress/unlzma_mm.h
pankso@5245 1017 @@ -0,0 +1,20 @@
pankso@5245 1018 +#ifndef UNLZMA_MM_H
pankso@5245 1019 +#define UNLZMA_MM_H
pankso@5245 1020 +
pankso@5245 1021 +#ifdef STATIC
pankso@5245 1022 +
pankso@5245 1023 +/* Code active when included from pre-boot environment: */
pankso@5245 1024 +#define INIT
pankso@5245 1025 +
pankso@5245 1026 +#elif defined(CONFIG_DECOMPRESS_LZMA_NEEDED)
pankso@5245 1027 +
pankso@5245 1028 +/* Make it available to non initramfs/initrd code */
pankso@5245 1029 +#define INIT
pankso@5245 1030 +#include <linux/module.h>
pankso@5245 1031 +#else
pankso@5245 1032 +
pankso@5245 1033 +/* Compile for initramfs/initrd code only */
pankso@5245 1034 +#define INIT __init
pankso@5245 1035 +#endif
pankso@5245 1036 +
pankso@5245 1037 +#endif
pankso@5245 1038
pankso@5245 1039 --- linux-2.6.30.6/lib/Kconfig
pankso@5245 1040 +++ linux-2.6.30.6/lib/Kconfig
pankso@5245 1041 @@ -10,6 +10,9 @@
pankso@5245 1042 config BITREVERSE
pankso@5245 1043 tristate
pankso@5245 1044
pankso@5245 1045 +config RATIONAL
pankso@5245 1046 + boolean
pankso@5245 1047 +
pankso@5245 1048 config GENERIC_FIND_FIRST_BIT
pankso@5245 1049 bool
pankso@5245 1050
pankso@5245 1051 @@ -114,6 +117,9 @@
pankso@5245 1052 config DECOMPRESS_LZMA
pankso@5245 1053 tristate
pankso@5245 1054
pankso@5245 1055 +config DECOMPRESS_LZMA_NEEDED
pankso@5245 1056 + boolean
pankso@5245 1057 +
pankso@5245 1058 #
pankso@5245 1059 # Generic allocator support is selected if needed
pankso@5245 1060 #
pankso@5245 1061 @@ -153,6 +159,9 @@
pankso@5245 1062 config TEXTSEARCH_FSM
pankso@5245 1063 tristate
pankso@5245 1064
pankso@5245 1065 +config BTREE
pankso@5245 1066 + boolean
pankso@5245 1067 +
pankso@5245 1068 config HAS_IOMEM
pankso@5245 1069 boolean
pankso@5245 1070 depends on !NO_IOMEM
pankso@5245 1071 @@ -190,5 +199,35 @@
pankso@5245 1072 #
pankso@5245 1073 config NLATTR
pankso@5245 1074 bool
pankso@5245 1075 +
pankso@5245 1076 +#
pankso@5245 1077 +# Generic 64-bit atomic support is selected if needed
pankso@5245 1078 +#
pankso@5245 1079 +config GENERIC_ATOMIC64
pankso@5245 1080 + bool
pankso@5245 1081 +
pankso@5245 1082 +config LRU_CACHE
pankso@5245 1083 + tristate
pankso@5245 1084 +
pankso@5245 1085 +config SHM_SIGNAL
pankso@5245 1086 + tristate "SHM Signal - Generic shared-memory signaling mechanism"
pankso@5245 1087 + default n
pankso@5245 1088 + help
pankso@5245 1089 + Provides a shared-memory based signaling mechanism to indicate
pankso@5245 1090 + memory-dirty notifications between two end-points.
pankso@5245 1091 +
pankso@5245 1092 + If unsure, say N
pankso@5245 1093 +
pankso@5245 1094 +config IOQ
pankso@5245 1095 + tristate "IO-Queue library - Generic shared-memory queue"
pankso@5245 1096 + select SHM_SIGNAL
pankso@5245 1097 + default n
pankso@5245 1098 + help
pankso@5245 1099 + IOQ is a generic shared-memory-queue mechanism that happens to be
pankso@5245 1100 + friendly to virtualization boundaries. It can be used in a variety
pankso@5245 1101 + of ways, though its intended purpose is to become a low-level
pankso@5245 1102 + communication path for paravirtualized drivers.
pankso@5245 1103 +
pankso@5245 1104 + If unsure, say N
pankso@5245 1105
pankso@5245 1106 endmenu
pankso@5245 1107
pankso@5245 1108 --- linux-2.6.30.6/lib/decompress_bunzip2.c
pankso@5245 1109 +++ linux-2.6.30.6/lib/decompress_bunzip2.c
pankso@5245 1110 @@ -45,12 +45,15 @@
pankso@5245 1111 */
pankso@5245 1112
pankso@5245 1113
pankso@5245 1114 -#ifndef STATIC
pankso@5245 1115 +#ifdef STATIC
pankso@5245 1116 +#define PREBOOT
pankso@5245 1117 +#else
pankso@5245 1118 #include <linux/decompress/bunzip2.h>
pankso@5245 1119 -#endif /* !STATIC */
pankso@5245 1120 +#include <linux/slab.h>
pankso@5245 1121 +#endif /* STATIC */
pankso@5245 1122
pankso@5245 1123 +#include <linux/decompress/bunzip2_mm.h>
pankso@5245 1124 #include <linux/decompress/mm.h>
pankso@5245 1125 -#include <linux/slab.h>
pankso@5245 1126
pankso@5245 1127 #ifndef INT_MAX
pankso@5245 1128 #define INT_MAX 0x7fffffff
pankso@5245 1129 @@ -297,7 +300,7 @@
pankso@5245 1130 again when using them (during symbol decoding).*/
pankso@5245 1131 base = hufGroup->base-1;
pankso@5245 1132 limit = hufGroup->limit-1;
pankso@5245 1133 - /* Calculate permute[]. Concurently, initialize
pankso@5245 1134 + /* Calculate permute[]. Concurrently, initialize
pankso@5245 1135 * temp[] and limit[]. */
pankso@5245 1136 pp = 0;
pankso@5245 1137 for (i = minLen; i <= maxLen; i++) {
pankso@5245 1138 @@ -635,6 +638,8 @@
pankso@5245 1139
pankso@5245 1140 /* Allocate bunzip_data. Most fields initialize to zero. */
pankso@5245 1141 bd = *bdp = malloc(i);
pankso@5245 1142 + if (!bd)
pankso@5245 1143 + return RETVAL_OUT_OF_MEMORY;
pankso@5245 1144 memset(bd, 0, sizeof(struct bunzip_data));
pankso@5245 1145 /* Setup input buffer */
pankso@5245 1146 bd->inbuf = inbuf;
pankso@5245 1147 @@ -662,6 +667,8 @@
pankso@5245 1148 bd->dbufSize = 100000*(i-BZh0);
pankso@5245 1149
pankso@5245 1150 bd->dbuf = large_malloc(bd->dbufSize * sizeof(int));
pankso@5245 1151 + if (!bd->dbuf)
pankso@5245 1152 + return RETVAL_OUT_OF_MEMORY;
pankso@5245 1153 return RETVAL_OK;
pankso@5245 1154 }
pankso@5245 1155
pankso@5245 1156 @@ -681,12 +688,10 @@
pankso@5245 1157 set_error_fn(error_fn);
pankso@5245 1158 if (flush)
pankso@5245 1159 outbuf = malloc(BZIP2_IOBUF_SIZE);
pankso@5245 1160 - else
pankso@5245 1161 - len -= 4; /* Uncompressed size hack active in pre-boot
pankso@5245 1162 - environment */
pankso@5245 1163 +
pankso@5245 1164 if (!outbuf) {
pankso@5245 1165 error("Could not allocate output bufer");
pankso@5245 1166 - return -1;
pankso@5245 1167 + return RETVAL_OUT_OF_MEMORY;
pankso@5245 1168 }
pankso@5245 1169 if (buf)
pankso@5245 1170 inbuf = buf;
pankso@5245 1171 @@ -694,6 +699,7 @@
pankso@5245 1172 inbuf = malloc(BZIP2_IOBUF_SIZE);
pankso@5245 1173 if (!inbuf) {
pankso@5245 1174 error("Could not allocate input bufer");
pankso@5245 1175 + i = RETVAL_OUT_OF_MEMORY;
pankso@5245 1176 goto exit_0;
pankso@5245 1177 }
pankso@5245 1178 i = start_bunzip(&bd, inbuf, len, fill);
pankso@5245 1179 @@ -720,11 +726,14 @@
pankso@5245 1180 } else if (i == RETVAL_UNEXPECTED_OUTPUT_EOF) {
pankso@5245 1181 error("Compressed file ends unexpectedly");
pankso@5245 1182 }
pankso@5245 1183 + if (!bd)
pankso@5245 1184 + goto exit_1;
pankso@5245 1185 if (bd->dbuf)
pankso@5245 1186 large_free(bd->dbuf);
pankso@5245 1187 if (pos)
pankso@5245 1188 *pos = bd->inbufPos;
pankso@5245 1189 free(bd);
pankso@5245 1190 +exit_1:
pankso@5245 1191 if (!buf)
pankso@5245 1192 free(inbuf);
pankso@5245 1193 exit_0:
pankso@5245 1194 @@ -733,4 +742,14 @@
pankso@5245 1195 return i;
pankso@5245 1196 }
pankso@5245 1197
pankso@5245 1198 -#define decompress bunzip2
pankso@5245 1199 +#ifdef PREBOOT
pankso@5245 1200 +STATIC int INIT decompress(unsigned char *buf, int len,
pankso@5245 1201 + int(*fill)(void*, unsigned int),
pankso@5245 1202 + int(*flush)(void*, unsigned int),
pankso@5245 1203 + unsigned char *outbuf,
pankso@5245 1204 + int *pos,
pankso@5245 1205 + void(*error_fn)(char *x))
pankso@5245 1206 +{
pankso@5245 1207 + return bunzip2(buf, len - 4, fill, flush, outbuf, pos, error_fn);
pankso@5245 1208 +}
pankso@5245 1209 +#endif
pankso@5245 1210
pankso@5245 1211 --- linux-2.6.30.6/lib/decompress_inflate.c
pankso@5245 1212 +++ linux-2.6.30.6/lib/decompress_inflate.c
pankso@5245 1213 @@ -19,14 +19,20 @@
pankso@5245 1214 #include "zlib_inflate/inflate.h"
pankso@5245 1215
pankso@5245 1216 #include "zlib_inflate/infutil.h"
pankso@5245 1217 +#include <linux/slab.h>
pankso@5245 1218
pankso@5245 1219 #endif /* STATIC */
pankso@5245 1220
pankso@5245 1221 +#include <linux/decompress/inflate_mm.h>
pankso@5245 1222 #include <linux/decompress/mm.h>
pankso@5245 1223 -#include <linux/slab.h>
pankso@5245 1224
pankso@5245 1225 -#define INBUF_LEN (16*1024)
pankso@5245 1226 +#define GZIP_IOBUF_SIZE (16*1024)
pankso@5245 1227
pankso@5245 1228 +static int nofill(void *buffer, unsigned int len)
pankso@5245 1229 +{
pankso@5245 1230 + return -1;
pankso@5245 1231 +}
pankso@5245 1232 +
pankso@5245 1233 /* Included from initramfs et al code */
pankso@5245 1234 STATIC int INIT gunzip(unsigned char *buf, int len,
pankso@5245 1235 int(*fill)(void*, unsigned int),
pankso@5245 1236 @@ -55,7 +61,7 @@
pankso@5245 1237 if (buf)
pankso@5245 1238 zbuf = buf;
pankso@5245 1239 else {
pankso@5245 1240 - zbuf = malloc(INBUF_LEN);
pankso@5245 1241 + zbuf = malloc(GZIP_IOBUF_SIZE);
pankso@5245 1242 len = 0;
pankso@5245 1243 }
pankso@5245 1244 if (!zbuf) {
pankso@5245 1245 @@ -76,8 +82,11 @@
pankso@5245 1246 goto gunzip_nomem4;
pankso@5245 1247 }
pankso@5245 1248
pankso@5245 1249 + if (!fill)
pankso@5245 1250 + fill = nofill;
pankso@5245 1251 +
pankso@5245 1252 if (len == 0)
pankso@5245 1253 - len = fill(zbuf, INBUF_LEN);
pankso@5245 1254 + len = fill(zbuf, GZIP_IOBUF_SIZE);
pankso@5245 1255
pankso@5245 1256 /* verify the gzip header */
pankso@5245 1257 if (len < 10 ||
pankso@5245 1258 @@ -113,7 +122,7 @@
pankso@5245 1259 while (rc == Z_OK) {
pankso@5245 1260 if (strm->avail_in == 0) {
pankso@5245 1261 /* TODO: handle case where both pos and fill are set */
pankso@5245 1262 - len = fill(zbuf, INBUF_LEN);
pankso@5245 1263 + len = fill(zbuf, GZIP_IOBUF_SIZE);
pankso@5245 1264 if (len < 0) {
pankso@5245 1265 rc = -1;
pankso@5245 1266 error("read error");
pankso@5245 1267
pankso@5245 1268 --- linux-2.6.30.6/lib/decompress_unlzma.c
pankso@5245 1269 +++ linux-2.6.30.6/lib/decompress_unlzma.c
pankso@5245 1270 @@ -29,12 +29,15 @@
pankso@5245 1271 *Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
pankso@5245 1272 */
pankso@5245 1273
pankso@5245 1274 -#ifndef STATIC
pankso@5245 1275 +#ifdef STATIC
pankso@5245 1276 +#define PREBOOT
pankso@5245 1277 +#else
pankso@5245 1278 #include <linux/decompress/unlzma.h>
pankso@5245 1279 +#include <linux/slab.h>
pankso@5245 1280 #endif /* STATIC */
pankso@5245 1281
pankso@5245 1282 +#include <linux/decompress/unlzma_mm.h>
pankso@5245 1283 #include <linux/decompress/mm.h>
pankso@5245 1284 -#include <linux/slab.h>
pankso@5245 1285
pankso@5245 1286 #define MIN(a, b) (((a) < (b)) ? (a) : (b))
pankso@5245 1287
pankso@5245 1288 @@ -80,8 +83,13 @@
pankso@5245 1289 #define RC_MODEL_TOTAL_BITS 11
pankso@5245 1290
pankso@5245 1291
pankso@5245 1292 +static int nofill(void *buffer, unsigned int len)
pankso@5245 1293 +{
pankso@5245 1294 + return -1;
pankso@5245 1295 +}
pankso@5245 1296 +
pankso@5245 1297 /* Called twice: once at startup and once in rc_normalize() */
pankso@5245 1298 -static void INIT rc_read(struct rc *rc)
pankso@5245 1299 +static void INIT rc_read(struct rc *rc, void(*error)(char *x))
pankso@5245 1300 {
pankso@5245 1301 rc->buffer_size = rc->fill((char *)rc->buffer, LZMA_IOBUF_SIZE);
pankso@5245 1302 if (rc->buffer_size <= 0)
pankso@5245 1303 @@ -95,7 +103,10 @@
pankso@5245 1304 int (*fill)(void*, unsigned int),
pankso@5245 1305 char *buffer, int buffer_size)
pankso@5245 1306 {
pankso@5245 1307 - rc->fill = fill;
pankso@5245 1308 + if (fill)
pankso@5245 1309 + rc->fill = fill;
pankso@5245 1310 + else
pankso@5245 1311 + rc->fill = nofill;
pankso@5245 1312 rc->buffer = (uint8_t *)buffer;
pankso@5245 1313 rc->buffer_size = buffer_size;
pankso@5245 1314 rc->buffer_end = rc->buffer + rc->buffer_size;
pankso@5245 1315 @@ -105,13 +116,13 @@
pankso@5245 1316 rc->range = 0xFFFFFFFF;
pankso@5245 1317 }
pankso@5245 1318
pankso@5245 1319 -static inline void INIT rc_init_code(struct rc *rc)
pankso@5245 1320 +static inline void INIT rc_init_code(struct rc *rc, void(*error)(char *x))
pankso@5245 1321 {
pankso@5245 1322 int i;
pankso@5245 1323
pankso@5245 1324 for (i = 0; i < 5; i++) {
pankso@5245 1325 if (rc->ptr >= rc->buffer_end)
pankso@5245 1326 - rc_read(rc);
pankso@5245 1327 + rc_read(rc, error);
pankso@5245 1328 rc->code = (rc->code << 8) | *rc->ptr++;
pankso@5245 1329 }
pankso@5245 1330 }
pankso@5245 1331 @@ -124,32 +135,33 @@
pankso@5245 1332 }
pankso@5245 1333
pankso@5245 1334 /* Called twice, but one callsite is in inline'd rc_is_bit_0_helper() */
pankso@5245 1335 -static void INIT rc_do_normalize(struct rc *rc)
pankso@5245 1336 +static void INIT rc_do_normalize(struct rc *rc, void(*error)(char *x))
pankso@5245 1337 {
pankso@5245 1338 if (rc->ptr >= rc->buffer_end)
pankso@5245 1339 - rc_read(rc);
pankso@5245 1340 + rc_read(rc, error);
pankso@5245 1341 rc->range <<= 8;
pankso@5245 1342 rc->code = (rc->code << 8) | *rc->ptr++;
pankso@5245 1343 }
pankso@5245 1344 -static inline void INIT rc_normalize(struct rc *rc)
pankso@5245 1345 +static inline void INIT rc_normalize(struct rc *rc, void(*error)(char *x))
pankso@5245 1346 {
pankso@5245 1347 if (rc->range < (1 << RC_TOP_BITS))
pankso@5245 1348 - rc_do_normalize(rc);
pankso@5245 1349 + rc_do_normalize(rc, error);
pankso@5245 1350 }
pankso@5245 1351
pankso@5245 1352 /* Called 9 times */
pankso@5245 1353 /* Why rc_is_bit_0_helper exists?
pankso@5245 1354 *Because we want to always expose (rc->code < rc->bound) to optimizer
pankso@5245 1355 */
pankso@5245 1356 -static inline uint32_t INIT rc_is_bit_0_helper(struct rc *rc, uint16_t *p)
pankso@5245 1357 +static inline uint32_t INIT rc_is_bit_0_helper(struct rc *rc, uint16_t *p,
pankso@5245 1358 + void (*error)(char *x))
pankso@5245 1359 {
pankso@5245 1360 - rc_normalize(rc);
pankso@5245 1361 + rc_normalize(rc, error);
pankso@5245 1362 rc->bound = *p * (rc->range >> RC_MODEL_TOTAL_BITS);
pankso@5245 1363 return rc->bound;
pankso@5245 1364 }
pankso@5245 1365 -static inline int INIT rc_is_bit_0(struct rc *rc, uint16_t *p)
pankso@5245 1366 +static inline int INIT rc_is_bit_0(struct rc *rc, uint16_t *p, void(*error)(char *x))
pankso@5245 1367 {
pankso@5245 1368 - uint32_t t = rc_is_bit_0_helper(rc, p);
pankso@5245 1369 + uint32_t t = rc_is_bit_0_helper(rc, p, error);
pankso@5245 1370 return rc->code < t;
pankso@5245 1371 }
pankso@5245 1372
pankso@5245 1373 @@ -167,9 +179,9 @@
pankso@5245 1374 }
pankso@5245 1375
pankso@5245 1376 /* Called 4 times in unlzma loop */
pankso@5245 1377 -static int INIT rc_get_bit(struct rc *rc, uint16_t *p, int *symbol)
pankso@5245 1378 +static int INIT rc_get_bit(struct rc *rc, uint16_t *p, int *symbol, void(*error)(char *x))
pankso@5245 1379 {
pankso@5245 1380 - if (rc_is_bit_0(rc, p)) {
pankso@5245 1381 + if (rc_is_bit_0(rc, p, error)) {
pankso@5245 1382 rc_update_bit_0(rc, p);
pankso@5245 1383 *symbol *= 2;
pankso@5245 1384 return 0;
pankso@5245 1385 @@ -181,9 +193,9 @@
pankso@5245 1386 }
pankso@5245 1387
pankso@5245 1388 /* Called once */
pankso@5245 1389 -static inline int INIT rc_direct_bit(struct rc *rc)
pankso@5245 1390 +static inline int INIT rc_direct_bit(struct rc *rc , void(*error)(char *x))
pankso@5245 1391 {
pankso@5245 1392 - rc_normalize(rc);
pankso@5245 1393 + rc_normalize(rc, error);
pankso@5245 1394 rc->range >>= 1;
pankso@5245 1395 if (rc->code >= rc->range) {
pankso@5245 1396 rc->code -= rc->range;
pankso@5245 1397 @@ -194,13 +206,14 @@
pankso@5245 1398
pankso@5245 1399 /* Called twice */
pankso@5245 1400 static inline void INIT
pankso@5245 1401 -rc_bit_tree_decode(struct rc *rc, uint16_t *p, int num_levels, int *symbol)
pankso@5245 1402 +rc_bit_tree_decode(struct rc *rc, uint16_t *p, int num_levels, int *symbol,
pankso@5245 1403 + void(*error)(char *x))
pankso@5245 1404 {
pankso@5245 1405 int i = num_levels;
pankso@5245 1406
pankso@5245 1407 *symbol = 1;
pankso@5245 1408 while (i--)
pankso@5245 1409 - rc_get_bit(rc, p + *symbol, symbol);
pankso@5245 1410 + rc_get_bit(rc, p + *symbol, symbol, error);
pankso@5245 1411 *symbol -= 1 << num_levels;
pankso@5245 1412 }
pankso@5245 1413
pankso@5245 1414 @@ -396,7 +409,8 @@
pankso@5245 1415 static inline void INIT process_bit0(struct writer *wr, struct rc *rc,
pankso@5245 1416 struct cstate *cst, uint16_t *p,
pankso@5245 1417 int pos_state, uint16_t *prob,
pankso@5245 1418 - int lc, uint32_t literal_pos_mask) {
pankso@5245 1419 + int lc, uint32_t literal_pos_mask,
pankso@5245 1420 + void(*error)(char *x)) {
pankso@5245 1421 int mi = 1;
pankso@5245 1422 static const int state[LZMA_NUM_STATES] =
pankso@5245 1423 { 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 4, 5 };
pankso@5245 1424 @@ -417,7 +431,7 @@
pankso@5245 1425 match_byte <<= 1;
pankso@5245 1426 bit = match_byte & 0x100;
pankso@5245 1427 prob_lit = prob + 0x100 + bit + mi;
pankso@5245 1428 - if (rc_get_bit(rc, prob_lit, &mi)) {
pankso@5245 1429 + if (rc_get_bit(rc, prob_lit, &mi, error)) {
pankso@5245 1430 if (!bit)
pankso@5245 1431 break;
pankso@5245 1432 } else {
pankso@5245 1433 @@ -428,7 +442,7 @@
pankso@5245 1434 }
pankso@5245 1435 while (mi < 0x100) {
pankso@5245 1436 uint16_t *prob_lit = prob + mi;
pankso@5245 1437 - rc_get_bit(rc, prob_lit, &mi);
pankso@5245 1438 + rc_get_bit(rc, prob_lit, &mi, error);
pankso@5245 1439 }
pankso@5245 1440 write_byte(wr, mi);
pankso@5245 1441 cst->state = state[cst->state];
pankso@5245 1442 @@ -436,7 +450,8 @@
pankso@5245 1443
pankso@5245 1444 static inline void INIT process_bit1(struct writer *wr, struct rc *rc,
pankso@5245 1445 struct cstate *cst, uint16_t *p,
pankso@5245 1446 - int pos_state, uint16_t *prob) {
pankso@5245 1447 + int pos_state, uint16_t *prob,
pankso@5245 1448 + void(*error)(char *x)) {
pankso@5245 1449 int offset;
pankso@5245 1450 uint16_t *prob_len;
pankso@5245 1451 int num_bits;
pankso@5245 1452 @@ -444,7 +459,7 @@
pankso@5245 1453
pankso@5245 1454 rc_update_bit_1(rc, prob);
pankso@5245 1455 prob = p + LZMA_IS_REP + cst->state;
pankso@5245 1456 - if (rc_is_bit_0(rc, prob)) {
pankso@5245 1457 + if (rc_is_bit_0(rc, prob, error)) {
pankso@5245 1458 rc_update_bit_0(rc, prob);
pankso@5245 1459 cst->rep3 = cst->rep2;
pankso@5245 1460 cst->rep2 = cst->rep1;
pankso@5245 1461 @@ -454,13 +469,13 @@
pankso@5245 1462 } else {
pankso@5245 1463 rc_update_bit_1(rc, prob);
pankso@5245 1464 prob += LZMA_IS_REP_G0 - LZMA_IS_REP;
pankso@5245 1465 - if (rc_is_bit_0(rc, prob)) {
pankso@5245 1466 + if (rc_is_bit_0(rc, prob, error)) {
pankso@5245 1467 rc_update_bit_0(rc, prob);
pankso@5245 1468 prob = (p + LZMA_IS_REP_0_LONG
pankso@5245 1469 + (cst->state <<
pankso@5245 1470 LZMA_NUM_POS_BITS_MAX) +
pankso@5245 1471 pos_state);
pankso@5245 1472 - if (rc_is_bit_0(rc, prob)) {
pankso@5245 1473 + if (rc_is_bit_0(rc, prob, error)) {
pankso@5245 1474 rc_update_bit_0(rc, prob);
pankso@5245 1475
pankso@5245 1476 cst->state = cst->state < LZMA_NUM_LIT_STATES ?
pankso@5245 1477 @@ -475,13 +490,13 @@
pankso@5245 1478
pankso@5245 1479 rc_update_bit_1(rc, prob);
pankso@5245 1480 prob += LZMA_IS_REP_G1 - LZMA_IS_REP_G0;
pankso@5245 1481 - if (rc_is_bit_0(rc, prob)) {
pankso@5245 1482 + if (rc_is_bit_0(rc, prob, error)) {
pankso@5245 1483 rc_update_bit_0(rc, prob);
pankso@5245 1484 distance = cst->rep1;
pankso@5245 1485 } else {
pankso@5245 1486 rc_update_bit_1(rc, prob);
pankso@5245 1487 prob += LZMA_IS_REP_G2 - LZMA_IS_REP_G1;
pankso@5245 1488 - if (rc_is_bit_0(rc, prob)) {
pankso@5245 1489 + if (rc_is_bit_0(rc, prob, error)) {
pankso@5245 1490 rc_update_bit_0(rc, prob);
pankso@5245 1491 distance = cst->rep2;
pankso@5245 1492 } else {
pankso@5245 1493 @@ -499,7 +514,7 @@
pankso@5245 1494 }
pankso@5245 1495
pankso@5245 1496 prob_len = prob + LZMA_LEN_CHOICE;
pankso@5245 1497 - if (rc_is_bit_0(rc, prob_len)) {
pankso@5245 1498 + if (rc_is_bit_0(rc, prob_len, error)) {
pankso@5245 1499 rc_update_bit_0(rc, prob_len);
pankso@5245 1500 prob_len += LZMA_LEN_LOW - LZMA_LEN_CHOICE
pankso@5245 1501 + (pos_state <<
pankso@5245 1502 @@ -509,7 +524,7 @@
pankso@5245 1503 } else {
pankso@5245 1504 rc_update_bit_1(rc, prob_len);
pankso@5245 1505 prob_len += LZMA_LEN_CHOICE_2 - LZMA_LEN_CHOICE;
pankso@5245 1506 - if (rc_is_bit_0(rc, prob_len)) {
pankso@5245 1507 + if (rc_is_bit_0(rc, prob_len, error)) {
pankso@5245 1508 rc_update_bit_0(rc, prob_len);
pankso@5245 1509 prob_len += LZMA_LEN_MID - LZMA_LEN_CHOICE_2
pankso@5245 1510 + (pos_state <<
pankso@5245 1511 @@ -525,7 +540,7 @@
pankso@5245 1512 }
pankso@5245 1513 }
pankso@5245 1514
pankso@5245 1515 - rc_bit_tree_decode(rc, prob_len, num_bits, &len);
pankso@5245 1516 + rc_bit_tree_decode(rc, prob_len, num_bits, &len, error);
pankso@5245 1517 len += offset;
pankso@5245 1518
pankso@5245 1519 if (cst->state < 4) {
pankso@5245 1520 @@ -540,7 +555,7 @@
pankso@5245 1521 << LZMA_NUM_POS_SLOT_BITS);
pankso@5245 1522 rc_bit_tree_decode(rc, prob,
pankso@5245 1523 LZMA_NUM_POS_SLOT_BITS,
pankso@5245 1524 - &pos_slot);
pankso@5245 1525 + &pos_slot, error);
pankso@5245 1526 if (pos_slot >= LZMA_START_POS_MODEL_INDEX) {
pankso@5245 1527 int i, mi;
pankso@5245 1528 num_bits = (pos_slot >> 1) - 1;
pankso@5245 1529 @@ -553,7 +568,7 @@
pankso@5245 1530 num_bits -= LZMA_NUM_ALIGN_BITS;
pankso@5245 1531 while (num_bits--)
pankso@5245 1532 cst->rep0 = (cst->rep0 << 1) |
pankso@5245 1533 - rc_direct_bit(rc);
pankso@5245 1534 + rc_direct_bit(rc, error);
pankso@5245 1535 prob = p + LZMA_ALIGN;
pankso@5245 1536 cst->rep0 <<= LZMA_NUM_ALIGN_BITS;
pankso@5245 1537 num_bits = LZMA_NUM_ALIGN_BITS;
pankso@5245 1538 @@ -561,7 +576,7 @@
pankso@5245 1539 i = 1;
pankso@5245 1540 mi = 1;
pankso@5245 1541 while (num_bits--) {
pankso@5245 1542 - if (rc_get_bit(rc, prob + mi, &mi))
pankso@5245 1543 + if (rc_get_bit(rc, prob + mi, &mi, error))
pankso@5245 1544 cst->rep0 |= i;
pankso@5245 1545 i <<= 1;
pankso@5245 1546 }
pankso@5245 1547 @@ -578,12 +593,12 @@
pankso@5245 1548
pankso@5245 1549
pankso@5245 1550
pankso@5245 1551 -STATIC inline int INIT unlzma(unsigned char *buf, int in_len,
pankso@5245 1552 +STATIC int INIT unlzma(unsigned char *buf, int in_len,
pankso@5245 1553 int(*fill)(void*, unsigned int),
pankso@5245 1554 int(*flush)(void*, unsigned int),
pankso@5245 1555 unsigned char *output,
pankso@5245 1556 int *posp,
pankso@5245 1557 - void(*error_fn)(char *x)
pankso@5245 1558 + void(*error)(char *x)
pankso@5245 1559 )
pankso@5245 1560 {
pankso@5245 1561 extern int cpio_flush_buffer(void*, unsigned int);
pankso@5245 1562 @@ -600,10 +615,6 @@
pankso@5245 1563 unsigned char *inbuf;
pankso@5245 1564 int ret = -1;
pankso@5245 1565
pankso@5245 1566 - set_error_fn(error_fn);
pankso@5245 1567 - if (!flush)
pankso@5245 1568 - in_len -= 4; /* Uncompressed size hack active in pre-boot
pankso@5245 1569 - environment */
pankso@5245 1570 if (buf)
pankso@5245 1571 inbuf = buf;
pankso@5245 1572 else
pankso@5245 1573 @@ -630,7 +641,7 @@
pankso@5245 1574
pankso@5245 1575 for (i = 0; i < sizeof(header); i++) {
pankso@5245 1576 if (rc.ptr >= rc.buffer_end)
pankso@5245 1577 - rc_read(&rc);
pankso@5245 1578 + rc_read(&rc, error);
pankso@5245 1579 ((unsigned char *)&header)[i] = *rc.ptr++;
pankso@5245 1580 }
pankso@5245 1581
pankso@5245 1582 @@ -675,17 +686,17 @@
pankso@5245 1583 for (i = 0; i < num_probs; i++)
pankso@5245 1584 p[i] = (1 << RC_MODEL_TOTAL_BITS) >> 1;
pankso@5245 1585 wr.max_index = wr.next_index = 0;
pankso@5245 1586 - rc_init_code(&rc);
pankso@5245 1587 + rc_init_code(&rc, error);
pankso@5245 1588
pankso@5245 1589 while (get_pos(&wr) < header.dst_size) {
pankso@5245 1590 int pos_state = get_pos(&wr) & pos_state_mask;
pankso@5245 1591 uint16_t *prob = p + LZMA_IS_MATCH +
pankso@5245 1592 (cst.state << LZMA_NUM_POS_BITS_MAX) + pos_state;
pankso@5245 1593 - if (rc_is_bit_0(&rc, prob))
pankso@5245 1594 + if (rc_is_bit_0(&rc, prob, error))
pankso@5245 1595 process_bit0(&wr, &rc, &cst, p, pos_state, prob,
pankso@5245 1596 - lc, literal_pos_mask);
pankso@5245 1597 + lc, literal_pos_mask, error);
pankso@5245 1598 else {
pankso@5245 1599 - process_bit1(&wr, &rc, &cst, p, pos_state, prob);
pankso@5245 1600 + process_bit1(&wr, &rc, &cst, p, pos_state, prob, error);
pankso@5245 1601 if (cst.rep0 == 0)
pankso@5245 1602 break;
pankso@5245 1603 }
pankso@5245 1604 @@ -719,5 +730,19 @@
pankso@5245 1605 exit_0:
pankso@5245 1606 return ret;
pankso@5245 1607 }
pankso@5245 1608 +#if defined(CONFIG_DECOMPRESS_LZMA_NEEDED) && !defined(PREBOOT)
pankso@5245 1609 +EXPORT_SYMBOL(unlzma);
pankso@5245 1610 +#endif
pankso@5245 1611
pankso@5245 1612 -#define decompress unlzma
pankso@5245 1613 +#ifdef PREBOOT
pankso@5245 1614 +STATIC int INIT decompress(unsigned char *buf, int in_len,
pankso@5245 1615 + int(*fill)(void*, unsigned int),
pankso@5245 1616 + int(*flush)(void*, unsigned int),
pankso@5245 1617 + unsigned char *output,
pankso@5245 1618 + int *posp,
pankso@5245 1619 + void(*error_fn)(char *x)
pankso@5245 1620 + )
pankso@5245 1621 +{
pankso@5245 1622 + return unlzma(buf, in_len - 4, fill, flush, output, posp, error_fn);
pankso@5245 1623 +}
pankso@5245 1624 +#endif