super.c revision 1aef9e4f12365714fd95ac9a7a059ea4c7d6d846
1cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen/* 2cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * Squashfs - a compressed read only filesystem for Linux 3cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * 4cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007, 2008 5cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * Phillip Lougher <phillip@lougher.demon.co.uk> 6cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * 7cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * This program is free software; you can redistribute it and/or 8cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * modify it under the terms of the GNU General Public License 9cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * as published by the Free Software Foundation; either version 2, 10cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * or (at your option) any later version. 11cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * 12cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * This program is distributed in the hope that it will be useful, 13cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * but WITHOUT ANY WARRANTY; without even the implied warranty of 14cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * GNU General Public License for more details. 16dd479e9769eceee9fcc34e2173376024f3aa3c5fJakob Stoklund Olesen * 175907d863659eb972ebb2afe07bc863a4c616f0efJakob Stoklund Olesen * You should have received a copy of the GNU General Public License 18cfafc54040cc9722995558124f253d05a038176bJakob Stoklund Olesen * along with this program; if not, write to the Free Software 19f428eb6c1b09a2322b7a577b0bf2e49dd107bceaJakob Stoklund Olesen * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 20cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * 21cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * super.c 22b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen */ 23d0bb5e2ca05d9c942223bf05e5940bb0c6cc9d3fJakob Stoklund Olesen 24cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen/* 250db841f9c2b9a25fb5ecb36e350d3a802c35654cJakob Stoklund Olesen * This file implements code to read the superblock, read and initialise 26cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * in-memory structures at mount time, and all the VFS glue code to register 27cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen * the filesystem. 28cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen */ 29cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 30b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen#include <linux/fs.h> 31cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/vfs.h> 32cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/slab.h> 33f428eb6c1b09a2322b7a577b0bf2e49dd107bceaJakob Stoklund Olesen#include <linux/vmalloc.h> 34cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/mutex.h> 35cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/pagemap.h> 36cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/init.h> 37cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/module.h> 38cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/zlib.h> 39cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/squashfs_fs.h> 4000005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen#include <linux/squashfs_fs_sb.h> 41cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include <linux/squashfs_fs_i.h> 42cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 43cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen#include "squashfs.h" 44533f58ecdd8a4732c2f0e149387c4d8d8d4142deJakob Stoklund Olesen 45cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenstatic struct file_system_type squashfs_fs_type; 4698d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesenstatic struct super_operations squashfs_super_ops; 4798d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen 48cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenstatic int supported_squashfs_filesystem(short major, short minor, short comp) 49cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen{ 500db841f9c2b9a25fb5ecb36e350d3a802c35654cJakob Stoklund Olesen int err = 0; 510db841f9c2b9a25fb5ecb36e350d3a802c35654cJakob Stoklund Olesen 520db841f9c2b9a25fb5ecb36e350d3a802c35654cJakob Stoklund Olesen if (major < SQUASHFS_MAJOR) { 530db841f9c2b9a25fb5ecb36e350d3a802c35654cJakob Stoklund Olesen ERROR("Major/Minor mismatch, older Squashfs %d.%d " 54a67f14bf53737f9bb0afefa28e08c4aac6ec4804Benjamin Kramer "filesystems are unsupported\n", major, minor); 5500005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen err = -EINVAL; 56708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen } else if (major > SQUASHFS_MAJOR || minor > SQUASHFS_MINOR) { 57708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen ERROR("Major/Minor mismatch, trying to mount newer " 58708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen "%d.%d filesystem\n", major, minor); 59708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen ERROR("Please update your kernel\n"); 60708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen err = -EINVAL; 61708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen } 62708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen 63708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen if (comp != ZLIB_COMPRESSION) 64708d06f7fb5dfd9c8559aea07b042a88c65645f8Jakob Stoklund Olesen err = -EINVAL; 65cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 66cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen return err; 67cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen} 68cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 6992a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 7092a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesenstatic int squashfs_fill_super(struct super_block *sb, void *data, int silent) 7192a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen{ 7292a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen struct squashfs_sb_info *msblk; 73cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen struct squashfs_super_block *sblk = NULL; 74cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen char b[BDEVNAME_SIZE]; 75cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen struct inode *root; 76cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen long long root_inode; 77b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen unsigned short flags; 78cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen unsigned int fragments; 79f428eb6c1b09a2322b7a577b0bf2e49dd107bceaJakob Stoklund Olesen long long lookup_table_start; 80d0bb5e2ca05d9c942223bf05e5940bb0c6cc9d3fJakob Stoklund Olesen int err; 81b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen 82b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen TRACE("Entered squashfs_fill_superblock\n"); 83f42b66169d75301346e3685fd2b3e45e47806367Jakob Stoklund Olesen 84f428eb6c1b09a2322b7a577b0bf2e49dd107bceaJakob Stoklund Olesen sb->s_fs_info = kzalloc(sizeof(*msblk), GFP_KERNEL); 85cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen if (sb->s_fs_info == NULL) { 86cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen ERROR("Failed to allocate squashfs_sb_info\n"); 8798d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen goto failure2; 881a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen } 8922a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen msblk = sb->s_fs_info; 9022a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen 9122a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen msblk->stream.workspace = vmalloc(zlib_inflate_workspacesize()); 9222a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen if (msblk->stream.workspace == NULL) { 9322a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen ERROR("Failed to allocate zlib workspace\n"); 9422a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen goto failure; 9522a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen } 9622a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen 9722a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen sblk = kzalloc(sizeof(*sblk), GFP_KERNEL); 9822a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen if (sblk == NULL) { 9922a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen ERROR("Failed to allocate squashfs_super_block\n"); 10022a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen goto failure; 10122a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen } 10222a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen 10322a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen msblk->devblksize = sb_min_blocksize(sb, BLOCK_SIZE); 104fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen msblk->devblksize_log2 = ffz(~msblk->devblksize); 105fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen 106fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen mutex_init(&msblk->read_data_mutex); 107fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen mutex_init(&msblk->read_page_mutex); 108fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen mutex_init(&msblk->meta_index_mutex); 109fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen 110fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen /* 111fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen * msblk->bytes_used is checked in squashfs_read_data to ensure reads 112fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen * are not beyond filesystem end. But as we're using squashfs_read_data 11349743b18f50ac0f7e065f4754a26965d4db388deJakob Stoklund Olesen * here to read the superblock (including the value of 11449743b18f50ac0f7e065f4754a26965d4db388deJakob Stoklund Olesen * bytes_used) we need to set it to an initial sensible dummy value 11549743b18f50ac0f7e065f4754a26965d4db388deJakob Stoklund Olesen */ 11649743b18f50ac0f7e065f4754a26965d4db388deJakob Stoklund Olesen msblk->bytes_used = sizeof(*sblk); 11749743b18f50ac0f7e065f4754a26965d4db388deJakob Stoklund Olesen err = squashfs_read_data(sb, sblk, SQUASHFS_START, sizeof(*sblk) | 118fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen SQUASHFS_COMPRESSED_BIT_BLOCK, NULL, sizeof(*sblk)); 119fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen 120fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen if (err < 0) { 121fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen ERROR("unable to read squashfs_super_block\n"); 122fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen goto failed_mount; 123fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen } 12422a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen 12522a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen /* Check it is a SQUASHFS superblock */ 126b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesen sb->s_magic = le32_to_cpu(sblk->s_magic); 127b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesen if (sb->s_magic != SQUASHFS_MAGIC) { 1281a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen if (!silent) 1291a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen ERROR("Can't find a SQUASHFS superblock on %s\n", 1301a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen bdevname(sb->s_bdev, b)); 1311a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen err = -EINVAL; 1321a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen goto failed_mount; 1331a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen } 1341a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen 1351a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen /* Check the MAJOR & MINOR versions and compression type */ 1361a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen err = supported_squashfs_filesystem(le16_to_cpu(sblk->s_major), 1371a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen le16_to_cpu(sblk->s_minor), 1381a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen le16_to_cpu(sblk->compression)); 13922a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen if (err < 0) 14022a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen goto failed_mount; 1411a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen 1421a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen err = -EINVAL; 1431a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen 1441a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen /* Check the filesystem does not extend beyond the end of the 1451a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen block device */ 1461a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen msblk->bytes_used = le64_to_cpu(sblk->bytes_used); 14722a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen if (msblk->bytes_used < 0 || msblk->bytes_used > 14822a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen i_size_read(sb->s_bdev->bd_inode)) 14922a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen goto failed_mount; 15022a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen 1511a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen /* Check block size for sanity */ 152f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen msblk->block_size = le32_to_cpu(sblk->block_size); 153f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen if (msblk->block_size > SQUASHFS_FILE_SIZE) 1541a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen goto failed_mount; 1551a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen 156f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen msblk->block_log = le16_to_cpu(sblk->block_log); 15722a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen if (msblk->block_log > SQUASHFS_FILE_LOG) 158cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen goto failed_mount; 15951458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen 16051458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen /* Check the root inode for sanity */ 16151458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen root_inode = le64_to_cpu(sblk->root_inode); 16251458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen if (SQUASHFS_INODE_OFFSET(root_inode) > SQUASHFS_METADATA_SIZE) 16351458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen goto failed_mount; 16451458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen 16551458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen msblk->inode_table = le64_to_cpu(sblk->inode_table_start); 16651458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen msblk->directory_table = le64_to_cpu(sblk->directory_table_start); 16751458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen msblk->inodes = le32_to_cpu(sblk->inodes); 16851458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen flags = le16_to_cpu(sblk->flags); 16951458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen 17051458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen TRACE("Found valid superblock on %s\n", bdevname(sb->s_bdev, b)); 17151458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen TRACE("Inodes are %scompressed\n", SQUASHFS_UNCOMPRESSED_INODES(flags) 17251458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen ? "un" : ""); 173b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen TRACE("Data is %scompressed\n", SQUASHFS_UNCOMPRESSED_DATA(flags) 17422a1df6bf24c188dd637a0bb2cf9a2648806b6b1Jakob Stoklund Olesen ? "un" : ""); 175bece06f0c6936527e2b1c72d09f7d3a949af9a47Jakob Stoklund Olesen TRACE("Filesystem size %lld bytes\n", msblk->bytes_used); 176b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen TRACE("Block size %d\n", msblk->block_size); 177eda0fe8d58b0aaff5f18e7f13edfda3022384e70Jakob Stoklund Olesen TRACE("Number of inodes %d\n", msblk->inodes); 178eda0fe8d58b0aaff5f18e7f13edfda3022384e70Jakob Stoklund Olesen TRACE("Number of fragments %d\n", le32_to_cpu(sblk->fragments)); 179eda0fe8d58b0aaff5f18e7f13edfda3022384e70Jakob Stoklund Olesen TRACE("Number of ids %d\n", le16_to_cpu(sblk->no_ids)); 1807b41fbe87234f3ceef6ae11209730cbed4b69092Jakob Stoklund Olesen TRACE("sblk->inode_table_start %llx\n", msblk->inode_table); 18196dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen TRACE("sblk->directory_table_start %llx\n", 182b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen msblk->directory_table_start); 18396dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen TRACE("sblk->fragment_table_start %llx\n", 18496dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen le64_to_cpu(sblk->fragment_table_start)); 18500005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen TRACE("sblk->id_table_start %llx\n", le64_to_cpu(sblk->id_table_start)); 18696dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen 18700005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen sb->s_maxbytes = MAX_LFS_FILESIZE; 18800005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen sb->s_flags |= MS_RDONLY; 18900005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen sb->s_op = &squashfs_super_ops; 19000005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen 19100005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen err = -ENOMEM; 192c66a37df73f70ec3dbed06277763624f33ee3512Jakob Stoklund Olesen 19300005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen msblk->block_cache = squashfs_cache_init("metadata", 19400005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen SQUASHFS_CACHED_BLKS, SQUASHFS_METADATA_SIZE, 0); 19596dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen if (msblk->block_cache == NULL) 1965db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen goto failed_mount; 1975db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen 198c66a37df73f70ec3dbed06277763624f33ee3512Jakob Stoklund Olesen /* Allocate read_page block */ 1995db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen msblk->read_page = vmalloc(msblk->block_size); 20000005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen if (msblk->read_page == NULL) { 201c66a37df73f70ec3dbed06277763624f33ee3512Jakob Stoklund Olesen ERROR("Failed to allocate read_page block\n"); 2025db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen goto failed_mount; 2035db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen } 2045db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen 20500005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen /* Allocate and read id index table */ 20600005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen msblk->id_table = read_id_index_table(sb, 20700005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen le64_to_cpu(sblk->id_table_start), le16_to_cpu(sblk->no_ids)); 20800005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen if (IS_ERR(msblk->id_table)) { 20900005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen err = PTR_ERR(msblk->id_table); 21000005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen msblk->id_table = NULL; 21100005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen goto failed_mount; 21200005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen } 21300005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen 21400005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen fragments = le32_to_cpu(sblk->fragments); 21500005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen if (fragments == 0) 21600005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen goto allocate_lookup_table; 21796dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen 21896dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen msblk->fragment_cache = squashfs_cache_init("fragment", 21996dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen SQUASHFS_CACHED_FRAGMENTS, msblk->block_size, 1); 22096dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen if (msblk->fragment_cache == NULL) { 22196dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen err = -ENOMEM; 22296dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen goto failed_mount; 22396dcd95a45968de6cb05864cf91aae33169cf179Jakob Stoklund Olesen } 22400005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen 22500005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen /* Allocate and read fragment index table */ 22600005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen msblk->fragment_index = read_fragment_index_table(sb, 22700005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen le64_to_cpu(sblk->fragment_table_start), fragments); 22800005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen if (IS_ERR(msblk->fragment_index)) { 22900005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen err = PTR_ERR(msblk->fragment_index); 230cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen msblk->fragment_index = NULL; 231cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen goto failed_mount; 232cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen } 233cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 234cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenallocate_lookup_table: 235533f58ecdd8a4732c2f0e149387c4d8d8d4142deJakob Stoklund Olesen lookup_table_start = le64_to_cpu(sblk->lookup_table_start); 236cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen if (lookup_table_start == SQUASHFS_INVALID_BLK) 237cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen goto allocate_root; 238cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 239cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen /* Allocate and read inode lookup table */ 240cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen msblk->inode_lookup_table = read_inode_lookup_table(sb, 241cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen lookup_table_start, msblk->inodes); 24298d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen if (IS_ERR(msblk->inode_lookup_table)) { 24398d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen err = PTR_ERR(msblk->inode_lookup_table); 244ccdb3fcef9aeb9f683cd738afbe1cd961bb0c1efJakob Stoklund Olesen msblk->inode_lookup_table = NULL; 245ccdb3fcef9aeb9f683cd738afbe1cd961bb0c1efJakob Stoklund Olesen goto failed_mount; 246cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen } 247cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 248cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen sb->s_export_op = &squashfs_export_ops; 249cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 250cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenallocate_root: 251b853e6c3702149cdbbd6fa404334e3ba0055641aAndrew Trick root = new_inode(sb); 252b853e6c3702149cdbbd6fa404334e3ba0055641aAndrew Trick if (!root) { 25392a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen err = -ENOMEM; 2547792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen goto failed_mount; 2551d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen } 256f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen 25792a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen err = squashfs_read_inode(root, root_inode); 258200729882a47535d4c2496283d26600171531fadJakob Stoklund Olesen if (err) { 259f4afdfc501b7185d24a0ef184fe3d0c0bbe22e0cJakob Stoklund Olesen iget_failed(root); 260f4afdfc501b7185d24a0ef184fe3d0c0bbe22e0cJakob Stoklund Olesen goto failed_mount; 261c66a37df73f70ec3dbed06277763624f33ee3512Jakob Stoklund Olesen } 262c66a37df73f70ec3dbed06277763624f33ee3512Jakob Stoklund Olesen insert_inode_hash(root); 26387972fa63f0e2631778166e0c258c456ec12db7cJakob Stoklund Olesen 26400005782fa860f4b48b3b5261d92541c61ee2495Jakob Stoklund Olesen sb->s_root = d_alloc_root(root); 265034a80d065358b412cdd270e08fb6f1986e65e50Jakob Stoklund Olesen if (sb->s_root == NULL) { 26651458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen ERROR("Root inode create failed\n"); 26751458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen err = -ENOMEM; 26851458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen iput(root); 26951458ed09e6db0e424cd528e10b879f59915abe4Jakob Stoklund Olesen goto failed_mount; 270b64d92e29f38002e52a22fe36ea2d488968e3537Jakob Stoklund Olesen } 2716bfba2e5af163442a1c6b11fe14aa9df9101cfd7Jakob Stoklund Olesen 2726bfba2e5af163442a1c6b11fe14aa9df9101cfd7Jakob Stoklund Olesen TRACE("Leaving squashfs_fill_super\n"); 27398c8141b6d8fcbb9bd258ebcdd4171f55c5a8e9dJakob Stoklund Olesen kfree(sblk); 2746bfba2e5af163442a1c6b11fe14aa9df9101cfd7Jakob Stoklund Olesen return 0; 275b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen 276b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesenfailed_mount: 277dab35d33ae17353cb01aaaa42abbcb28b33eb98aJakob Stoklund Olesen squashfs_cache_delete(msblk->block_cache); 278dab35d33ae17353cb01aaaa42abbcb28b33eb98aJakob Stoklund Olesen squashfs_cache_delete(msblk->fragment_cache); 279034a80d065358b412cdd270e08fb6f1986e65e50Jakob Stoklund Olesen kfree(msblk->inode_lookup_table); 280034a80d065358b412cdd270e08fb6f1986e65e50Jakob Stoklund Olesen kfree(msblk->fragment_index); 281b64d92e29f38002e52a22fe36ea2d488968e3537Jakob Stoklund Olesen kfree(msblk->id_table); 282b64d92e29f38002e52a22fe36ea2d488968e3537Jakob Stoklund Olesen vfree(msblk->read_page); 283cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen vfree(msblk->stream.workspace); 284cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen kfree(sb->s_fs_info); 285cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen sb->s_fs_info = NULL; 286cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen kfree(sblk); 287cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen return err; 288b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesen 289b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesenfailure: 290fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen vfree(msblk->stream.workspace); 291fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen kfree(sb->s_fs_info); 292fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen sb->s_fs_info = NULL; 29349743b18f50ac0f7e065f4754a26965d4db388deJakob Stoklund Olesenfailure2: 294fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen return -ENOMEM; 295fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen} 296b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesen 297b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesen 298b8d936bc179ddf31b6350015d74900b74db6b450Jakob Stoklund Olesenstatic int squashfs_statfs(struct dentry *dentry, struct kstatfs *buf) 299200729882a47535d4c2496283d26600171531fadJakob Stoklund Olesen{ 300200729882a47535d4c2496283d26600171531fadJakob Stoklund Olesen struct squashfs_sb_info *msblk = dentry->d_sb->s_fs_info; 301200729882a47535d4c2496283d26600171531fadJakob Stoklund Olesen 302200729882a47535d4c2496283d26600171531fadJakob Stoklund Olesen TRACE("Entered squashfs_statfs\n"); 303200729882a47535d4c2496283d26600171531fadJakob Stoklund Olesen 304cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen buf->f_type = SQUASHFS_MAGIC; 305cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen buf->f_bsize = msblk->block_size; 306cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen buf->f_blocks = ((msblk->bytes_used - 1) >> msblk->block_log) + 1; 307cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen buf->f_bfree = buf->f_bavail = 0; 3081a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen buf->f_files = msblk->inodes; 309cfafc54040cc9722995558124f253d05a038176bJakob Stoklund Olesen buf->f_ffree = 0; 310b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen buf->f_namelen = SQUASHFS_NAME_LEN; 311cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 312cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen return 0; 313cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen} 3145b220213bfe9c37c2bb41a7ae0804e06a14f1007Rafael Espindola 315cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 316cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenstatic int squashfs_remount(struct super_block *sb, int *flags, char *data) 317cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen{ 318cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen *flags |= MS_RDONLY; 319cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen return 0; 320b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen} 321b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen 322cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 323cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenstatic void squashfs_put_super(struct super_block *sb) 324cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen{ 325cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen if (sb->s_fs_info) { 326cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen struct squashfs_sb_info *sbi = sb->s_fs_info; 327cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen squashfs_cache_delete(sbi->block_cache); 328cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen squashfs_cache_delete(sbi->fragment_cache); 329b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen vfree(sbi->read_page); 330cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen kfree(sbi->id_table); 331cfafc54040cc9722995558124f253d05a038176bJakob Stoklund Olesen kfree(sbi->fragment_index); 332cfafc54040cc9722995558124f253d05a038176bJakob Stoklund Olesen kfree(sbi->meta_index); 333cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen vfree(sbi->stream.workspace); 334cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen kfree(sb->s_fs_info); 33527215676c7114132a0374f7b5c9ea73d9354d329Jakob Stoklund Olesen sb->s_fs_info = NULL; 336cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen } 337cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen} 338cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 339f428eb6c1b09a2322b7a577b0bf2e49dd107bceaJakob Stoklund Olesen 340f428eb6c1b09a2322b7a577b0bf2e49dd107bceaJakob Stoklund Olesenstatic int squashfs_get_sb(struct file_system_type *fs_type, int flags, 341cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen const char *dev_name, void *data, 342cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen struct vfsmount *mnt) 343cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen{ 344cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen return get_sb_bdev(fs_type, flags, dev_name, data, squashfs_fill_super, 345b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen mnt); 346b5fa9333431673aac2ced8dea80152349a85cf6fJakob Stoklund Olesen} 347cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 348cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 349cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenstatic struct kmem_cache *squashfs_inode_cachep; 35092a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 35192a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 35292a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesenstatic void init_once(void *foo) 35392a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen{ 35492a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen struct squashfs_inode_info *ei = foo; 35592a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 35692a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen inode_init_once(&ei->vfs_inode); 35792a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen} 35892a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 35992a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 3607792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesenstatic int __init init_inodecache(void) 3617792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen{ 3627792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen squashfs_inode_cachep = kmem_cache_create("squashfs_inode_cache", 3637792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen sizeof(struct squashfs_inode_info), 0, 3647792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen SLAB_HWCACHE_ALIGN|SLAB_RECLAIM_ACCOUNT, init_once); 3657792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen 3667792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen return squashfs_inode_cachep ? 0 : -ENOMEM; 3677792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen} 3687792e980c43536814ea42448db9799b4da32fef6Jakob Stoklund Olesen 36992a55f4bdd120cdd3bb5a004c792d4d24a940311Jakob Stoklund Olesen 3701d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesenstatic void destroy_inodecache(void) 3711d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen{ 3721d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen kmem_cache_destroy(squashfs_inode_cachep); 3731d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen} 3741d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen 3751d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen 3761d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesenstatic int __init init_squashfs_fs(void) 3771d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen{ 3781d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen int err = init_inodecache(); 3791d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen 3801d5b84508173b93faf513032b3847152e6060791Jakob Stoklund Olesen if (err) 381f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen goto out; 382f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen 383165e231c4295deb5cabd124d08e231b551bcc0b2Jakob Stoklund Olesen err = register_filesystem(&squashfs_fs_type); 384165e231c4295deb5cabd124d08e231b551bcc0b2Jakob Stoklund Olesen if (err) { 385f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen destroy_inodecache(); 386165e231c4295deb5cabd124d08e231b551bcc0b2Jakob Stoklund Olesen goto out; 3871a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen } 3881a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen 389f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen printk(KERN_INFO "squashfs: version 4.0 (2008/10/20) " 390f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen "Phillip Lougher\n"); 391cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 392cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenout: 3931a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen return err; 3945db4289e404d76664f8aabe2675a4cc2d7b0e98eJakob Stoklund Olesen} 395cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 396cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesen 397cba2e06d525b723849cd8e1f083eb1e59a494b4eJakob Stoklund Olesenstatic void __exit exit_squashfs_fs(void) 39898d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen{ 39998d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen unregister_filesystem(&squashfs_fs_type); 40098d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen destroy_inodecache(); 401107d366df762c18294dc00f5de916f62672353ffJakob Stoklund Olesen} 402107d366df762c18294dc00f5de916f62672353ffJakob Stoklund Olesen 40398d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen 40498d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesenstatic struct inode *squashfs_alloc_inode(struct super_block *sb) 405107d366df762c18294dc00f5de916f62672353ffJakob Stoklund Olesen{ 40690c1d7ddfc65654f7efe72d56cad65d1af9e6b2aJakob Stoklund Olesen struct squashfs_inode_info *ei = 4071a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen kmem_cache_alloc(squashfs_inode_cachep, GFP_KERNEL); 4081a988004dba412deb5d6b8e93b955dfc837065f0Jakob Stoklund Olesen 409fa89a0344bba7a0ae87d3de204d18bb1ecaa5955Jakob Stoklund Olesen return ei ? &ei->vfs_inode : NULL; 410f22ca3fe5f0cfbb832cf41270f97cf5c0134fd7bJakob Stoklund Olesen} 411cc07e04262fe4bc35469fbadc53d2ec7bfd02fe2Jakob Stoklund Olesen 412eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen 413eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesenstatic void squashfs_destroy_inode(struct inode *inode) 414eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen{ 415cc07e04262fe4bc35469fbadc53d2ec7bfd02fe2Jakob Stoklund Olesen kmem_cache_free(squashfs_inode_cachep, SQUASHFS_I(inode)); 416cc07e04262fe4bc35469fbadc53d2ec7bfd02fe2Jakob Stoklund Olesen} 417cc07e04262fe4bc35469fbadc53d2ec7bfd02fe2Jakob Stoklund Olesen 418cc07e04262fe4bc35469fbadc53d2ec7bfd02fe2Jakob Stoklund Olesen 419cc07e04262fe4bc35469fbadc53d2ec7bfd02fe2Jakob Stoklund Olesenstatic struct file_system_type squashfs_fs_type = { 420eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen .owner = THIS_MODULE, 421eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen .name = "squashfs", 422107d366df762c18294dc00f5de916f62672353ffJakob Stoklund Olesen .get_sb = squashfs_get_sb, 423d2a50734234a80893ad71da90d9f32032c47e000Jakob Stoklund Olesen .kill_sb = kill_block_super, 424eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen .fs_flags = FS_REQUIRES_DEV 425eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen}; 426eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesen 427eb29157d80847c207b77910bcd40a6a6c91ca5c5Jakob Stoklund Olesenstatic struct super_operations squashfs_super_ops = { 428107d366df762c18294dc00f5de916f62672353ffJakob Stoklund Olesen .alloc_inode = squashfs_alloc_inode, 429107d366df762c18294dc00f5de916f62672353ffJakob Stoklund Olesen .destroy_inode = squashfs_destroy_inode, 43090c1d7ddfc65654f7efe72d56cad65d1af9e6b2aJakob Stoklund Olesen .statfs = squashfs_statfs, 43190c1d7ddfc65654f7efe72d56cad65d1af9e6b2aJakob Stoklund Olesen .put_super = squashfs_put_super, 43298d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen .remount_fs = squashfs_remount 43398d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen}; 43498d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesen 43598d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesenmodule_init(init_squashfs_fs); 43698d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund Olesenmodule_exit(exit_squashfs_fs); 43798d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund OlesenMODULE_DESCRIPTION("squashfs 4.0, a compressed read-only filesystem"); 43898d9648de7d571b2e6d139b65961a70d1833b0d7Jakob Stoklund OlesenMODULE_AUTHOR("Phillip Lougher <phillip@lougher.demon.co.uk>"); 439770d42de3b7643b2b4f835f32e3a16275b9fbdbaJakob Stoklund OlesenMODULE_LICENSE("GPL"); 4406bfba2e5af163442a1c6b11fe14aa9df9101cfd7Jakob Stoklund Olesen