summaryrefslogtreecommitdiffstats
path: root/qemu/roms/u-boot/fs/ext4
diff options
context:
space:
mode:
authorRajithaY <rajithax.yerrumsetty@intel.com>2017-04-25 03:31:15 -0700
committerRajitha Yerrumchetty <rajithax.yerrumsetty@intel.com>2017-05-22 06:48:08 +0000
commitbb756eebdac6fd24e8919e2c43f7d2c8c4091f59 (patch)
treeca11e03542edf2d8f631efeca5e1626d211107e3 /qemu/roms/u-boot/fs/ext4
parenta14b48d18a9ed03ec191cf16b162206998a895ce (diff)
Adding qemu as a submodule of KVMFORNFV
This Patch includes the changes to add qemu as a submodule to kvmfornfv repo and make use of the updated latest qemu for the execution of all testcase Change-Id: I1280af507a857675c7f81d30c95255635667bdd7 Signed-off-by:RajithaY<rajithax.yerrumsetty@intel.com>
Diffstat (limited to 'qemu/roms/u-boot/fs/ext4')
-rw-r--r--qemu/roms/u-boot/fs/ext4/Makefile13
-rw-r--r--qemu/roms/u-boot/fs/ext4/crc16.c62
-rw-r--r--qemu/roms/u-boot/fs/ext4/crc16.h16
-rw-r--r--qemu/roms/u-boot/fs/ext4/dev.c146
-rw-r--r--qemu/roms/u-boot/fs/ext4/ext4_common.c2250
-rw-r--r--qemu/roms/u-boot/fs/ext4/ext4_common.h78
-rw-r--r--qemu/roms/u-boot/fs/ext4/ext4_journal.c653
-rw-r--r--qemu/roms/u-boot/fs/ext4/ext4_journal.h125
-rw-r--r--qemu/roms/u-boot/fs/ext4/ext4_write.c977
-rw-r--r--qemu/roms/u-boot/fs/ext4/ext4fs.c228
10 files changed, 0 insertions, 4548 deletions
diff --git a/qemu/roms/u-boot/fs/ext4/Makefile b/qemu/roms/u-boot/fs/ext4/Makefile
deleted file mode 100644
index 8d15bdad6..000000000
--- a/qemu/roms/u-boot/fs/ext4/Makefile
+++ /dev/null
@@ -1,13 +0,0 @@
-#
-# (C) Copyright 2006
-# Wolfgang Denk, DENX Software Engineering, wd@denx.de.
-#
-# (C) Copyright 2003
-# Pavel Bartusek, Sysgo Real-Time Solutions AG, pba@sysgo.de
-#
-#
-# SPDX-License-Identifier: GPL-2.0+
-#
-
-obj-y := ext4fs.o ext4_common.o dev.o
-obj-$(CONFIG_EXT4_WRITE) += ext4_write.o ext4_journal.o crc16.o
diff --git a/qemu/roms/u-boot/fs/ext4/crc16.c b/qemu/roms/u-boot/fs/ext4/crc16.c
deleted file mode 100644
index 3afb34dae..000000000
--- a/qemu/roms/u-boot/fs/ext4/crc16.c
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * crc16.c
- *
- * This source code is licensed under the GNU General Public License,
- * Version 2. See the file COPYING for more details.
- */
-
-#include <common.h>
-#include <asm/byteorder.h>
-#include <linux/stat.h>
-#include "crc16.h"
-
-/** CRC table for the CRC-16. The poly is 0x8005 (x16 + x15 + x2 + 1) */
-static __u16 const crc16_table[256] = {
- 0x0000, 0xC0C1, 0xC181, 0x0140, 0xC301, 0x03C0, 0x0280, 0xC241,
- 0xC601, 0x06C0, 0x0780, 0xC741, 0x0500, 0xC5C1, 0xC481, 0x0440,
- 0xCC01, 0x0CC0, 0x0D80, 0xCD41, 0x0F00, 0xCFC1, 0xCE81, 0x0E40,
- 0x0A00, 0xCAC1, 0xCB81, 0x0B40, 0xC901, 0x09C0, 0x0880, 0xC841,
- 0xD801, 0x18C0, 0x1980, 0xD941, 0x1B00, 0xDBC1, 0xDA81, 0x1A40,
- 0x1E00, 0xDEC1, 0xDF81, 0x1F40, 0xDD01, 0x1DC0, 0x1C80, 0xDC41,
- 0x1400, 0xD4C1, 0xD581, 0x1540, 0xD701, 0x17C0, 0x1680, 0xD641,
- 0xD201, 0x12C0, 0x1380, 0xD341, 0x1100, 0xD1C1, 0xD081, 0x1040,
- 0xF001, 0x30C0, 0x3180, 0xF141, 0x3300, 0xF3C1, 0xF281, 0x3240,
- 0x3600, 0xF6C1, 0xF781, 0x3740, 0xF501, 0x35C0, 0x3480, 0xF441,
- 0x3C00, 0xFCC1, 0xFD81, 0x3D40, 0xFF01, 0x3FC0, 0x3E80, 0xFE41,
- 0xFA01, 0x3AC0, 0x3B80, 0xFB41, 0x3900, 0xF9C1, 0xF881, 0x3840,
- 0x2800, 0xE8C1, 0xE981, 0x2940, 0xEB01, 0x2BC0, 0x2A80, 0xEA41,
- 0xEE01, 0x2EC0, 0x2F80, 0xEF41, 0x2D00, 0xEDC1, 0xEC81, 0x2C40,
- 0xE401, 0x24C0, 0x2580, 0xE541, 0x2700, 0xE7C1, 0xE681, 0x2640,
- 0x2200, 0xE2C1, 0xE381, 0x2340, 0xE101, 0x21C0, 0x2080, 0xE041,
- 0xA001, 0x60C0, 0x6180, 0xA141, 0x6300, 0xA3C1, 0xA281, 0x6240,
- 0x6600, 0xA6C1, 0xA781, 0x6740, 0xA501, 0x65C0, 0x6480, 0xA441,
- 0x6C00, 0xACC1, 0xAD81, 0x6D40, 0xAF01, 0x6FC0, 0x6E80, 0xAE41,
- 0xAA01, 0x6AC0, 0x6B80, 0xAB41, 0x6900, 0xA9C1, 0xA881, 0x6840,
- 0x7800, 0xB8C1, 0xB981, 0x7940, 0xBB01, 0x7BC0, 0x7A80, 0xBA41,
- 0xBE01, 0x7EC0, 0x7F80, 0xBF41, 0x7D00, 0xBDC1, 0xBC81, 0x7C40,
- 0xB401, 0x74C0, 0x7580, 0xB541, 0x7700, 0xB7C1, 0xB681, 0x7640,
- 0x7200, 0xB2C1, 0xB381, 0x7340, 0xB101, 0x71C0, 0x7080, 0xB041,
- 0x5000, 0x90C1, 0x9181, 0x5140, 0x9301, 0x53C0, 0x5280, 0x9241,
- 0x9601, 0x56C0, 0x5780, 0x9741, 0x5500, 0x95C1, 0x9481, 0x5440,
- 0x9C01, 0x5CC0, 0x5D80, 0x9D41, 0x5F00, 0x9FC1, 0x9E81, 0x5E40,
- 0x5A00, 0x9AC1, 0x9B81, 0x5B40, 0x9901, 0x59C0, 0x5880, 0x9841,
- 0x8801, 0x48C0, 0x4980, 0x8941, 0x4B00, 0x8BC1, 0x8A81, 0x4A40,
- 0x4E00, 0x8EC1, 0x8F81, 0x4F40, 0x8D01, 0x4DC0, 0x4C80, 0x8C41,
- 0x4400, 0x84C1, 0x8581, 0x4540, 0x8701, 0x47C0, 0x4680, 0x8641,
- 0x8201, 0x42C0, 0x4380, 0x8341, 0x4100, 0x81C1, 0x8081, 0x4040
-};
-
-/**
- * Compute the CRC-16 for the data buffer
-*/
-
-unsigned int ext2fs_crc16(unsigned int crc,
- const void *buffer, unsigned int len)
-{
- const unsigned char *cp = buffer;
-
- while (len--)
- crc = (((crc >> 8) & 0xffU) ^
- crc16_table[(crc ^ *cp++) & 0xffU]) & 0x0000ffffU;
- return crc;
-}
diff --git a/qemu/roms/u-boot/fs/ext4/crc16.h b/qemu/roms/u-boot/fs/ext4/crc16.h
deleted file mode 100644
index 5fd113a56..000000000
--- a/qemu/roms/u-boot/fs/ext4/crc16.h
+++ /dev/null
@@ -1,16 +0,0 @@
-/*
- * crc16.h - CRC-16 routine
- * Implements the standard CRC-16:
- * Width 16
- * Poly 0x8005 (x16 + x15 + x2 + 1)
- * Init 0
- *
- * Copyright (c) 2005 Ben Gardner <bgardner@wabtec.com>
- * This source code is licensed under the GNU General Public License,
- * Version 2. See the file COPYING for more details.
- */
-#ifndef __CRC16_H
-#define __CRC16_H
-extern unsigned int ext2fs_crc16(unsigned int crc,
- const void *buffer, unsigned int len);
-#endif
diff --git a/qemu/roms/u-boot/fs/ext4/dev.c b/qemu/roms/u-boot/fs/ext4/dev.c
deleted file mode 100644
index e0b513a4e..000000000
--- a/qemu/roms/u-boot/fs/ext4/dev.c
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * made from existing ext2/dev.c file of Uboot
- * (C) Copyright 2004
- * esd gmbh <www.esd-electronics.com>
- * Reinhard Arlt <reinhard.arlt@esd-electronics.com>
- *
- * based on code of fs/reiserfs/dev.c by
- *
- * (C) Copyright 2003 - 2004
- * Sysgo AG, <www.elinos.com>, Pavel Bartusek <pba@sysgo.com>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-/*
- * Changelog:
- * 0.1 - Newly created file for ext4fs support. Taken from
- * fs/ext2/dev.c file in uboot.
- */
-
-#include <common.h>
-#include <config.h>
-#include <ext4fs.h>
-#include <ext_common.h>
-#include "ext4_common.h"
-
-lbaint_t part_offset;
-
-static block_dev_desc_t *ext4fs_block_dev_desc;
-static disk_partition_t *part_info;
-
-void ext4fs_set_blk_dev(block_dev_desc_t *rbdd, disk_partition_t *info)
-{
- assert(rbdd->blksz == (1 << rbdd->log2blksz));
- ext4fs_block_dev_desc = rbdd;
- get_fs()->dev_desc = rbdd;
- part_info = info;
- part_offset = info->start;
- get_fs()->total_sect = ((uint64_t)info->size * info->blksz) >>
- get_fs()->dev_desc->log2blksz;
-}
-
-int ext4fs_devread(lbaint_t sector, int byte_offset, int byte_len, char *buf)
-{
- unsigned block_len;
- int log2blksz = ext4fs_block_dev_desc->log2blksz;
- ALLOC_CACHE_ALIGN_BUFFER(char, sec_buf, (ext4fs_block_dev_desc ?
- ext4fs_block_dev_desc->blksz :
- 0));
- if (ext4fs_block_dev_desc == NULL) {
- printf("** Invalid Block Device Descriptor (NULL)\n");
- return 0;
- }
-
- /* Check partition boundaries */
- if ((sector < 0) ||
- ((sector + ((byte_offset + byte_len - 1) >> log2blksz))
- >= part_info->size)) {
- printf("%s read outside partition " LBAFU "\n", __func__,
- sector);
- return 0;
- }
-
- /* Get the read to the beginning of a partition */
- sector += byte_offset >> log2blksz;
- byte_offset &= ext4fs_block_dev_desc->blksz - 1;
-
- debug(" <" LBAFU ", %d, %d>\n", sector, byte_offset, byte_len);
-
- if (byte_offset != 0) {
- /* read first part which isn't aligned with start of sector */
- if (ext4fs_block_dev_desc->
- block_read(ext4fs_block_dev_desc->dev,
- part_info->start + sector, 1,
- (unsigned long *) sec_buf) != 1) {
- printf(" ** ext2fs_devread() read error **\n");
- return 0;
- }
- memcpy(buf, sec_buf + byte_offset,
- min(ext4fs_block_dev_desc->blksz
- - byte_offset, byte_len));
- buf += min(ext4fs_block_dev_desc->blksz
- - byte_offset, byte_len);
- byte_len -= min(ext4fs_block_dev_desc->blksz
- - byte_offset, byte_len);
- sector++;
- }
-
- if (byte_len == 0)
- return 1;
-
- /* read sector aligned part */
- block_len = byte_len & ~(ext4fs_block_dev_desc->blksz - 1);
-
- if (block_len == 0) {
- ALLOC_CACHE_ALIGN_BUFFER(u8, p, ext4fs_block_dev_desc->blksz);
-
- block_len = ext4fs_block_dev_desc->blksz;
- ext4fs_block_dev_desc->block_read(ext4fs_block_dev_desc->dev,
- part_info->start + sector,
- 1, (unsigned long *)p);
- memcpy(buf, p, byte_len);
- return 1;
- }
-
- if (ext4fs_block_dev_desc->block_read(ext4fs_block_dev_desc->dev,
- part_info->start + sector,
- block_len >> log2blksz,
- (unsigned long *) buf) !=
- block_len >> log2blksz) {
- printf(" ** %s read error - block\n", __func__);
- return 0;
- }
- block_len = byte_len & ~(ext4fs_block_dev_desc->blksz - 1);
- buf += block_len;
- byte_len -= block_len;
- sector += block_len / ext4fs_block_dev_desc->blksz;
-
- if (byte_len != 0) {
- /* read rest of data which are not in whole sector */
- if (ext4fs_block_dev_desc->
- block_read(ext4fs_block_dev_desc->dev,
- part_info->start + sector, 1,
- (unsigned long *) sec_buf) != 1) {
- printf("* %s read error - last part\n", __func__);
- return 0;
- }
- memcpy(buf, sec_buf, byte_len);
- }
- return 1;
-}
-
-int ext4_read_superblock(char *buffer)
-{
- struct ext_filesystem *fs = get_fs();
- int sect = SUPERBLOCK_START >> fs->dev_desc->log2blksz;
- int off = SUPERBLOCK_START % fs->dev_desc->blksz;
-
- return ext4fs_devread(sect, off, SUPERBLOCK_SIZE,
- buffer);
-}
diff --git a/qemu/roms/u-boot/fs/ext4/ext4_common.c b/qemu/roms/u-boot/fs/ext4/ext4_common.c
deleted file mode 100644
index 1c1172163..000000000
--- a/qemu/roms/u-boot/fs/ext4/ext4_common.c
+++ /dev/null
@@ -1,2250 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * ext4ls and ext4load : Based on ext2 ls load support in Uboot.
- *
- * (C) Copyright 2004
- * esd gmbh <www.esd-electronics.com>
- * Reinhard Arlt <reinhard.arlt@esd-electronics.com>
- *
- * based on code from grub2 fs/ext2.c and fs/fshelp.c by
- * GRUB -- GRand Unified Bootloader
- * Copyright (C) 2003, 2004 Free Software Foundation, Inc.
- *
- * ext4write : Based on generic ext4 protocol.
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-#include <ext_common.h>
-#include <ext4fs.h>
-#include <malloc.h>
-#include <stddef.h>
-#include <linux/stat.h>
-#include <linux/time.h>
-#include <asm/byteorder.h>
-#include "ext4_common.h"
-
-struct ext2_data *ext4fs_root;
-struct ext2fs_node *ext4fs_file;
-uint32_t *ext4fs_indir1_block;
-int ext4fs_indir1_size;
-int ext4fs_indir1_blkno = -1;
-uint32_t *ext4fs_indir2_block;
-int ext4fs_indir2_size;
-int ext4fs_indir2_blkno = -1;
-
-uint32_t *ext4fs_indir3_block;
-int ext4fs_indir3_size;
-int ext4fs_indir3_blkno = -1;
-struct ext2_inode *g_parent_inode;
-static int symlinknest;
-
-#if defined(CONFIG_EXT4_WRITE)
-uint32_t ext4fs_div_roundup(uint32_t size, uint32_t n)
-{
- uint32_t res = size / n;
- if (res * n != size)
- res++;
-
- return res;
-}
-
-void put_ext4(uint64_t off, void *buf, uint32_t size)
-{
- uint64_t startblock;
- uint64_t remainder;
- unsigned char *temp_ptr = NULL;
- struct ext_filesystem *fs = get_fs();
- int log2blksz = fs->dev_desc->log2blksz;
- ALLOC_CACHE_ALIGN_BUFFER(unsigned char, sec_buf, fs->dev_desc->blksz);
-
- startblock = off >> log2blksz;
- startblock += part_offset;
- remainder = off & (uint64_t)(fs->dev_desc->blksz - 1);
-
- if (fs->dev_desc == NULL)
- return;
-
- if ((startblock + (size >> log2blksz)) >
- (part_offset + fs->total_sect)) {
- printf("part_offset is " LBAFU "\n", part_offset);
- printf("total_sector is %llu\n", fs->total_sect);
- printf("error: overflow occurs\n");
- return;
- }
-
- if (remainder) {
- if (fs->dev_desc->block_read) {
- fs->dev_desc->block_read(fs->dev_desc->dev,
- startblock, 1, sec_buf);
- temp_ptr = sec_buf;
- memcpy((temp_ptr + remainder),
- (unsigned char *)buf, size);
- fs->dev_desc->block_write(fs->dev_desc->dev,
- startblock, 1, sec_buf);
- }
- } else {
- if (size >> log2blksz != 0) {
- fs->dev_desc->block_write(fs->dev_desc->dev,
- startblock,
- size >> log2blksz,
- (unsigned long *)buf);
- } else {
- fs->dev_desc->block_read(fs->dev_desc->dev,
- startblock, 1, sec_buf);
- temp_ptr = sec_buf;
- memcpy(temp_ptr, buf, size);
- fs->dev_desc->block_write(fs->dev_desc->dev,
- startblock, 1,
- (unsigned long *)sec_buf);
- }
- }
-}
-
-static int _get_new_inode_no(unsigned char *buffer)
-{
- struct ext_filesystem *fs = get_fs();
- unsigned char input;
- int operand, status;
- int count = 1;
- int j = 0;
-
- /* get the blocksize of the filesystem */
- unsigned char *ptr = buffer;
- while (*ptr == 255) {
- ptr++;
- count += 8;
- if (count > ext4fs_root->sblock.inodes_per_group)
- return -1;
- }
-
- for (j = 0; j < fs->blksz; j++) {
- input = *ptr;
- int i = 0;
- while (i <= 7) {
- operand = 1 << i;
- status = input & operand;
- if (status) {
- i++;
- count++;
- } else {
- *ptr |= operand;
- return count;
- }
- }
- ptr = ptr + 1;
- }
-
- return -1;
-}
-
-static int _get_new_blk_no(unsigned char *buffer)
-{
- unsigned char input;
- int operand, status;
- int count = 0;
- int j = 0;
- unsigned char *ptr = buffer;
- struct ext_filesystem *fs = get_fs();
-
- if (fs->blksz != 1024)
- count = 0;
- else
- count = 1;
-
- while (*ptr == 255) {
- ptr++;
- count += 8;
- if (count == (fs->blksz * 8))
- return -1;
- }
-
- for (j = 0; j < fs->blksz; j++) {
- input = *ptr;
- int i = 0;
- while (i <= 7) {
- operand = 1 << i;
- status = input & operand;
- if (status) {
- i++;
- count++;
- } else {
- *ptr |= operand;
- return count;
- }
- }
- ptr = ptr + 1;
- }
-
- return -1;
-}
-
-int ext4fs_set_block_bmap(long int blockno, unsigned char *buffer, int index)
-{
- int i, remainder, status;
- unsigned char *ptr = buffer;
- unsigned char operand;
- i = blockno / 8;
- remainder = blockno % 8;
- int blocksize = EXT2_BLOCK_SIZE(ext4fs_root);
-
- i = i - (index * blocksize);
- if (blocksize != 1024) {
- ptr = ptr + i;
- operand = 1 << remainder;
- status = *ptr & operand;
- if (status)
- return -1;
-
- *ptr = *ptr | operand;
- return 0;
- } else {
- if (remainder == 0) {
- ptr = ptr + i - 1;
- operand = (1 << 7);
- } else {
- ptr = ptr + i;
- operand = (1 << (remainder - 1));
- }
- status = *ptr & operand;
- if (status)
- return -1;
-
- *ptr = *ptr | operand;
- return 0;
- }
-}
-
-void ext4fs_reset_block_bmap(long int blockno, unsigned char *buffer, int index)
-{
- int i, remainder, status;
- unsigned char *ptr = buffer;
- unsigned char operand;
- i = blockno / 8;
- remainder = blockno % 8;
- int blocksize = EXT2_BLOCK_SIZE(ext4fs_root);
-
- i = i - (index * blocksize);
- if (blocksize != 1024) {
- ptr = ptr + i;
- operand = (1 << remainder);
- status = *ptr & operand;
- if (status)
- *ptr = *ptr & ~(operand);
- } else {
- if (remainder == 0) {
- ptr = ptr + i - 1;
- operand = (1 << 7);
- } else {
- ptr = ptr + i;
- operand = (1 << (remainder - 1));
- }
- status = *ptr & operand;
- if (status)
- *ptr = *ptr & ~(operand);
- }
-}
-
-int ext4fs_set_inode_bmap(int inode_no, unsigned char *buffer, int index)
-{
- int i, remainder, status;
- unsigned char *ptr = buffer;
- unsigned char operand;
-
- inode_no -= (index * ext4fs_root->sblock.inodes_per_group);
- i = inode_no / 8;
- remainder = inode_no % 8;
- if (remainder == 0) {
- ptr = ptr + i - 1;
- operand = (1 << 7);
- } else {
- ptr = ptr + i;
- operand = (1 << (remainder - 1));
- }
- status = *ptr & operand;
- if (status)
- return -1;
-
- *ptr = *ptr | operand;
-
- return 0;
-}
-
-void ext4fs_reset_inode_bmap(int inode_no, unsigned char *buffer, int index)
-{
- int i, remainder, status;
- unsigned char *ptr = buffer;
- unsigned char operand;
-
- inode_no -= (index * ext4fs_root->sblock.inodes_per_group);
- i = inode_no / 8;
- remainder = inode_no % 8;
- if (remainder == 0) {
- ptr = ptr + i - 1;
- operand = (1 << 7);
- } else {
- ptr = ptr + i;
- operand = (1 << (remainder - 1));
- }
- status = *ptr & operand;
- if (status)
- *ptr = *ptr & ~(operand);
-}
-
-int ext4fs_checksum_update(unsigned int i)
-{
- struct ext2_block_group *desc;
- struct ext_filesystem *fs = get_fs();
- __u16 crc = 0;
-
- desc = (struct ext2_block_group *)&fs->bgd[i];
- if (fs->sb->feature_ro_compat & EXT4_FEATURE_RO_COMPAT_GDT_CSUM) {
- int offset = offsetof(struct ext2_block_group, bg_checksum);
-
- crc = ext2fs_crc16(~0, fs->sb->unique_id,
- sizeof(fs->sb->unique_id));
- crc = ext2fs_crc16(crc, &i, sizeof(i));
- crc = ext2fs_crc16(crc, desc, offset);
- offset += sizeof(desc->bg_checksum); /* skip checksum */
- assert(offset == sizeof(*desc));
- }
-
- return crc;
-}
-
-static int check_void_in_dentry(struct ext2_dirent *dir, char *filename)
-{
- int dentry_length;
- int sizeof_void_space;
- int new_entry_byte_reqd;
- short padding_factor = 0;
-
- if (dir->namelen % 4 != 0)
- padding_factor = 4 - (dir->namelen % 4);
-
- dentry_length = sizeof(struct ext2_dirent) +
- dir->namelen + padding_factor;
- sizeof_void_space = dir->direntlen - dentry_length;
- if (sizeof_void_space == 0)
- return 0;
-
- padding_factor = 0;
- if (strlen(filename) % 4 != 0)
- padding_factor = 4 - (strlen(filename) % 4);
-
- new_entry_byte_reqd = strlen(filename) +
- sizeof(struct ext2_dirent) + padding_factor;
- if (sizeof_void_space >= new_entry_byte_reqd) {
- dir->direntlen = dentry_length;
- return sizeof_void_space;
- }
-
- return 0;
-}
-
-void ext4fs_update_parent_dentry(char *filename, int *p_ino, int file_type)
-{
- unsigned int *zero_buffer = NULL;
- char *root_first_block_buffer = NULL;
- int direct_blk_idx;
- long int root_blknr;
- long int first_block_no_of_root = 0;
- long int previous_blknr = -1;
- int totalbytes = 0;
- short int padding_factor = 0;
- unsigned int new_entry_byte_reqd;
- unsigned int last_entry_dirlen;
- int sizeof_void_space = 0;
- int templength = 0;
- int inodeno;
- int status;
- struct ext_filesystem *fs = get_fs();
- /* directory entry */
- struct ext2_dirent *dir;
- char *temp_dir = NULL;
-
- zero_buffer = zalloc(fs->blksz);
- if (!zero_buffer) {
- printf("No Memory\n");
- return;
- }
- root_first_block_buffer = zalloc(fs->blksz);
- if (!root_first_block_buffer) {
- free(zero_buffer);
- printf("No Memory\n");
- return;
- }
-restart:
-
- /* read the block no allocated to a file */
- for (direct_blk_idx = 0; direct_blk_idx < INDIRECT_BLOCKS;
- direct_blk_idx++) {
- root_blknr = read_allocated_block(g_parent_inode,
- direct_blk_idx);
- if (root_blknr == 0) {
- first_block_no_of_root = previous_blknr;
- break;
- }
- previous_blknr = root_blknr;
- }
-
- status = ext4fs_devread((lbaint_t)first_block_no_of_root
- * fs->sect_perblk,
- 0, fs->blksz, root_first_block_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(root_first_block_buffer, first_block_no_of_root))
- goto fail;
- dir = (struct ext2_dirent *)root_first_block_buffer;
- totalbytes = 0;
- while (dir->direntlen > 0) {
- /*
- * blocksize-totalbytes because last directory length
- * i.e. dir->direntlen is free availble space in the
- * block that means it is a last entry of directory
- * entry
- */
-
- /* traversing the each directory entry */
- if (fs->blksz - totalbytes == dir->direntlen) {
- if (strlen(filename) % 4 != 0)
- padding_factor = 4 - (strlen(filename) % 4);
-
- new_entry_byte_reqd = strlen(filename) +
- sizeof(struct ext2_dirent) + padding_factor;
- padding_factor = 0;
- /*
- * update last directory entry length to its
- * length because we are creating new directory
- * entry
- */
- if (dir->namelen % 4 != 0)
- padding_factor = 4 - (dir->namelen % 4);
-
- last_entry_dirlen = dir->namelen +
- sizeof(struct ext2_dirent) + padding_factor;
- if ((fs->blksz - totalbytes - last_entry_dirlen) <
- new_entry_byte_reqd) {
- printf("1st Block Full:Allocate new block\n");
-
- if (direct_blk_idx == INDIRECT_BLOCKS - 1) {
- printf("Directory exceeds limit\n");
- goto fail;
- }
- g_parent_inode->b.blocks.dir_blocks
- [direct_blk_idx] = ext4fs_get_new_blk_no();
- if (g_parent_inode->b.blocks.dir_blocks
- [direct_blk_idx] == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- put_ext4(((uint64_t)
- ((uint64_t)g_parent_inode->b.
- blocks.dir_blocks[direct_blk_idx] *
- (uint64_t)fs->blksz)), zero_buffer, fs->blksz);
- g_parent_inode->size =
- g_parent_inode->size + fs->blksz;
- g_parent_inode->blockcnt =
- g_parent_inode->blockcnt + fs->sect_perblk;
- if (ext4fs_put_metadata
- (root_first_block_buffer,
- first_block_no_of_root))
- goto fail;
- goto restart;
- }
- dir->direntlen = last_entry_dirlen;
- break;
- }
-
- templength = dir->direntlen;
- totalbytes = totalbytes + templength;
- sizeof_void_space = check_void_in_dentry(dir, filename);
- if (sizeof_void_space)
- break;
-
- dir = (struct ext2_dirent *)((char *)dir + templength);
- }
-
- /* make a pointer ready for creating next directory entry */
- templength = dir->direntlen;
- totalbytes = totalbytes + templength;
- dir = (struct ext2_dirent *)((char *)dir + templength);
-
- /* get the next available inode number */
- inodeno = ext4fs_get_new_inode_no();
- if (inodeno == -1) {
- printf("no inode left to assign\n");
- goto fail;
- }
- dir->inode = inodeno;
- if (sizeof_void_space)
- dir->direntlen = sizeof_void_space;
- else
- dir->direntlen = fs->blksz - totalbytes;
-
- dir->namelen = strlen(filename);
- dir->filetype = FILETYPE_REG; /* regular file */
- temp_dir = (char *)dir;
- temp_dir = temp_dir + sizeof(struct ext2_dirent);
- memcpy(temp_dir, filename, strlen(filename));
-
- *p_ino = inodeno;
-
- /* update or write the 1st block of root inode */
- if (ext4fs_put_metadata(root_first_block_buffer,
- first_block_no_of_root))
- goto fail;
-
-fail:
- free(zero_buffer);
- free(root_first_block_buffer);
-}
-
-static int search_dir(struct ext2_inode *parent_inode, char *dirname)
-{
- int status;
- int inodeno;
- int totalbytes;
- int templength;
- int direct_blk_idx;
- long int blknr;
- int found = 0;
- char *ptr = NULL;
- unsigned char *block_buffer = NULL;
- struct ext2_dirent *dir = NULL;
- struct ext2_dirent *previous_dir = NULL;
- struct ext_filesystem *fs = get_fs();
-
- /* read the block no allocated to a file */
- for (direct_blk_idx = 0; direct_blk_idx < INDIRECT_BLOCKS;
- direct_blk_idx++) {
- blknr = read_allocated_block(parent_inode, direct_blk_idx);
- if (blknr == 0)
- goto fail;
-
- /* read the blocks of parenet inode */
- block_buffer = zalloc(fs->blksz);
- if (!block_buffer)
- goto fail;
-
- status = ext4fs_devread((lbaint_t)blknr * fs->sect_perblk,
- 0, fs->blksz, (char *)block_buffer);
- if (status == 0)
- goto fail;
-
- dir = (struct ext2_dirent *)block_buffer;
- ptr = (char *)dir;
- totalbytes = 0;
- while (dir->direntlen >= 0) {
- /*
- * blocksize-totalbytes because last directory
- * length i.e.,*dir->direntlen is free availble
- * space in the block that means
- * it is a last entry of directory entry
- */
- if (strlen(dirname) == dir->namelen) {
- if (strncmp(dirname, ptr +
- sizeof(struct ext2_dirent),
- dir->namelen) == 0) {
- previous_dir->direntlen +=
- dir->direntlen;
- inodeno = dir->inode;
- dir->inode = 0;
- found = 1;
- break;
- }
- }
-
- if (fs->blksz - totalbytes == dir->direntlen)
- break;
-
- /* traversing the each directory entry */
- templength = dir->direntlen;
- totalbytes = totalbytes + templength;
- previous_dir = dir;
- dir = (struct ext2_dirent *)((char *)dir + templength);
- ptr = (char *)dir;
- }
-
- if (found == 1) {
- free(block_buffer);
- block_buffer = NULL;
- return inodeno;
- }
-
- free(block_buffer);
- block_buffer = NULL;
- }
-
-fail:
- free(block_buffer);
-
- return -1;
-}
-
-static int find_dir_depth(char *dirname)
-{
- char *token = strtok(dirname, "/");
- int count = 0;
- while (token != NULL) {
- token = strtok(NULL, "/");
- count++;
- }
- return count + 1 + 1;
- /*
- * for example for string /home/temp
- * depth=home(1)+temp(1)+1 extra for NULL;
- * so count is 4;
- */
-}
-
-static int parse_path(char **arr, char *dirname)
-{
- char *token = strtok(dirname, "/");
- int i = 0;
-
- /* add root */
- arr[i] = zalloc(strlen("/") + 1);
- if (!arr[i])
- return -ENOMEM;
-
- arr[i++] = "/";
-
- /* add each path entry after root */
- while (token != NULL) {
- arr[i] = zalloc(strlen(token) + 1);
- if (!arr[i])
- return -ENOMEM;
- memcpy(arr[i++], token, strlen(token));
- token = strtok(NULL, "/");
- }
- arr[i] = NULL;
-
- return 0;
-}
-
-int ext4fs_iget(int inode_no, struct ext2_inode *inode)
-{
- if (ext4fs_read_inode(ext4fs_root, inode_no, inode) == 0)
- return -1;
-
- return 0;
-}
-
-/*
- * Function: ext4fs_get_parent_inode_num
- * Return Value: inode Number of the parent directory of file/Directory to be
- * created
- * dirname : Input parmater, input path name of the file/directory to be created
- * dname : Output parameter, to be filled with the name of the directory
- * extracted from dirname
- */
-int ext4fs_get_parent_inode_num(const char *dirname, char *dname, int flags)
-{
- int i;
- int depth = 0;
- int matched_inode_no;
- int result_inode_no = -1;
- char **ptr = NULL;
- char *depth_dirname = NULL;
- char *parse_dirname = NULL;
- struct ext2_inode *parent_inode = NULL;
- struct ext2_inode *first_inode = NULL;
- struct ext2_inode temp_inode;
-
- if (*dirname != '/') {
- printf("Please supply Absolute path\n");
- return -1;
- }
-
- /* TODO: input validation make equivalent to linux */
- depth_dirname = zalloc(strlen(dirname) + 1);
- if (!depth_dirname)
- return -ENOMEM;
-
- memcpy(depth_dirname, dirname, strlen(dirname));
- depth = find_dir_depth(depth_dirname);
- parse_dirname = zalloc(strlen(dirname) + 1);
- if (!parse_dirname)
- goto fail;
- memcpy(parse_dirname, dirname, strlen(dirname));
-
- /* allocate memory for each directory level */
- ptr = zalloc((depth) * sizeof(char *));
- if (!ptr)
- goto fail;
- if (parse_path(ptr, parse_dirname))
- goto fail;
- parent_inode = zalloc(sizeof(struct ext2_inode));
- if (!parent_inode)
- goto fail;
- first_inode = zalloc(sizeof(struct ext2_inode));
- if (!first_inode)
- goto fail;
- memcpy(parent_inode, ext4fs_root->inode, sizeof(struct ext2_inode));
- memcpy(first_inode, parent_inode, sizeof(struct ext2_inode));
- if (flags & F_FILE)
- result_inode_no = EXT2_ROOT_INO;
- for (i = 1; i < depth; i++) {
- matched_inode_no = search_dir(parent_inode, ptr[i]);
- if (matched_inode_no == -1) {
- if (ptr[i + 1] == NULL && i == 1) {
- result_inode_no = EXT2_ROOT_INO;
- goto end;
- } else {
- if (ptr[i + 1] == NULL)
- break;
- printf("Invalid path\n");
- result_inode_no = -1;
- goto fail;
- }
- } else {
- if (ptr[i + 1] != NULL) {
- memset(parent_inode, '\0',
- sizeof(struct ext2_inode));
- if (ext4fs_iget(matched_inode_no,
- parent_inode)) {
- result_inode_no = -1;
- goto fail;
- }
- result_inode_no = matched_inode_no;
- } else {
- break;
- }
- }
- }
-
-end:
- if (i == 1)
- matched_inode_no = search_dir(first_inode, ptr[i]);
- else
- matched_inode_no = search_dir(parent_inode, ptr[i]);
-
- if (matched_inode_no != -1) {
- ext4fs_iget(matched_inode_no, &temp_inode);
- if (temp_inode.mode & S_IFDIR) {
- printf("It is a Directory\n");
- result_inode_no = -1;
- goto fail;
- }
- }
-
- if (strlen(ptr[i]) > 256) {
- result_inode_no = -1;
- goto fail;
- }
- memcpy(dname, ptr[i], strlen(ptr[i]));
-
-fail:
- free(depth_dirname);
- free(parse_dirname);
- free(ptr);
- free(parent_inode);
- free(first_inode);
-
- return result_inode_no;
-}
-
-static int check_filename(char *filename, unsigned int blknr)
-{
- unsigned int first_block_no_of_root;
- int totalbytes = 0;
- int templength = 0;
- int status, inodeno;
- int found = 0;
- char *root_first_block_buffer = NULL;
- char *root_first_block_addr = NULL;
- struct ext2_dirent *dir = NULL;
- struct ext2_dirent *previous_dir = NULL;
- char *ptr = NULL;
- struct ext_filesystem *fs = get_fs();
-
- /* get the first block of root */
- first_block_no_of_root = blknr;
- root_first_block_buffer = zalloc(fs->blksz);
- if (!root_first_block_buffer)
- return -ENOMEM;
- root_first_block_addr = root_first_block_buffer;
- status = ext4fs_devread((lbaint_t)first_block_no_of_root *
- fs->sect_perblk, 0,
- fs->blksz, root_first_block_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(root_first_block_buffer, first_block_no_of_root))
- goto fail;
- dir = (struct ext2_dirent *)root_first_block_buffer;
- ptr = (char *)dir;
- totalbytes = 0;
- while (dir->direntlen >= 0) {
- /*
- * blocksize-totalbytes because last
- * directory length i.e., *dir->direntlen
- * is free availble space in the block that
- * means it is a last entry of directory entry
- */
- if (strlen(filename) == dir->namelen) {
- if (strncmp(filename, ptr + sizeof(struct ext2_dirent),
- dir->namelen) == 0) {
- printf("file found deleting\n");
- previous_dir->direntlen += dir->direntlen;
- inodeno = dir->inode;
- dir->inode = 0;
- found = 1;
- break;
- }
- }
-
- if (fs->blksz - totalbytes == dir->direntlen)
- break;
-
- /* traversing the each directory entry */
- templength = dir->direntlen;
- totalbytes = totalbytes + templength;
- previous_dir = dir;
- dir = (struct ext2_dirent *)((char *)dir + templength);
- ptr = (char *)dir;
- }
-
-
- if (found == 1) {
- if (ext4fs_put_metadata(root_first_block_addr,
- first_block_no_of_root))
- goto fail;
- return inodeno;
- }
-fail:
- free(root_first_block_buffer);
-
- return -1;
-}
-
-int ext4fs_filename_check(char *filename)
-{
- short direct_blk_idx = 0;
- long int blknr = -1;
- int inodeno = -1;
-
- /* read the block no allocated to a file */
- for (direct_blk_idx = 0; direct_blk_idx < INDIRECT_BLOCKS;
- direct_blk_idx++) {
- blknr = read_allocated_block(g_parent_inode, direct_blk_idx);
- if (blknr == 0)
- break;
- inodeno = check_filename(filename, blknr);
- if (inodeno != -1)
- return inodeno;
- }
-
- return -1;
-}
-
-long int ext4fs_get_new_blk_no(void)
-{
- short i;
- short status;
- int remainder;
- unsigned int bg_idx;
- static int prev_bg_bitmap_index = -1;
- unsigned int blk_per_grp = ext4fs_root->sblock.blocks_per_group;
- struct ext_filesystem *fs = get_fs();
- char *journal_buffer = zalloc(fs->blksz);
- char *zero_buffer = zalloc(fs->blksz);
- if (!journal_buffer || !zero_buffer)
- goto fail;
- struct ext2_block_group *bgd = (struct ext2_block_group *)fs->gdtable;
-
- if (fs->first_pass_bbmap == 0) {
- for (i = 0; i < fs->no_blkgrp; i++) {
- if (bgd[i].free_blocks) {
- if (bgd[i].bg_flags & EXT4_BG_BLOCK_UNINIT) {
- put_ext4(((uint64_t) ((uint64_t)bgd[i].block_id *
- (uint64_t)fs->blksz)),
- zero_buffer, fs->blksz);
- bgd[i].bg_flags =
- bgd[i].
- bg_flags & ~EXT4_BG_BLOCK_UNINIT;
- memcpy(fs->blk_bmaps[i], zero_buffer,
- fs->blksz);
- }
- fs->curr_blkno =
- _get_new_blk_no(fs->blk_bmaps[i]);
- if (fs->curr_blkno == -1)
- /* if block bitmap is completely fill */
- continue;
- fs->curr_blkno = fs->curr_blkno +
- (i * fs->blksz * 8);
- fs->first_pass_bbmap++;
- bgd[i].free_blocks--;
- fs->sb->free_blocks--;
- status = ext4fs_devread((lbaint_t)
- bgd[i].block_id *
- fs->sect_perblk, 0,
- fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer,
- bgd[i].block_id))
- goto fail;
- goto success;
- } else {
- debug("no space left on block group %d\n", i);
- }
- }
-
- goto fail;
- } else {
-restart:
- fs->curr_blkno++;
- /* get the blockbitmap index respective to blockno */
- bg_idx = fs->curr_blkno / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = fs->curr_blkno % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
-
- /*
- * To skip completely filled block group bitmaps
- * Optimize the block allocation
- */
- if (bg_idx >= fs->no_blkgrp)
- goto fail;
-
- if (bgd[bg_idx].free_blocks == 0) {
- debug("block group %u is full. Skipping\n", bg_idx);
- fs->curr_blkno = fs->curr_blkno + blk_per_grp;
- fs->curr_blkno--;
- goto restart;
- }
-
- if (bgd[bg_idx].bg_flags & EXT4_BG_BLOCK_UNINIT) {
- memset(zero_buffer, '\0', fs->blksz);
- put_ext4(((uint64_t) ((uint64_t)bgd[bg_idx].block_id *
- (uint64_t)fs->blksz)), zero_buffer, fs->blksz);
- memcpy(fs->blk_bmaps[bg_idx], zero_buffer, fs->blksz);
- bgd[bg_idx].bg_flags = bgd[bg_idx].bg_flags &
- ~EXT4_BG_BLOCK_UNINIT;
- }
-
- if (ext4fs_set_block_bmap(fs->curr_blkno, fs->blk_bmaps[bg_idx],
- bg_idx) != 0) {
- debug("going for restart for the block no %ld %u\n",
- fs->curr_blkno, bg_idx);
- goto restart;
- }
-
- /* journal backup */
- if (prev_bg_bitmap_index != bg_idx) {
- memset(journal_buffer, '\0', fs->blksz);
- status = ext4fs_devread((lbaint_t)bgd[bg_idx].block_id
- * fs->sect_perblk,
- 0, fs->blksz, journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
-
- prev_bg_bitmap_index = bg_idx;
- }
- bgd[bg_idx].free_blocks--;
- fs->sb->free_blocks--;
- goto success;
- }
-success:
- free(journal_buffer);
- free(zero_buffer);
-
- return fs->curr_blkno;
-fail:
- free(journal_buffer);
- free(zero_buffer);
-
- return -1;
-}
-
-int ext4fs_get_new_inode_no(void)
-{
- short i;
- short status;
- unsigned int ibmap_idx;
- static int prev_inode_bitmap_index = -1;
- unsigned int inodes_per_grp = ext4fs_root->sblock.inodes_per_group;
- struct ext_filesystem *fs = get_fs();
- char *journal_buffer = zalloc(fs->blksz);
- char *zero_buffer = zalloc(fs->blksz);
- if (!journal_buffer || !zero_buffer)
- goto fail;
- struct ext2_block_group *bgd = (struct ext2_block_group *)fs->gdtable;
-
- if (fs->first_pass_ibmap == 0) {
- for (i = 0; i < fs->no_blkgrp; i++) {
- if (bgd[i].free_inodes) {
- if (bgd[i].bg_itable_unused !=
- bgd[i].free_inodes)
- bgd[i].bg_itable_unused =
- bgd[i].free_inodes;
- if (bgd[i].bg_flags & EXT4_BG_INODE_UNINIT) {
- put_ext4(((uint64_t)
- ((uint64_t)bgd[i].inode_id *
- (uint64_t)fs->blksz)),
- zero_buffer, fs->blksz);
- bgd[i].bg_flags = bgd[i].bg_flags &
- ~EXT4_BG_INODE_UNINIT;
- memcpy(fs->inode_bmaps[i],
- zero_buffer, fs->blksz);
- }
- fs->curr_inode_no =
- _get_new_inode_no(fs->inode_bmaps[i]);
- if (fs->curr_inode_no == -1)
- /* if block bitmap is completely fill */
- continue;
- fs->curr_inode_no = fs->curr_inode_no +
- (i * inodes_per_grp);
- fs->first_pass_ibmap++;
- bgd[i].free_inodes--;
- bgd[i].bg_itable_unused--;
- fs->sb->free_inodes--;
- status = ext4fs_devread((lbaint_t)
- bgd[i].inode_id *
- fs->sect_perblk, 0,
- fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer,
- bgd[i].inode_id))
- goto fail;
- goto success;
- } else
- debug("no inode left on block group %d\n", i);
- }
- goto fail;
- } else {
-restart:
- fs->curr_inode_no++;
- /* get the blockbitmap index respective to blockno */
- ibmap_idx = fs->curr_inode_no / inodes_per_grp;
- if (bgd[ibmap_idx].bg_flags & EXT4_BG_INODE_UNINIT) {
- memset(zero_buffer, '\0', fs->blksz);
- put_ext4(((uint64_t) ((uint64_t)bgd[ibmap_idx].inode_id *
- (uint64_t)fs->blksz)), zero_buffer,
- fs->blksz);
- bgd[ibmap_idx].bg_flags =
- bgd[ibmap_idx].bg_flags & ~EXT4_BG_INODE_UNINIT;
- memcpy(fs->inode_bmaps[ibmap_idx], zero_buffer,
- fs->blksz);
- }
-
- if (ext4fs_set_inode_bmap(fs->curr_inode_no,
- fs->inode_bmaps[ibmap_idx],
- ibmap_idx) != 0) {
- debug("going for restart for the block no %d %u\n",
- fs->curr_inode_no, ibmap_idx);
- goto restart;
- }
-
- /* journal backup */
- if (prev_inode_bitmap_index != ibmap_idx) {
- memset(journal_buffer, '\0', fs->blksz);
- status = ext4fs_devread((lbaint_t)
- bgd[ibmap_idx].inode_id
- * fs->sect_perblk,
- 0, fs->blksz, journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer,
- bgd[ibmap_idx].inode_id))
- goto fail;
- prev_inode_bitmap_index = ibmap_idx;
- }
- if (bgd[ibmap_idx].bg_itable_unused !=
- bgd[ibmap_idx].free_inodes)
- bgd[ibmap_idx].bg_itable_unused =
- bgd[ibmap_idx].free_inodes;
- bgd[ibmap_idx].free_inodes--;
- bgd[ibmap_idx].bg_itable_unused--;
- fs->sb->free_inodes--;
- goto success;
- }
-
-success:
- free(journal_buffer);
- free(zero_buffer);
-
- return fs->curr_inode_no;
-fail:
- free(journal_buffer);
- free(zero_buffer);
-
- return -1;
-
-}
-
-
-static void alloc_single_indirect_block(struct ext2_inode *file_inode,
- unsigned int *total_remaining_blocks,
- unsigned int *no_blks_reqd)
-{
- short i;
- short status;
- long int actual_block_no;
- long int si_blockno;
- /* si :single indirect */
- unsigned int *si_buffer = NULL;
- unsigned int *si_start_addr = NULL;
- struct ext_filesystem *fs = get_fs();
-
- if (*total_remaining_blocks != 0) {
- si_buffer = zalloc(fs->blksz);
- if (!si_buffer) {
- printf("No Memory\n");
- return;
- }
- si_start_addr = si_buffer;
- si_blockno = ext4fs_get_new_blk_no();
- if (si_blockno == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- (*no_blks_reqd)++;
- debug("SIPB %ld: %u\n", si_blockno, *total_remaining_blocks);
-
- status = ext4fs_devread((lbaint_t)si_blockno * fs->sect_perblk,
- 0, fs->blksz, (char *)si_buffer);
- memset(si_buffer, '\0', fs->blksz);
- if (status == 0)
- goto fail;
-
- for (i = 0; i < (fs->blksz / sizeof(int)); i++) {
- actual_block_no = ext4fs_get_new_blk_no();
- if (actual_block_no == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- *si_buffer = actual_block_no;
- debug("SIAB %u: %u\n", *si_buffer,
- *total_remaining_blocks);
-
- si_buffer++;
- (*total_remaining_blocks)--;
- if (*total_remaining_blocks == 0)
- break;
- }
-
- /* write the block to disk */
- put_ext4(((uint64_t) ((uint64_t)si_blockno * (uint64_t)fs->blksz)),
- si_start_addr, fs->blksz);
- file_inode->b.blocks.indir_block = si_blockno;
- }
-fail:
- free(si_start_addr);
-}
-
-static void alloc_double_indirect_block(struct ext2_inode *file_inode,
- unsigned int *total_remaining_blocks,
- unsigned int *no_blks_reqd)
-{
- short i;
- short j;
- short status;
- long int actual_block_no;
- /* di:double indirect */
- long int di_blockno_parent;
- long int di_blockno_child;
- unsigned int *di_parent_buffer = NULL;
- unsigned int *di_child_buff = NULL;
- unsigned int *di_block_start_addr = NULL;
- unsigned int *di_child_buff_start = NULL;
- struct ext_filesystem *fs = get_fs();
-
- if (*total_remaining_blocks != 0) {
- /* double indirect parent block connecting to inode */
- di_blockno_parent = ext4fs_get_new_blk_no();
- if (di_blockno_parent == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- di_parent_buffer = zalloc(fs->blksz);
- if (!di_parent_buffer)
- goto fail;
-
- di_block_start_addr = di_parent_buffer;
- (*no_blks_reqd)++;
- debug("DIPB %ld: %u\n", di_blockno_parent,
- *total_remaining_blocks);
-
- status = ext4fs_devread((lbaint_t)di_blockno_parent *
- fs->sect_perblk, 0,
- fs->blksz, (char *)di_parent_buffer);
-
- if (!status) {
- printf("%s: Device read error!\n", __func__);
- goto fail;
- }
- memset(di_parent_buffer, '\0', fs->blksz);
-
- /*
- * start:for each double indirect parent
- * block create one more block
- */
- for (i = 0; i < (fs->blksz / sizeof(int)); i++) {
- di_blockno_child = ext4fs_get_new_blk_no();
- if (di_blockno_child == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- di_child_buff = zalloc(fs->blksz);
- if (!di_child_buff)
- goto fail;
-
- di_child_buff_start = di_child_buff;
- *di_parent_buffer = di_blockno_child;
- di_parent_buffer++;
- (*no_blks_reqd)++;
- debug("DICB %ld: %u\n", di_blockno_child,
- *total_remaining_blocks);
-
- status = ext4fs_devread((lbaint_t)di_blockno_child *
- fs->sect_perblk, 0,
- fs->blksz,
- (char *)di_child_buff);
-
- if (!status) {
- printf("%s: Device read error!\n", __func__);
- goto fail;
- }
- memset(di_child_buff, '\0', fs->blksz);
- /* filling of actual datablocks for each child */
- for (j = 0; j < (fs->blksz / sizeof(int)); j++) {
- actual_block_no = ext4fs_get_new_blk_no();
- if (actual_block_no == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- *di_child_buff = actual_block_no;
- debug("DIAB %ld: %u\n", actual_block_no,
- *total_remaining_blocks);
-
- di_child_buff++;
- (*total_remaining_blocks)--;
- if (*total_remaining_blocks == 0)
- break;
- }
- /* write the block table */
- put_ext4(((uint64_t) ((uint64_t)di_blockno_child * (uint64_t)fs->blksz)),
- di_child_buff_start, fs->blksz);
- free(di_child_buff_start);
- di_child_buff_start = NULL;
-
- if (*total_remaining_blocks == 0)
- break;
- }
- put_ext4(((uint64_t) ((uint64_t)di_blockno_parent * (uint64_t)fs->blksz)),
- di_block_start_addr, fs->blksz);
- file_inode->b.blocks.double_indir_block = di_blockno_parent;
- }
-fail:
- free(di_block_start_addr);
-}
-
-static void alloc_triple_indirect_block(struct ext2_inode *file_inode,
- unsigned int *total_remaining_blocks,
- unsigned int *no_blks_reqd)
-{
- short i;
- short j;
- short k;
- long int actual_block_no;
- /* ti: Triple Indirect */
- long int ti_gp_blockno;
- long int ti_parent_blockno;
- long int ti_child_blockno;
- unsigned int *ti_gp_buff = NULL;
- unsigned int *ti_parent_buff = NULL;
- unsigned int *ti_child_buff = NULL;
- unsigned int *ti_gp_buff_start_addr = NULL;
- unsigned int *ti_pbuff_start_addr = NULL;
- unsigned int *ti_cbuff_start_addr = NULL;
- struct ext_filesystem *fs = get_fs();
- if (*total_remaining_blocks != 0) {
- /* triple indirect grand parent block connecting to inode */
- ti_gp_blockno = ext4fs_get_new_blk_no();
- if (ti_gp_blockno == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- ti_gp_buff = zalloc(fs->blksz);
- if (!ti_gp_buff)
- goto fail;
-
- ti_gp_buff_start_addr = ti_gp_buff;
- (*no_blks_reqd)++;
- debug("TIGPB %ld: %u\n", ti_gp_blockno,
- *total_remaining_blocks);
-
- /* for each 4 byte grand parent entry create one more block */
- for (i = 0; i < (fs->blksz / sizeof(int)); i++) {
- ti_parent_blockno = ext4fs_get_new_blk_no();
- if (ti_parent_blockno == -1) {
- printf("no block left to assign\n");
- goto fail;
- }
- ti_parent_buff = zalloc(fs->blksz);
- if (!ti_parent_buff)
- goto fail;
-
- ti_pbuff_start_addr = ti_parent_buff;
- *ti_gp_buff = ti_parent_blockno;
- ti_gp_buff++;
- (*no_blks_reqd)++;
- debug("TIPB %ld: %u\n", ti_parent_blockno,
- *total_remaining_blocks);
-
- /* for each 4 byte entry parent create one more block */
- for (j = 0; j < (fs->blksz / sizeof(int)); j++) {
- ti_child_blockno = ext4fs_get_new_blk_no();
- if (ti_child_blockno == -1) {
- printf("no block left assign\n");
- goto fail;
- }
- ti_child_buff = zalloc(fs->blksz);
- if (!ti_child_buff)
- goto fail;
-
- ti_cbuff_start_addr = ti_child_buff;
- *ti_parent_buff = ti_child_blockno;
- ti_parent_buff++;
- (*no_blks_reqd)++;
- debug("TICB %ld: %u\n", ti_parent_blockno,
- *total_remaining_blocks);
-
- /* fill actual datablocks for each child */
- for (k = 0; k < (fs->blksz / sizeof(int));
- k++) {
- actual_block_no =
- ext4fs_get_new_blk_no();
- if (actual_block_no == -1) {
- printf("no block left\n");
- goto fail;
- }
- *ti_child_buff = actual_block_no;
- debug("TIAB %ld: %u\n", actual_block_no,
- *total_remaining_blocks);
-
- ti_child_buff++;
- (*total_remaining_blocks)--;
- if (*total_remaining_blocks == 0)
- break;
- }
- /* write the child block */
- put_ext4(((uint64_t) ((uint64_t)ti_child_blockno *
- (uint64_t)fs->blksz)),
- ti_cbuff_start_addr, fs->blksz);
- free(ti_cbuff_start_addr);
-
- if (*total_remaining_blocks == 0)
- break;
- }
- /* write the parent block */
- put_ext4(((uint64_t) ((uint64_t)ti_parent_blockno * (uint64_t)fs->blksz)),
- ti_pbuff_start_addr, fs->blksz);
- free(ti_pbuff_start_addr);
-
- if (*total_remaining_blocks == 0)
- break;
- }
- /* write the grand parent block */
- put_ext4(((uint64_t) ((uint64_t)ti_gp_blockno * (uint64_t)fs->blksz)),
- ti_gp_buff_start_addr, fs->blksz);
- file_inode->b.blocks.triple_indir_block = ti_gp_blockno;
- }
-fail:
- free(ti_gp_buff_start_addr);
-}
-
-void ext4fs_allocate_blocks(struct ext2_inode *file_inode,
- unsigned int total_remaining_blocks,
- unsigned int *total_no_of_block)
-{
- short i;
- long int direct_blockno;
- unsigned int no_blks_reqd = 0;
-
- /* allocation of direct blocks */
- for (i = 0; i < INDIRECT_BLOCKS; i++) {
- direct_blockno = ext4fs_get_new_blk_no();
- if (direct_blockno == -1) {
- printf("no block left to assign\n");
- return;
- }
- file_inode->b.blocks.dir_blocks[i] = direct_blockno;
- debug("DB %ld: %u\n", direct_blockno, total_remaining_blocks);
-
- total_remaining_blocks--;
- if (total_remaining_blocks == 0)
- break;
- }
-
- alloc_single_indirect_block(file_inode, &total_remaining_blocks,
- &no_blks_reqd);
- alloc_double_indirect_block(file_inode, &total_remaining_blocks,
- &no_blks_reqd);
- alloc_triple_indirect_block(file_inode, &total_remaining_blocks,
- &no_blks_reqd);
- *total_no_of_block += no_blks_reqd;
-}
-
-#endif
-
-static struct ext4_extent_header *ext4fs_get_extent_block
- (struct ext2_data *data, char *buf,
- struct ext4_extent_header *ext_block,
- uint32_t fileblock, int log2_blksz)
-{
- struct ext4_extent_idx *index;
- unsigned long long block;
- int blksz = EXT2_BLOCK_SIZE(data);
- int i;
-
- while (1) {
- index = (struct ext4_extent_idx *)(ext_block + 1);
-
- if (le16_to_cpu(ext_block->eh_magic) != EXT4_EXT_MAGIC)
- return 0;
-
- if (ext_block->eh_depth == 0)
- return ext_block;
- i = -1;
- do {
- i++;
- if (i >= le16_to_cpu(ext_block->eh_entries))
- break;
- } while (fileblock >= le32_to_cpu(index[i].ei_block));
-
- if (--i < 0)
- return 0;
-
- block = le16_to_cpu(index[i].ei_leaf_hi);
- block = (block << 32) + le32_to_cpu(index[i].ei_leaf_lo);
-
- if (ext4fs_devread((lbaint_t)block << log2_blksz, 0, blksz,
- buf))
- ext_block = (struct ext4_extent_header *)buf;
- else
- return 0;
- }
-}
-
-static int ext4fs_blockgroup
- (struct ext2_data *data, int group, struct ext2_block_group *blkgrp)
-{
- long int blkno;
- unsigned int blkoff, desc_per_blk;
- int log2blksz = get_fs()->dev_desc->log2blksz;
-
- desc_per_blk = EXT2_BLOCK_SIZE(data) / sizeof(struct ext2_block_group);
-
- blkno = __le32_to_cpu(data->sblock.first_data_block) + 1 +
- group / desc_per_blk;
- blkoff = (group % desc_per_blk) * sizeof(struct ext2_block_group);
-
- debug("ext4fs read %d group descriptor (blkno %ld blkoff %u)\n",
- group, blkno, blkoff);
-
- return ext4fs_devread((lbaint_t)blkno <<
- (LOG2_BLOCK_SIZE(data) - log2blksz),
- blkoff, sizeof(struct ext2_block_group),
- (char *)blkgrp);
-}
-
-int ext4fs_read_inode(struct ext2_data *data, int ino, struct ext2_inode *inode)
-{
- struct ext2_block_group blkgrp;
- struct ext2_sblock *sblock = &data->sblock;
- struct ext_filesystem *fs = get_fs();
- int log2blksz = get_fs()->dev_desc->log2blksz;
- int inodes_per_block, status;
- long int blkno;
- unsigned int blkoff;
-
- /* It is easier to calculate if the first inode is 0. */
- ino--;
- status = ext4fs_blockgroup(data, ino / __le32_to_cpu
- (sblock->inodes_per_group), &blkgrp);
- if (status == 0)
- return 0;
-
- inodes_per_block = EXT2_BLOCK_SIZE(data) / fs->inodesz;
- blkno = __le32_to_cpu(blkgrp.inode_table_id) +
- (ino % __le32_to_cpu(sblock->inodes_per_group)) / inodes_per_block;
- blkoff = (ino % inodes_per_block) * fs->inodesz;
- /* Read the inode. */
- status = ext4fs_devread((lbaint_t)blkno << (LOG2_BLOCK_SIZE(data) -
- log2blksz), blkoff,
- sizeof(struct ext2_inode), (char *)inode);
- if (status == 0)
- return 0;
-
- return 1;
-}
-
-long int read_allocated_block(struct ext2_inode *inode, int fileblock)
-{
- long int blknr;
- int blksz;
- int log2_blksz;
- int status;
- long int rblock;
- long int perblock_parent;
- long int perblock_child;
- unsigned long long start;
- /* get the blocksize of the filesystem */
- blksz = EXT2_BLOCK_SIZE(ext4fs_root);
- log2_blksz = LOG2_BLOCK_SIZE(ext4fs_root)
- - get_fs()->dev_desc->log2blksz;
-
- if (le32_to_cpu(inode->flags) & EXT4_EXTENTS_FL) {
- char *buf = zalloc(blksz);
- if (!buf)
- return -ENOMEM;
- struct ext4_extent_header *ext_block;
- struct ext4_extent *extent;
- int i = -1;
- ext_block =
- ext4fs_get_extent_block(ext4fs_root, buf,
- (struct ext4_extent_header *)
- inode->b.blocks.dir_blocks,
- fileblock, log2_blksz);
- if (!ext_block) {
- printf("invalid extent block\n");
- free(buf);
- return -EINVAL;
- }
-
- extent = (struct ext4_extent *)(ext_block + 1);
-
- do {
- i++;
- if (i >= le16_to_cpu(ext_block->eh_entries))
- break;
- } while (fileblock >= le32_to_cpu(extent[i].ee_block));
- if (--i >= 0) {
- fileblock -= le32_to_cpu(extent[i].ee_block);
- if (fileblock >= le16_to_cpu(extent[i].ee_len)) {
- free(buf);
- return 0;
- }
-
- start = le16_to_cpu(extent[i].ee_start_hi);
- start = (start << 32) +
- le32_to_cpu(extent[i].ee_start_lo);
- free(buf);
- return fileblock + start;
- }
-
- printf("Extent Error\n");
- free(buf);
- return -1;
- }
-
- /* Direct blocks. */
- if (fileblock < INDIRECT_BLOCKS)
- blknr = __le32_to_cpu(inode->b.blocks.dir_blocks[fileblock]);
-
- /* Indirect. */
- else if (fileblock < (INDIRECT_BLOCKS + (blksz / 4))) {
- if (ext4fs_indir1_block == NULL) {
- ext4fs_indir1_block = zalloc(blksz);
- if (ext4fs_indir1_block == NULL) {
- printf("** SI ext2fs read block (indir 1)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir1_size = blksz;
- ext4fs_indir1_blkno = -1;
- }
- if (blksz != ext4fs_indir1_size) {
- free(ext4fs_indir1_block);
- ext4fs_indir1_block = NULL;
- ext4fs_indir1_size = 0;
- ext4fs_indir1_blkno = -1;
- ext4fs_indir1_block = zalloc(blksz);
- if (ext4fs_indir1_block == NULL) {
- printf("** SI ext2fs read block (indir 1):"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir1_size = blksz;
- }
- if ((__le32_to_cpu(inode->b.blocks.indir_block) <<
- log2_blksz) != ext4fs_indir1_blkno) {
- status =
- ext4fs_devread((lbaint_t)__le32_to_cpu
- (inode->b.blocks.
- indir_block) << log2_blksz, 0,
- blksz, (char *)ext4fs_indir1_block);
- if (status == 0) {
- printf("** SI ext2fs read block (indir 1)"
- "failed. **\n");
- return 0;
- }
- ext4fs_indir1_blkno =
- __le32_to_cpu(inode->b.blocks.
- indir_block) << log2_blksz;
- }
- blknr = __le32_to_cpu(ext4fs_indir1_block
- [fileblock - INDIRECT_BLOCKS]);
- }
- /* Double indirect. */
- else if (fileblock < (INDIRECT_BLOCKS + (blksz / 4 *
- (blksz / 4 + 1)))) {
-
- long int perblock = blksz / 4;
- long int rblock = fileblock - (INDIRECT_BLOCKS + blksz / 4);
-
- if (ext4fs_indir1_block == NULL) {
- ext4fs_indir1_block = zalloc(blksz);
- if (ext4fs_indir1_block == NULL) {
- printf("** DI ext2fs read block (indir 2 1)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir1_size = blksz;
- ext4fs_indir1_blkno = -1;
- }
- if (blksz != ext4fs_indir1_size) {
- free(ext4fs_indir1_block);
- ext4fs_indir1_block = NULL;
- ext4fs_indir1_size = 0;
- ext4fs_indir1_blkno = -1;
- ext4fs_indir1_block = zalloc(blksz);
- if (ext4fs_indir1_block == NULL) {
- printf("** DI ext2fs read block (indir 2 1)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir1_size = blksz;
- }
- if ((__le32_to_cpu(inode->b.blocks.double_indir_block) <<
- log2_blksz) != ext4fs_indir1_blkno) {
- status =
- ext4fs_devread((lbaint_t)__le32_to_cpu
- (inode->b.blocks.
- double_indir_block) << log2_blksz,
- 0, blksz,
- (char *)ext4fs_indir1_block);
- if (status == 0) {
- printf("** DI ext2fs read block (indir 2 1)"
- "failed. **\n");
- return -1;
- }
- ext4fs_indir1_blkno =
- __le32_to_cpu(inode->b.blocks.double_indir_block) <<
- log2_blksz;
- }
-
- if (ext4fs_indir2_block == NULL) {
- ext4fs_indir2_block = zalloc(blksz);
- if (ext4fs_indir2_block == NULL) {
- printf("** DI ext2fs read block (indir 2 2)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir2_size = blksz;
- ext4fs_indir2_blkno = -1;
- }
- if (blksz != ext4fs_indir2_size) {
- free(ext4fs_indir2_block);
- ext4fs_indir2_block = NULL;
- ext4fs_indir2_size = 0;
- ext4fs_indir2_blkno = -1;
- ext4fs_indir2_block = zalloc(blksz);
- if (ext4fs_indir2_block == NULL) {
- printf("** DI ext2fs read block (indir 2 2)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir2_size = blksz;
- }
- if ((__le32_to_cpu(ext4fs_indir1_block[rblock / perblock]) <<
- log2_blksz) != ext4fs_indir2_blkno) {
- status = ext4fs_devread((lbaint_t)__le32_to_cpu
- (ext4fs_indir1_block
- [rblock /
- perblock]) << log2_blksz, 0,
- blksz,
- (char *)ext4fs_indir2_block);
- if (status == 0) {
- printf("** DI ext2fs read block (indir 2 2)"
- "failed. **\n");
- return -1;
- }
- ext4fs_indir2_blkno =
- __le32_to_cpu(ext4fs_indir1_block[rblock
- /
- perblock]) <<
- log2_blksz;
- }
- blknr = __le32_to_cpu(ext4fs_indir2_block[rblock % perblock]);
- }
- /* Tripple indirect. */
- else {
- rblock = fileblock - (INDIRECT_BLOCKS + blksz / 4 +
- (blksz / 4 * blksz / 4));
- perblock_child = blksz / 4;
- perblock_parent = ((blksz / 4) * (blksz / 4));
-
- if (ext4fs_indir1_block == NULL) {
- ext4fs_indir1_block = zalloc(blksz);
- if (ext4fs_indir1_block == NULL) {
- printf("** TI ext2fs read block (indir 2 1)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir1_size = blksz;
- ext4fs_indir1_blkno = -1;
- }
- if (blksz != ext4fs_indir1_size) {
- free(ext4fs_indir1_block);
- ext4fs_indir1_block = NULL;
- ext4fs_indir1_size = 0;
- ext4fs_indir1_blkno = -1;
- ext4fs_indir1_block = zalloc(blksz);
- if (ext4fs_indir1_block == NULL) {
- printf("** TI ext2fs read block (indir 2 1)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir1_size = blksz;
- }
- if ((__le32_to_cpu(inode->b.blocks.triple_indir_block) <<
- log2_blksz) != ext4fs_indir1_blkno) {
- status = ext4fs_devread
- ((lbaint_t)
- __le32_to_cpu(inode->b.blocks.triple_indir_block)
- << log2_blksz, 0, blksz,
- (char *)ext4fs_indir1_block);
- if (status == 0) {
- printf("** TI ext2fs read block (indir 2 1)"
- "failed. **\n");
- return -1;
- }
- ext4fs_indir1_blkno =
- __le32_to_cpu(inode->b.blocks.triple_indir_block) <<
- log2_blksz;
- }
-
- if (ext4fs_indir2_block == NULL) {
- ext4fs_indir2_block = zalloc(blksz);
- if (ext4fs_indir2_block == NULL) {
- printf("** TI ext2fs read block (indir 2 2)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir2_size = blksz;
- ext4fs_indir2_blkno = -1;
- }
- if (blksz != ext4fs_indir2_size) {
- free(ext4fs_indir2_block);
- ext4fs_indir2_block = NULL;
- ext4fs_indir2_size = 0;
- ext4fs_indir2_blkno = -1;
- ext4fs_indir2_block = zalloc(blksz);
- if (ext4fs_indir2_block == NULL) {
- printf("** TI ext2fs read block (indir 2 2)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir2_size = blksz;
- }
- if ((__le32_to_cpu(ext4fs_indir1_block[rblock /
- perblock_parent]) <<
- log2_blksz)
- != ext4fs_indir2_blkno) {
- status = ext4fs_devread((lbaint_t)__le32_to_cpu
- (ext4fs_indir1_block
- [rblock /
- perblock_parent]) <<
- log2_blksz, 0, blksz,
- (char *)ext4fs_indir2_block);
- if (status == 0) {
- printf("** TI ext2fs read block (indir 2 2)"
- "failed. **\n");
- return -1;
- }
- ext4fs_indir2_blkno =
- __le32_to_cpu(ext4fs_indir1_block[rblock /
- perblock_parent])
- << log2_blksz;
- }
-
- if (ext4fs_indir3_block == NULL) {
- ext4fs_indir3_block = zalloc(blksz);
- if (ext4fs_indir3_block == NULL) {
- printf("** TI ext2fs read block (indir 2 2)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir3_size = blksz;
- ext4fs_indir3_blkno = -1;
- }
- if (blksz != ext4fs_indir3_size) {
- free(ext4fs_indir3_block);
- ext4fs_indir3_block = NULL;
- ext4fs_indir3_size = 0;
- ext4fs_indir3_blkno = -1;
- ext4fs_indir3_block = zalloc(blksz);
- if (ext4fs_indir3_block == NULL) {
- printf("** TI ext2fs read block (indir 2 2)"
- "malloc failed. **\n");
- return -1;
- }
- ext4fs_indir3_size = blksz;
- }
- if ((__le32_to_cpu(ext4fs_indir2_block[rblock
- /
- perblock_child]) <<
- log2_blksz) != ext4fs_indir3_blkno) {
- status =
- ext4fs_devread((lbaint_t)__le32_to_cpu
- (ext4fs_indir2_block
- [(rblock / perblock_child)
- % (blksz / 4)]) << log2_blksz, 0,
- blksz, (char *)ext4fs_indir3_block);
- if (status == 0) {
- printf("** TI ext2fs read block (indir 2 2)"
- "failed. **\n");
- return -1;
- }
- ext4fs_indir3_blkno =
- __le32_to_cpu(ext4fs_indir2_block[(rblock /
- perblock_child) %
- (blksz /
- 4)]) <<
- log2_blksz;
- }
-
- blknr = __le32_to_cpu(ext4fs_indir3_block
- [rblock % perblock_child]);
- }
- debug("read_allocated_block %ld\n", blknr);
-
- return blknr;
-}
-
-/**
- * ext4fs_reinit_global() - Reinitialize values of ext4 write implementation's
- * global pointers
- *
- * This function assures that for a file with the same name but different size
- * the sequential store on the ext4 filesystem will be correct.
- *
- * In this function the global data, responsible for internal representation
- * of the ext4 data are initialized to the reset state. Without this, during
- * replacement of the smaller file with the bigger truncation of new file was
- * performed.
- */
-void ext4fs_reinit_global(void)
-{
- if (ext4fs_indir1_block != NULL) {
- free(ext4fs_indir1_block);
- ext4fs_indir1_block = NULL;
- ext4fs_indir1_size = 0;
- ext4fs_indir1_blkno = -1;
- }
- if (ext4fs_indir2_block != NULL) {
- free(ext4fs_indir2_block);
- ext4fs_indir2_block = NULL;
- ext4fs_indir2_size = 0;
- ext4fs_indir2_blkno = -1;
- }
- if (ext4fs_indir3_block != NULL) {
- free(ext4fs_indir3_block);
- ext4fs_indir3_block = NULL;
- ext4fs_indir3_size = 0;
- ext4fs_indir3_blkno = -1;
- }
-}
-void ext4fs_close(void)
-{
- if ((ext4fs_file != NULL) && (ext4fs_root != NULL)) {
- ext4fs_free_node(ext4fs_file, &ext4fs_root->diropen);
- ext4fs_file = NULL;
- }
- if (ext4fs_root != NULL) {
- free(ext4fs_root);
- ext4fs_root = NULL;
- }
-
- ext4fs_reinit_global();
-}
-
-int ext4fs_iterate_dir(struct ext2fs_node *dir, char *name,
- struct ext2fs_node **fnode, int *ftype)
-{
- unsigned int fpos = 0;
- int status;
- struct ext2fs_node *diro = (struct ext2fs_node *) dir;
-
-#ifdef DEBUG
- if (name != NULL)
- printf("Iterate dir %s\n", name);
-#endif /* of DEBUG */
- if (!diro->inode_read) {
- status = ext4fs_read_inode(diro->data, diro->ino, &diro->inode);
- if (status == 0)
- return 0;
- }
- /* Search the file. */
- while (fpos < __le32_to_cpu(diro->inode.size)) {
- struct ext2_dirent dirent;
-
- status = ext4fs_read_file(diro, fpos,
- sizeof(struct ext2_dirent),
- (char *) &dirent);
- if (status < 1)
- return 0;
-
- if (dirent.namelen != 0) {
- char filename[dirent.namelen + 1];
- struct ext2fs_node *fdiro;
- int type = FILETYPE_UNKNOWN;
-
- status = ext4fs_read_file(diro,
- fpos +
- sizeof(struct ext2_dirent),
- dirent.namelen, filename);
- if (status < 1)
- return 0;
-
- fdiro = zalloc(sizeof(struct ext2fs_node));
- if (!fdiro)
- return 0;
-
- fdiro->data = diro->data;
- fdiro->ino = __le32_to_cpu(dirent.inode);
-
- filename[dirent.namelen] = '\0';
-
- if (dirent.filetype != FILETYPE_UNKNOWN) {
- fdiro->inode_read = 0;
-
- if (dirent.filetype == FILETYPE_DIRECTORY)
- type = FILETYPE_DIRECTORY;
- else if (dirent.filetype == FILETYPE_SYMLINK)
- type = FILETYPE_SYMLINK;
- else if (dirent.filetype == FILETYPE_REG)
- type = FILETYPE_REG;
- } else {
- status = ext4fs_read_inode(diro->data,
- __le32_to_cpu
- (dirent.inode),
- &fdiro->inode);
- if (status == 0) {
- free(fdiro);
- return 0;
- }
- fdiro->inode_read = 1;
-
- if ((__le16_to_cpu(fdiro->inode.mode) &
- FILETYPE_INO_MASK) ==
- FILETYPE_INO_DIRECTORY) {
- type = FILETYPE_DIRECTORY;
- } else if ((__le16_to_cpu(fdiro->inode.mode)
- & FILETYPE_INO_MASK) ==
- FILETYPE_INO_SYMLINK) {
- type = FILETYPE_SYMLINK;
- } else if ((__le16_to_cpu(fdiro->inode.mode)
- & FILETYPE_INO_MASK) ==
- FILETYPE_INO_REG) {
- type = FILETYPE_REG;
- }
- }
-#ifdef DEBUG
- printf("iterate >%s<\n", filename);
-#endif /* of DEBUG */
- if ((name != NULL) && (fnode != NULL)
- && (ftype != NULL)) {
- if (strcmp(filename, name) == 0) {
- *ftype = type;
- *fnode = fdiro;
- return 1;
- }
- } else {
- if (fdiro->inode_read == 0) {
- status = ext4fs_read_inode(diro->data,
- __le32_to_cpu(
- dirent.inode),
- &fdiro->inode);
- if (status == 0) {
- free(fdiro);
- return 0;
- }
- fdiro->inode_read = 1;
- }
- switch (type) {
- case FILETYPE_DIRECTORY:
- printf("<DIR> ");
- break;
- case FILETYPE_SYMLINK:
- printf("<SYM> ");
- break;
- case FILETYPE_REG:
- printf(" ");
- break;
- default:
- printf("< ? > ");
- break;
- }
- printf("%10d %s\n",
- __le32_to_cpu(fdiro->inode.size),
- filename);
- }
- free(fdiro);
- }
- fpos += __le16_to_cpu(dirent.direntlen);
- }
- return 0;
-}
-
-static char *ext4fs_read_symlink(struct ext2fs_node *node)
-{
- char *symlink;
- struct ext2fs_node *diro = node;
- int status;
-
- if (!diro->inode_read) {
- status = ext4fs_read_inode(diro->data, diro->ino, &diro->inode);
- if (status == 0)
- return 0;
- }
- symlink = zalloc(__le32_to_cpu(diro->inode.size) + 1);
- if (!symlink)
- return 0;
-
- if (__le32_to_cpu(diro->inode.size) <= 60) {
- strncpy(symlink, diro->inode.b.symlink,
- __le32_to_cpu(diro->inode.size));
- } else {
- status = ext4fs_read_file(diro, 0,
- __le32_to_cpu(diro->inode.size),
- symlink);
- if (status == 0) {
- free(symlink);
- return 0;
- }
- }
- symlink[__le32_to_cpu(diro->inode.size)] = '\0';
- return symlink;
-}
-
-static int ext4fs_find_file1(const char *currpath,
- struct ext2fs_node *currroot,
- struct ext2fs_node **currfound, int *foundtype)
-{
- char fpath[strlen(currpath) + 1];
- char *name = fpath;
- char *next;
- int status;
- int type = FILETYPE_DIRECTORY;
- struct ext2fs_node *currnode = currroot;
- struct ext2fs_node *oldnode = currroot;
-
- strncpy(fpath, currpath, strlen(currpath) + 1);
-
- /* Remove all leading slashes. */
- while (*name == '/')
- name++;
-
- if (!*name) {
- *currfound = currnode;
- return 1;
- }
-
- for (;;) {
- int found;
-
- /* Extract the actual part from the pathname. */
- next = strchr(name, '/');
- if (next) {
- /* Remove all leading slashes. */
- while (*next == '/')
- *(next++) = '\0';
- }
-
- if (type != FILETYPE_DIRECTORY) {
- ext4fs_free_node(currnode, currroot);
- return 0;
- }
-
- oldnode = currnode;
-
- /* Iterate over the directory. */
- found = ext4fs_iterate_dir(currnode, name, &currnode, &type);
- if (found == 0)
- return 0;
-
- if (found == -1)
- break;
-
- /* Read in the symlink and follow it. */
- if (type == FILETYPE_SYMLINK) {
- char *symlink;
-
- /* Test if the symlink does not loop. */
- if (++symlinknest == 8) {
- ext4fs_free_node(currnode, currroot);
- ext4fs_free_node(oldnode, currroot);
- return 0;
- }
-
- symlink = ext4fs_read_symlink(currnode);
- ext4fs_free_node(currnode, currroot);
-
- if (!symlink) {
- ext4fs_free_node(oldnode, currroot);
- return 0;
- }
-
- debug("Got symlink >%s<\n", symlink);
-
- if (symlink[0] == '/') {
- ext4fs_free_node(oldnode, currroot);
- oldnode = &ext4fs_root->diropen;
- }
-
- /* Lookup the node the symlink points to. */
- status = ext4fs_find_file1(symlink, oldnode,
- &currnode, &type);
-
- free(symlink);
-
- if (status == 0) {
- ext4fs_free_node(oldnode, currroot);
- return 0;
- }
- }
-
- ext4fs_free_node(oldnode, currroot);
-
- /* Found the node! */
- if (!next || *next == '\0') {
- *currfound = currnode;
- *foundtype = type;
- return 1;
- }
- name = next;
- }
- return -1;
-}
-
-int ext4fs_find_file(const char *path, struct ext2fs_node *rootnode,
- struct ext2fs_node **foundnode, int expecttype)
-{
- int status;
- int foundtype = FILETYPE_DIRECTORY;
-
- symlinknest = 0;
- if (!path)
- return 0;
-
- status = ext4fs_find_file1(path, rootnode, foundnode, &foundtype);
- if (status == 0)
- return 0;
-
- /* Check if the node that was found was of the expected type. */
- if ((expecttype == FILETYPE_REG) && (foundtype != expecttype))
- return 0;
- else if ((expecttype == FILETYPE_DIRECTORY)
- && (foundtype != expecttype))
- return 0;
-
- return 1;
-}
-
-int ext4fs_open(const char *filename)
-{
- struct ext2fs_node *fdiro = NULL;
- int status;
- int len;
-
- if (ext4fs_root == NULL)
- return -1;
-
- ext4fs_file = NULL;
- status = ext4fs_find_file(filename, &ext4fs_root->diropen, &fdiro,
- FILETYPE_REG);
- if (status == 0)
- goto fail;
-
- if (!fdiro->inode_read) {
- status = ext4fs_read_inode(fdiro->data, fdiro->ino,
- &fdiro->inode);
- if (status == 0)
- goto fail;
- }
- len = __le32_to_cpu(fdiro->inode.size);
- ext4fs_file = fdiro;
-
- return len;
-fail:
- ext4fs_free_node(fdiro, &ext4fs_root->diropen);
-
- return -1;
-}
-
-int ext4fs_mount(unsigned part_length)
-{
- struct ext2_data *data;
- int status;
- struct ext_filesystem *fs = get_fs();
- data = zalloc(SUPERBLOCK_SIZE);
- if (!data)
- return 0;
-
- /* Read the superblock. */
- status = ext4_read_superblock((char *)&data->sblock);
-
- if (status == 0)
- goto fail;
-
- /* Make sure this is an ext2 filesystem. */
- if (__le16_to_cpu(data->sblock.magic) != EXT2_MAGIC)
- goto fail;
-
- if (__le32_to_cpu(data->sblock.revision_level == 0))
- fs->inodesz = 128;
- else
- fs->inodesz = __le16_to_cpu(data->sblock.inode_size);
-
- debug("EXT2 rev %d, inode_size %d\n",
- __le32_to_cpu(data->sblock.revision_level), fs->inodesz);
-
- data->diropen.data = data;
- data->diropen.ino = 2;
- data->diropen.inode_read = 1;
- data->inode = &data->diropen.inode;
-
- status = ext4fs_read_inode(data, 2, data->inode);
- if (status == 0)
- goto fail;
-
- ext4fs_root = data;
-
- return 1;
-fail:
- printf("Failed to mount ext2 filesystem...\n");
- free(data);
- ext4fs_root = NULL;
-
- return 0;
-}
diff --git a/qemu/roms/u-boot/fs/ext4/ext4_common.h b/qemu/roms/u-boot/fs/ext4/ext4_common.h
deleted file mode 100644
index 5fa1719f2..000000000
--- a/qemu/roms/u-boot/fs/ext4/ext4_common.h
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * ext4ls and ext4load : based on ext2 ls load support in Uboot.
- *
- * (C) Copyright 2004
- * esd gmbh <www.esd-electronics.com>
- * Reinhard Arlt <reinhard.arlt@esd-electronics.com>
- *
- * based on code from grub2 fs/ext2.c and fs/fshelp.c by
- * GRUB -- GRand Unified Bootloader
- * Copyright (C) 2003, 2004 Free Software Foundation, Inc.
- *
- * ext4write : Based on generic ext4 protocol.
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#ifndef __EXT4_COMMON__
-#define __EXT4_COMMON__
-#include <ext_common.h>
-#include <ext4fs.h>
-#include <malloc.h>
-#include <asm/errno.h>
-#if defined(CONFIG_EXT4_WRITE)
-#include "ext4_journal.h"
-#include "crc16.h"
-#endif
-
-#define YES 1
-#define NO 0
-#define RECOVER 1
-#define SCAN 0
-
-#define S_IFLNK 0120000 /* symbolic link */
-#define BLOCK_NO_ONE 1
-#define SUPERBLOCK_START (2 * 512)
-#define SUPERBLOCK_SIZE 1024
-#define F_FILE 1
-
-static inline void *zalloc(size_t size)
-{
- void *p = memalign(ARCH_DMA_MINALIGN, size);
- memset(p, 0, size);
- return p;
-}
-
-int ext4fs_read_inode(struct ext2_data *data, int ino,
- struct ext2_inode *inode);
-int ext4fs_read_file(struct ext2fs_node *node, int pos,
- unsigned int len, char *buf);
-int ext4fs_find_file(const char *path, struct ext2fs_node *rootnode,
- struct ext2fs_node **foundnode, int expecttype);
-int ext4fs_iterate_dir(struct ext2fs_node *dir, char *name,
- struct ext2fs_node **fnode, int *ftype);
-
-#if defined(CONFIG_EXT4_WRITE)
-uint32_t ext4fs_div_roundup(uint32_t size, uint32_t n);
-int ext4fs_checksum_update(unsigned int i);
-int ext4fs_get_parent_inode_num(const char *dirname, char *dname, int flags);
-void ext4fs_update_parent_dentry(char *filename, int *p_ino, int file_type);
-long int ext4fs_get_new_blk_no(void);
-int ext4fs_get_new_inode_no(void);
-void ext4fs_reset_block_bmap(long int blockno, unsigned char *buffer,
- int index);
-int ext4fs_set_block_bmap(long int blockno, unsigned char *buffer, int index);
-int ext4fs_set_inode_bmap(int inode_no, unsigned char *buffer, int index);
-void ext4fs_reset_inode_bmap(int inode_no, unsigned char *buffer, int index);
-int ext4fs_iget(int inode_no, struct ext2_inode *inode);
-void ext4fs_allocate_blocks(struct ext2_inode *file_inode,
- unsigned int total_remaining_blocks,
- unsigned int *total_no_of_block);
-void put_ext4(uint64_t off, void *buf, uint32_t size);
-#endif
-#endif
diff --git a/qemu/roms/u-boot/fs/ext4/ext4_journal.c b/qemu/roms/u-boot/fs/ext4/ext4_journal.c
deleted file mode 100644
index 3f613351a..000000000
--- a/qemu/roms/u-boot/fs/ext4/ext4_journal.c
+++ /dev/null
@@ -1,653 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * Journal data structures and headers for Journaling feature of ext4
- * have been referred from JBD2 (Journaling Block device 2)
- * implementation in Linux Kernel.
- * Written by Stephen C. Tweedie <sct@redhat.com>
- *
- * Copyright 1998-2000 Red Hat, Inc --- All Rights Reserved
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-#include <ext4fs.h>
-#include <malloc.h>
-#include <ext_common.h>
-#include "ext4_common.h"
-
-static struct revoke_blk_list *revk_blk_list;
-static struct revoke_blk_list *prev_node;
-static int first_node = true;
-
-int gindex;
-int gd_index;
-int jrnl_blk_idx;
-struct journal_log *journal_ptr[MAX_JOURNAL_ENTRIES];
-struct dirty_blocks *dirty_block_ptr[MAX_JOURNAL_ENTRIES];
-
-int ext4fs_init_journal(void)
-{
- int i;
- char *temp = NULL;
- struct ext_filesystem *fs = get_fs();
-
- /* init globals */
- revk_blk_list = NULL;
- prev_node = NULL;
- gindex = 0;
- gd_index = 0;
- jrnl_blk_idx = 1;
-
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- journal_ptr[i] = zalloc(sizeof(struct journal_log));
- if (!journal_ptr[i])
- goto fail;
- dirty_block_ptr[i] = zalloc(sizeof(struct dirty_blocks));
- if (!dirty_block_ptr[i])
- goto fail;
- journal_ptr[i]->buf = NULL;
- journal_ptr[i]->blknr = -1;
-
- dirty_block_ptr[i]->buf = NULL;
- dirty_block_ptr[i]->blknr = -1;
- }
-
- if (fs->blksz == 4096) {
- temp = zalloc(fs->blksz);
- if (!temp)
- goto fail;
- journal_ptr[gindex]->buf = zalloc(fs->blksz);
- if (!journal_ptr[gindex]->buf)
- goto fail;
- ext4fs_devread(0, 0, fs->blksz, temp);
- memcpy(temp + SUPERBLOCK_SIZE, fs->sb, SUPERBLOCK_SIZE);
- memcpy(journal_ptr[gindex]->buf, temp, fs->blksz);
- journal_ptr[gindex++]->blknr = 0;
- free(temp);
- } else {
- journal_ptr[gindex]->buf = zalloc(fs->blksz);
- if (!journal_ptr[gindex]->buf)
- goto fail;
- memcpy(journal_ptr[gindex]->buf, fs->sb, SUPERBLOCK_SIZE);
- journal_ptr[gindex++]->blknr = 1;
- }
-
- /* Check the file system state using journal super block */
- if (ext4fs_check_journal_state(SCAN))
- goto fail;
- /* Check the file system state using journal super block */
- if (ext4fs_check_journal_state(RECOVER))
- goto fail;
-
- return 0;
-fail:
- return -1;
-}
-
-void ext4fs_dump_metadata(void)
-{
- struct ext_filesystem *fs = get_fs();
- int i;
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (dirty_block_ptr[i]->blknr == -1)
- break;
- put_ext4((uint64_t) ((uint64_t)dirty_block_ptr[i]->blknr *
- (uint64_t)fs->blksz), dirty_block_ptr[i]->buf,
- fs->blksz);
- }
-}
-
-void ext4fs_free_journal(void)
-{
- int i;
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (dirty_block_ptr[i]->blknr == -1)
- break;
- if (dirty_block_ptr[i]->buf)
- free(dirty_block_ptr[i]->buf);
- }
-
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (journal_ptr[i]->blknr == -1)
- break;
- if (journal_ptr[i]->buf)
- free(journal_ptr[i]->buf);
- }
-
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (journal_ptr[i])
- free(journal_ptr[i]);
- if (dirty_block_ptr[i])
- free(dirty_block_ptr[i]);
- }
- gindex = 0;
- gd_index = 0;
- jrnl_blk_idx = 1;
-}
-
-int ext4fs_log_gdt(char *gd_table)
-{
- struct ext_filesystem *fs = get_fs();
- short i;
- long int var = fs->gdtable_blkno;
- for (i = 0; i < fs->no_blk_pergdt; i++) {
- journal_ptr[gindex]->buf = zalloc(fs->blksz);
- if (!journal_ptr[gindex]->buf)
- return -ENOMEM;
- memcpy(journal_ptr[gindex]->buf, gd_table, fs->blksz);
- gd_table += fs->blksz;
- journal_ptr[gindex++]->blknr = var++;
- }
-
- return 0;
-}
-
-/*
- * This function stores the backup copy of meta data in RAM
- * journal_buffer -- Buffer containing meta data
- * blknr -- Block number on disk of the meta data buffer
- */
-int ext4fs_log_journal(char *journal_buffer, long int blknr)
-{
- struct ext_filesystem *fs = get_fs();
- short i;
-
- if (!journal_buffer) {
- printf("Invalid input arguments %s\n", __func__);
- return -EINVAL;
- }
-
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (journal_ptr[i]->blknr == -1)
- break;
- if (journal_ptr[i]->blknr == blknr)
- return 0;
- }
-
- journal_ptr[gindex]->buf = zalloc(fs->blksz);
- if (!journal_ptr[gindex]->buf)
- return -ENOMEM;
-
- memcpy(journal_ptr[gindex]->buf, journal_buffer, fs->blksz);
- journal_ptr[gindex++]->blknr = blknr;
-
- return 0;
-}
-
-/*
- * This function stores the modified meta data in RAM
- * metadata_buffer -- Buffer containing meta data
- * blknr -- Block number on disk of the meta data buffer
- */
-int ext4fs_put_metadata(char *metadata_buffer, long int blknr)
-{
- struct ext_filesystem *fs = get_fs();
- if (!metadata_buffer) {
- printf("Invalid input arguments %s\n", __func__);
- return -EINVAL;
- }
- dirty_block_ptr[gd_index]->buf = zalloc(fs->blksz);
- if (!dirty_block_ptr[gd_index]->buf)
- return -ENOMEM;
- memcpy(dirty_block_ptr[gd_index]->buf, metadata_buffer, fs->blksz);
- dirty_block_ptr[gd_index++]->blknr = blknr;
-
- return 0;
-}
-
-void print_revoke_blks(char *revk_blk)
-{
- int offset;
- int max;
- long int blocknr;
- struct journal_revoke_header_t *header;
-
- if (revk_blk == NULL)
- return;
-
- header = (struct journal_revoke_header_t *) revk_blk;
- offset = sizeof(struct journal_revoke_header_t);
- max = be32_to_cpu(header->r_count);
- printf("total bytes %d\n", max);
-
- while (offset < max) {
- blocknr = be32_to_cpu(*((long int *)(revk_blk + offset)));
- printf("revoke blknr is %ld\n", blocknr);
- offset += 4;
- }
-}
-
-static struct revoke_blk_list *_get_node(void)
-{
- struct revoke_blk_list *tmp_node;
- tmp_node = zalloc(sizeof(struct revoke_blk_list));
- if (tmp_node == NULL)
- return NULL;
- tmp_node->content = NULL;
- tmp_node->next = NULL;
-
- return tmp_node;
-}
-
-void ext4fs_push_revoke_blk(char *buffer)
-{
- struct revoke_blk_list *node = NULL;
- struct ext_filesystem *fs = get_fs();
- if (buffer == NULL) {
- printf("buffer ptr is NULL\n");
- return;
- }
- node = _get_node();
- if (!node) {
- printf("_get_node: malloc failed\n");
- return;
- }
-
- node->content = zalloc(fs->blksz);
- if (node->content == NULL)
- return;
- memcpy(node->content, buffer, fs->blksz);
-
- if (first_node == true) {
- revk_blk_list = node;
- prev_node = node;
- first_node = false;
- } else {
- prev_node->next = node;
- prev_node = node;
- }
-}
-
-void ext4fs_free_revoke_blks(void)
-{
- struct revoke_blk_list *tmp_node = revk_blk_list;
- struct revoke_blk_list *next_node = NULL;
-
- while (tmp_node != NULL) {
- if (tmp_node->content)
- free(tmp_node->content);
- tmp_node = tmp_node->next;
- }
-
- tmp_node = revk_blk_list;
- while (tmp_node != NULL) {
- next_node = tmp_node->next;
- free(tmp_node);
- tmp_node = next_node;
- }
-
- revk_blk_list = NULL;
- prev_node = NULL;
- first_node = true;
-}
-
-int check_blknr_for_revoke(long int blknr, int sequence_no)
-{
- struct journal_revoke_header_t *header;
- int offset;
- int max;
- long int blocknr;
- char *revk_blk;
- struct revoke_blk_list *tmp_revk_node = revk_blk_list;
- while (tmp_revk_node != NULL) {
- revk_blk = tmp_revk_node->content;
-
- header = (struct journal_revoke_header_t *) revk_blk;
- if (sequence_no < be32_to_cpu(header->r_header.h_sequence)) {
- offset = sizeof(struct journal_revoke_header_t);
- max = be32_to_cpu(header->r_count);
-
- while (offset < max) {
- blocknr = be32_to_cpu(*((long int *)
- (revk_blk + offset)));
- if (blocknr == blknr)
- goto found;
- offset += 4;
- }
- }
- tmp_revk_node = tmp_revk_node->next;
- }
-
- return -1;
-
-found:
- return 0;
-}
-
-/*
- * This function parses the journal blocks and replays the
- * suceessful transactions. A transaction is successfull
- * if commit block is found for a descriptor block
- * The tags in descriptor block contain the disk block
- * numbers of the metadata to be replayed
- */
-void recover_transaction(int prev_desc_logical_no)
-{
- struct ext2_inode inode_journal;
- struct ext_filesystem *fs = get_fs();
- struct journal_header_t *jdb;
- long int blknr;
- char *p_jdb;
- int ofs, flags;
- int i;
- struct ext3_journal_block_tag *tag;
- char *temp_buff = zalloc(fs->blksz);
- char *metadata_buff = zalloc(fs->blksz);
- if (!temp_buff || !metadata_buff)
- goto fail;
- i = prev_desc_logical_no;
- ext4fs_read_inode(ext4fs_root, EXT2_JOURNAL_INO,
- (struct ext2_inode *)&inode_journal);
- blknr = read_allocated_block((struct ext2_inode *)
- &inode_journal, i);
- ext4fs_devread((lbaint_t)blknr * fs->sect_perblk, 0, fs->blksz,
- temp_buff);
- p_jdb = (char *)temp_buff;
- jdb = (struct journal_header_t *) temp_buff;
- ofs = sizeof(struct journal_header_t);
-
- do {
- tag = (struct ext3_journal_block_tag *)&p_jdb[ofs];
- ofs += sizeof(struct ext3_journal_block_tag);
-
- if (ofs > fs->blksz)
- break;
-
- flags = be32_to_cpu(tag->flags);
- if (!(flags & EXT3_JOURNAL_FLAG_SAME_UUID))
- ofs += 16;
-
- i++;
- debug("\t\ttag %u\n", be32_to_cpu(tag->block));
- if (revk_blk_list != NULL) {
- if (check_blknr_for_revoke(be32_to_cpu(tag->block),
- be32_to_cpu(jdb->h_sequence)) == 0)
- continue;
- }
- blknr = read_allocated_block(&inode_journal, i);
- ext4fs_devread((lbaint_t)blknr * fs->sect_perblk, 0,
- fs->blksz, metadata_buff);
- put_ext4((uint64_t)((uint64_t)be32_to_cpu(tag->block) * (uint64_t)fs->blksz),
- metadata_buff, (uint32_t) fs->blksz);
- } while (!(flags & EXT3_JOURNAL_FLAG_LAST_TAG));
-fail:
- free(temp_buff);
- free(metadata_buff);
-}
-
-void print_jrnl_status(int recovery_flag)
-{
- if (recovery_flag == RECOVER)
- printf("Journal Recovery Completed\n");
- else
- printf("Journal Scan Completed\n");
-}
-
-int ext4fs_check_journal_state(int recovery_flag)
-{
- int i;
- int DB_FOUND = NO;
- long int blknr;
- int transaction_state = TRANSACTION_COMPLETE;
- int prev_desc_logical_no = 0;
- int curr_desc_logical_no = 0;
- int ofs, flags;
- struct ext2_inode inode_journal;
- struct journal_superblock_t *jsb = NULL;
- struct journal_header_t *jdb = NULL;
- char *p_jdb = NULL;
- struct ext3_journal_block_tag *tag = NULL;
- char *temp_buff = NULL;
- char *temp_buff1 = NULL;
- struct ext_filesystem *fs = get_fs();
-
- temp_buff = zalloc(fs->blksz);
- if (!temp_buff)
- return -ENOMEM;
- temp_buff1 = zalloc(fs->blksz);
- if (!temp_buff1) {
- free(temp_buff);
- return -ENOMEM;
- }
-
- ext4fs_read_inode(ext4fs_root, EXT2_JOURNAL_INO, &inode_journal);
- blknr = read_allocated_block(&inode_journal, EXT2_JOURNAL_SUPERBLOCK);
- ext4fs_devread((lbaint_t)blknr * fs->sect_perblk, 0, fs->blksz,
- temp_buff);
- jsb = (struct journal_superblock_t *) temp_buff;
-
- if (fs->sb->feature_incompat & EXT3_FEATURE_INCOMPAT_RECOVER) {
- if (recovery_flag == RECOVER)
- printf("Recovery required\n");
- } else {
- if (recovery_flag == RECOVER)
- printf("File System is consistent\n");
- goto end;
- }
-
- if (be32_to_cpu(jsb->s_start) == 0)
- goto end;
-
- if (!(jsb->s_feature_compat &
- cpu_to_be32(JBD2_FEATURE_COMPAT_CHECKSUM)))
- jsb->s_feature_compat |=
- cpu_to_be32(JBD2_FEATURE_COMPAT_CHECKSUM);
-
- i = be32_to_cpu(jsb->s_first);
- while (1) {
- blknr = read_allocated_block(&inode_journal, i);
- memset(temp_buff1, '\0', fs->blksz);
- ext4fs_devread((lbaint_t)blknr * fs->sect_perblk,
- 0, fs->blksz, temp_buff1);
- jdb = (struct journal_header_t *) temp_buff1;
-
- if (be32_to_cpu(jdb->h_blocktype) ==
- EXT3_JOURNAL_DESCRIPTOR_BLOCK) {
- if (be32_to_cpu(jdb->h_sequence) !=
- be32_to_cpu(jsb->s_sequence)) {
- print_jrnl_status(recovery_flag);
- break;
- }
-
- curr_desc_logical_no = i;
- if (transaction_state == TRANSACTION_COMPLETE)
- transaction_state = TRANSACTION_RUNNING;
- else
- return -1;
- p_jdb = (char *)temp_buff1;
- ofs = sizeof(struct journal_header_t);
- do {
- tag = (struct ext3_journal_block_tag *)
- &p_jdb[ofs];
- ofs += sizeof(struct ext3_journal_block_tag);
- if (ofs > fs->blksz)
- break;
- flags = be32_to_cpu(tag->flags);
- if (!(flags & EXT3_JOURNAL_FLAG_SAME_UUID))
- ofs += 16;
- i++;
- debug("\t\ttag %u\n", be32_to_cpu(tag->block));
- } while (!(flags & EXT3_JOURNAL_FLAG_LAST_TAG));
- i++;
- DB_FOUND = YES;
- } else if (be32_to_cpu(jdb->h_blocktype) ==
- EXT3_JOURNAL_COMMIT_BLOCK) {
- if (be32_to_cpu(jdb->h_sequence) !=
- be32_to_cpu(jsb->s_sequence)) {
- print_jrnl_status(recovery_flag);
- break;
- }
-
- if (transaction_state == TRANSACTION_RUNNING ||
- (DB_FOUND == NO)) {
- transaction_state = TRANSACTION_COMPLETE;
- i++;
- jsb->s_sequence =
- cpu_to_be32(be32_to_cpu(
- jsb->s_sequence) + 1);
- }
- prev_desc_logical_no = curr_desc_logical_no;
- if ((recovery_flag == RECOVER) && (DB_FOUND == YES))
- recover_transaction(prev_desc_logical_no);
-
- DB_FOUND = NO;
- } else if (be32_to_cpu(jdb->h_blocktype) ==
- EXT3_JOURNAL_REVOKE_BLOCK) {
- if (be32_to_cpu(jdb->h_sequence) !=
- be32_to_cpu(jsb->s_sequence)) {
- print_jrnl_status(recovery_flag);
- break;
- }
- if (recovery_flag == SCAN)
- ext4fs_push_revoke_blk((char *)jdb);
- i++;
- } else {
- debug("Else Case\n");
- if (be32_to_cpu(jdb->h_sequence) !=
- be32_to_cpu(jsb->s_sequence)) {
- print_jrnl_status(recovery_flag);
- break;
- }
- }
- }
-
-end:
- if (recovery_flag == RECOVER) {
- jsb->s_start = cpu_to_be32(1);
- jsb->s_sequence = cpu_to_be32(be32_to_cpu(jsb->s_sequence) + 1);
- /* get the superblock */
- ext4_read_superblock((char *)fs->sb);
- fs->sb->feature_incompat |= EXT3_FEATURE_INCOMPAT_RECOVER;
-
- /* Update the super block */
- put_ext4((uint64_t) (SUPERBLOCK_SIZE),
- (struct ext2_sblock *)fs->sb,
- (uint32_t) SUPERBLOCK_SIZE);
- ext4_read_superblock((char *)fs->sb);
-
- blknr = read_allocated_block(&inode_journal,
- EXT2_JOURNAL_SUPERBLOCK);
- put_ext4((uint64_t) ((uint64_t)blknr * (uint64_t)fs->blksz),
- (struct journal_superblock_t *)temp_buff,
- (uint32_t) fs->blksz);
- ext4fs_free_revoke_blks();
- }
- free(temp_buff);
- free(temp_buff1);
-
- return 0;
-}
-
-static void update_descriptor_block(long int blknr)
-{
- int i;
- long int jsb_blknr;
- struct journal_header_t jdb;
- struct ext3_journal_block_tag tag;
- struct ext2_inode inode_journal;
- struct journal_superblock_t *jsb = NULL;
- char *buf = NULL;
- char *temp = NULL;
- struct ext_filesystem *fs = get_fs();
- char *temp_buff = zalloc(fs->blksz);
- if (!temp_buff)
- return;
-
- ext4fs_read_inode(ext4fs_root, EXT2_JOURNAL_INO, &inode_journal);
- jsb_blknr = read_allocated_block(&inode_journal,
- EXT2_JOURNAL_SUPERBLOCK);
- ext4fs_devread((lbaint_t)jsb_blknr * fs->sect_perblk, 0, fs->blksz,
- temp_buff);
- jsb = (struct journal_superblock_t *) temp_buff;
-
- jdb.h_blocktype = cpu_to_be32(EXT3_JOURNAL_DESCRIPTOR_BLOCK);
- jdb.h_magic = cpu_to_be32(EXT3_JOURNAL_MAGIC_NUMBER);
- jdb.h_sequence = jsb->s_sequence;
- buf = zalloc(fs->blksz);
- if (!buf) {
- free(temp_buff);
- return;
- }
- temp = buf;
- memcpy(buf, &jdb, sizeof(struct journal_header_t));
- temp += sizeof(struct journal_header_t);
-
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (journal_ptr[i]->blknr == -1)
- break;
-
- tag.block = cpu_to_be32(journal_ptr[i]->blknr);
- tag.flags = cpu_to_be32(EXT3_JOURNAL_FLAG_SAME_UUID);
- memcpy(temp, &tag, sizeof(struct ext3_journal_block_tag));
- temp = temp + sizeof(struct ext3_journal_block_tag);
- }
-
- tag.block = cpu_to_be32(journal_ptr[--i]->blknr);
- tag.flags = cpu_to_be32(EXT3_JOURNAL_FLAG_LAST_TAG);
- memcpy(temp - sizeof(struct ext3_journal_block_tag), &tag,
- sizeof(struct ext3_journal_block_tag));
- put_ext4((uint64_t) ((uint64_t)blknr * (uint64_t)fs->blksz), buf, (uint32_t) fs->blksz);
-
- free(temp_buff);
- free(buf);
-}
-
-static void update_commit_block(long int blknr)
-{
- struct journal_header_t jdb;
- struct ext_filesystem *fs = get_fs();
- char *buf = NULL;
- struct ext2_inode inode_journal;
- struct journal_superblock_t *jsb;
- long int jsb_blknr;
- char *temp_buff = zalloc(fs->blksz);
- if (!temp_buff)
- return;
-
- ext4fs_read_inode(ext4fs_root, EXT2_JOURNAL_INO,
- &inode_journal);
- jsb_blknr = read_allocated_block(&inode_journal,
- EXT2_JOURNAL_SUPERBLOCK);
- ext4fs_devread((lbaint_t)jsb_blknr * fs->sect_perblk, 0, fs->blksz,
- temp_buff);
- jsb = (struct journal_superblock_t *) temp_buff;
-
- jdb.h_blocktype = cpu_to_be32(EXT3_JOURNAL_COMMIT_BLOCK);
- jdb.h_magic = cpu_to_be32(EXT3_JOURNAL_MAGIC_NUMBER);
- jdb.h_sequence = jsb->s_sequence;
- buf = zalloc(fs->blksz);
- if (!buf) {
- free(temp_buff);
- return;
- }
- memcpy(buf, &jdb, sizeof(struct journal_header_t));
- put_ext4((uint64_t) ((uint64_t)blknr * (uint64_t)fs->blksz), buf, (uint32_t) fs->blksz);
-
- free(temp_buff);
- free(buf);
-}
-
-void ext4fs_update_journal(void)
-{
- struct ext2_inode inode_journal;
- struct ext_filesystem *fs = get_fs();
- long int blknr;
- int i;
- ext4fs_read_inode(ext4fs_root, EXT2_JOURNAL_INO, &inode_journal);
- blknr = read_allocated_block(&inode_journal, jrnl_blk_idx++);
- update_descriptor_block(blknr);
- for (i = 0; i < MAX_JOURNAL_ENTRIES; i++) {
- if (journal_ptr[i]->blknr == -1)
- break;
- blknr = read_allocated_block(&inode_journal, jrnl_blk_idx++);
- put_ext4((uint64_t) ((uint64_t)blknr * (uint64_t)fs->blksz),
- journal_ptr[i]->buf, fs->blksz);
- }
- blknr = read_allocated_block(&inode_journal, jrnl_blk_idx++);
- update_commit_block(blknr);
- printf("update journal finished\n");
-}
diff --git a/qemu/roms/u-boot/fs/ext4/ext4_journal.h b/qemu/roms/u-boot/fs/ext4/ext4_journal.h
deleted file mode 100644
index d926094be..000000000
--- a/qemu/roms/u-boot/fs/ext4/ext4_journal.h
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * Journal data structures and headers for Journaling feature of ext4
- * have been referred from JBD2 (Journaling Block device 2)
- * implementation in Linux Kernel.
- *
- * Written by Stephen C. Tweedie <sct@redhat.com>
- *
- * Copyright 1998-2000 Red Hat, Inc --- All Rights Reserved
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#ifndef __EXT4_JRNL__
-#define __EXT4_JRNL__
-
-#define EXT2_JOURNAL_INO 8 /* Journal inode */
-#define EXT2_JOURNAL_SUPERBLOCK 0 /* Journal Superblock number */
-
-#define JBD2_FEATURE_COMPAT_CHECKSUM 0x00000001
-#define EXT3_JOURNAL_MAGIC_NUMBER 0xc03b3998U
-#define TRANSACTION_RUNNING 1
-#define TRANSACTION_COMPLETE 0
-#define EXT3_FEATURE_INCOMPAT_RECOVER 0x0004 /* Needs recovery */
-#define EXT3_JOURNAL_DESCRIPTOR_BLOCK 1
-#define EXT3_JOURNAL_COMMIT_BLOCK 2
-#define EXT3_JOURNAL_SUPERBLOCK_V1 3
-#define EXT3_JOURNAL_SUPERBLOCK_V2 4
-#define EXT3_JOURNAL_REVOKE_BLOCK 5
-#define EXT3_JOURNAL_FLAG_ESCAPE 1
-#define EXT3_JOURNAL_FLAG_SAME_UUID 2
-#define EXT3_JOURNAL_FLAG_DELETED 4
-#define EXT3_JOURNAL_FLAG_LAST_TAG 8
-
-/* Maximum entries in 1 journal transaction */
-#define MAX_JOURNAL_ENTRIES 100
-struct journal_log {
- char *buf;
- int blknr;
-};
-
-struct dirty_blocks {
- char *buf;
- int blknr;
-};
-
-/* Standard header for all descriptor blocks: */
-struct journal_header_t {
- __u32 h_magic;
- __u32 h_blocktype;
- __u32 h_sequence;
-};
-
-/* The journal superblock. All fields are in big-endian byte order. */
-struct journal_superblock_t {
- /* 0x0000 */
- struct journal_header_t s_header;
-
- /* Static information describing the journal */
- __u32 s_blocksize; /* journal device blocksize */
- __u32 s_maxlen; /* total blocks in journal file */
- __u32 s_first; /* first block of log information */
-
- /* Dynamic information describing the current state of the log */
- __u32 s_sequence; /* first commit ID expected in log */
- __u32 s_start; /* blocknr of start of log */
-
- /* Error value, as set by journal_abort(). */
- __s32 s_errno;
-
- /* Remaining fields are only valid in a version-2 superblock */
- __u32 s_feature_compat; /* compatible feature set */
- __u32 s_feature_incompat; /* incompatible feature set */
- __u32 s_feature_ro_compat; /* readonly-compatible feature set */
- /* 0x0030 */
- __u8 s_uuid[16]; /* 128-bit uuid for journal */
-
- /* 0x0040 */
- __u32 s_nr_users; /* Nr of filesystems sharing log */
-
- __u32 s_dynsuper; /* Blocknr of dynamic superblock copy */
-
- /* 0x0048 */
- __u32 s_max_transaction; /* Limit of journal blocks per trans. */
- __u32 s_max_trans_data; /* Limit of data blocks per trans. */
-
- /* 0x0050 */
- __u32 s_padding[44];
-
- /* 0x0100 */
- __u8 s_users[16 * 48]; /* ids of all fs'es sharing the log */
- /* 0x0400 */
-} ;
-
-struct ext3_journal_block_tag {
- uint32_t block;
- uint32_t flags;
-};
-
-struct journal_revoke_header_t {
- struct journal_header_t r_header;
- int r_count; /* Count of bytes used in the block */
-};
-
-struct revoke_blk_list {
- char *content; /* revoke block itself */
- struct revoke_blk_list *next;
-};
-
-extern struct ext2_data *ext4fs_root;
-
-int ext4fs_init_journal(void);
-int ext4fs_log_gdt(char *gd_table);
-int ext4fs_check_journal_state(int recovery_flag);
-int ext4fs_log_journal(char *journal_buffer, long int blknr);
-int ext4fs_put_metadata(char *metadata_buffer, long int blknr);
-void ext4fs_update_journal(void);
-void ext4fs_dump_metadata(void);
-void ext4fs_push_revoke_blk(char *buffer);
-void ext4fs_free_journal(void);
-void ext4fs_free_revoke_blks(void);
-#endif
diff --git a/qemu/roms/u-boot/fs/ext4/ext4_write.c b/qemu/roms/u-boot/fs/ext4/ext4_write.c
deleted file mode 100644
index c42add9a7..000000000
--- a/qemu/roms/u-boot/fs/ext4/ext4_write.c
+++ /dev/null
@@ -1,977 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * ext4ls and ext4load : Based on ext2 ls and load support in Uboot.
- * Ext4 read optimization taken from Open-Moko
- * Qi bootloader
- *
- * (C) Copyright 2004
- * esd gmbh <www.esd-electronics.com>
- * Reinhard Arlt <reinhard.arlt@esd-electronics.com>
- *
- * based on code from grub2 fs/ext2.c and fs/fshelp.c by
- * GRUB -- GRand Unified Bootloader
- * Copyright (C) 2003, 2004 Free Software Foundation, Inc.
- *
- * ext4write : Based on generic ext4 protocol.
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-
-#include <common.h>
-#include <linux/stat.h>
-#include <div64.h>
-#include "ext4_common.h"
-
-static void ext4fs_update(void)
-{
- short i;
- ext4fs_update_journal();
- struct ext_filesystem *fs = get_fs();
-
- /* update super block */
- put_ext4((uint64_t)(SUPERBLOCK_SIZE),
- (struct ext2_sblock *)fs->sb, (uint32_t)SUPERBLOCK_SIZE);
-
- /* update block groups */
- for (i = 0; i < fs->no_blkgrp; i++) {
- fs->bgd[i].bg_checksum = ext4fs_checksum_update(i);
- put_ext4((uint64_t)((uint64_t)fs->bgd[i].block_id * (uint64_t)fs->blksz),
- fs->blk_bmaps[i], fs->blksz);
- }
-
- /* update inode table groups */
- for (i = 0; i < fs->no_blkgrp; i++) {
- put_ext4((uint64_t) ((uint64_t)fs->bgd[i].inode_id * (uint64_t)fs->blksz),
- fs->inode_bmaps[i], fs->blksz);
- }
-
- /* update the block group descriptor table */
- put_ext4((uint64_t)((uint64_t)fs->gdtable_blkno * (uint64_t)fs->blksz),
- (struct ext2_block_group *)fs->gdtable,
- (fs->blksz * fs->no_blk_pergdt));
-
- ext4fs_dump_metadata();
-
- gindex = 0;
- gd_index = 0;
-}
-
-int ext4fs_get_bgdtable(void)
-{
- int status;
- int grp_desc_size;
- struct ext_filesystem *fs = get_fs();
- grp_desc_size = sizeof(struct ext2_block_group);
- fs->no_blk_pergdt = (fs->no_blkgrp * grp_desc_size) / fs->blksz;
- if ((fs->no_blkgrp * grp_desc_size) % fs->blksz)
- fs->no_blk_pergdt++;
-
- /* allocate memory for gdtable */
- fs->gdtable = zalloc(fs->blksz * fs->no_blk_pergdt);
- if (!fs->gdtable)
- return -ENOMEM;
- /* read the group descriptor table */
- status = ext4fs_devread((lbaint_t)fs->gdtable_blkno * fs->sect_perblk,
- 0, fs->blksz * fs->no_blk_pergdt, fs->gdtable);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_gdt(fs->gdtable)) {
- printf("Error in ext4fs_log_gdt\n");
- return -1;
- }
-
- return 0;
-fail:
- free(fs->gdtable);
- fs->gdtable = NULL;
-
- return -1;
-}
-
-static void delete_single_indirect_block(struct ext2_inode *inode)
-{
- struct ext2_block_group *bgd = NULL;
- static int prev_bg_bmap_idx = -1;
- long int blknr;
- int remainder;
- int bg_idx;
- int status;
- unsigned int blk_per_grp = ext4fs_root->sblock.blocks_per_group;
- struct ext_filesystem *fs = get_fs();
- char *journal_buffer = zalloc(fs->blksz);
- if (!journal_buffer) {
- printf("No memory\n");
- return;
- }
- /* get block group descriptor table */
- bgd = (struct ext2_block_group *)fs->gdtable;
-
- /* deleting the single indirect block associated with inode */
- if (inode->b.blocks.indir_block != 0) {
- debug("SIPB releasing %u\n", inode->b.blocks.indir_block);
- blknr = inode->b.blocks.indir_block;
- bg_idx = blknr / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = blknr % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(blknr, fs->blk_bmaps[bg_idx], bg_idx);
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- status =
- ext4fs_devread((lbaint_t)bgd[bg_idx].block_id *
- fs->sect_perblk, 0, fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal
- (journal_buffer, bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- }
-fail:
- free(journal_buffer);
-}
-
-static void delete_double_indirect_block(struct ext2_inode *inode)
-{
- int i;
- short status;
- static int prev_bg_bmap_idx = -1;
- long int blknr;
- int remainder;
- int bg_idx;
- unsigned int blk_per_grp = ext4fs_root->sblock.blocks_per_group;
- unsigned int *di_buffer = NULL;
- unsigned int *DIB_start_addr = NULL;
- struct ext2_block_group *bgd = NULL;
- struct ext_filesystem *fs = get_fs();
- char *journal_buffer = zalloc(fs->blksz);
- if (!journal_buffer) {
- printf("No memory\n");
- return;
- }
- /* get the block group descriptor table */
- bgd = (struct ext2_block_group *)fs->gdtable;
-
- if (inode->b.blocks.double_indir_block != 0) {
- di_buffer = zalloc(fs->blksz);
- if (!di_buffer) {
- printf("No memory\n");
- return;
- }
- DIB_start_addr = (unsigned int *)di_buffer;
- blknr = inode->b.blocks.double_indir_block;
- status = ext4fs_devread((lbaint_t)blknr * fs->sect_perblk, 0,
- fs->blksz, (char *)di_buffer);
- for (i = 0; i < fs->blksz / sizeof(int); i++) {
- if (*di_buffer == 0)
- break;
-
- debug("DICB releasing %u\n", *di_buffer);
- bg_idx = *di_buffer / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = *di_buffer % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(*di_buffer,
- fs->blk_bmaps[bg_idx], bg_idx);
- di_buffer++;
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- status = ext4fs_devread((lbaint_t)
- bgd[bg_idx].block_id
- * fs->sect_perblk, 0,
- fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- }
-
- /* removing the parent double indirect block */
- blknr = inode->b.blocks.double_indir_block;
- bg_idx = blknr / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = blknr % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(blknr, fs->blk_bmaps[bg_idx], bg_idx);
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- memset(journal_buffer, '\0', fs->blksz);
- status = ext4fs_devread((lbaint_t)bgd[bg_idx].block_id *
- fs->sect_perblk, 0, fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- debug("DIPB releasing %ld\n", blknr);
- }
-fail:
- free(DIB_start_addr);
- free(journal_buffer);
-}
-
-static void delete_triple_indirect_block(struct ext2_inode *inode)
-{
- int i, j;
- short status;
- static int prev_bg_bmap_idx = -1;
- long int blknr;
- int remainder;
- int bg_idx;
- unsigned int blk_per_grp = ext4fs_root->sblock.blocks_per_group;
- unsigned int *tigp_buffer = NULL;
- unsigned int *tib_start_addr = NULL;
- unsigned int *tip_buffer = NULL;
- unsigned int *tipb_start_addr = NULL;
- struct ext2_block_group *bgd = NULL;
- struct ext_filesystem *fs = get_fs();
- char *journal_buffer = zalloc(fs->blksz);
- if (!journal_buffer) {
- printf("No memory\n");
- return;
- }
- /* get block group descriptor table */
- bgd = (struct ext2_block_group *)fs->gdtable;
-
- if (inode->b.blocks.triple_indir_block != 0) {
- tigp_buffer = zalloc(fs->blksz);
- if (!tigp_buffer) {
- printf("No memory\n");
- return;
- }
- tib_start_addr = (unsigned int *)tigp_buffer;
- blknr = inode->b.blocks.triple_indir_block;
- status = ext4fs_devread((lbaint_t)blknr * fs->sect_perblk, 0,
- fs->blksz, (char *)tigp_buffer);
- for (i = 0; i < fs->blksz / sizeof(int); i++) {
- if (*tigp_buffer == 0)
- break;
- debug("tigp buffer releasing %u\n", *tigp_buffer);
-
- tip_buffer = zalloc(fs->blksz);
- if (!tip_buffer)
- goto fail;
- tipb_start_addr = (unsigned int *)tip_buffer;
- status = ext4fs_devread((lbaint_t)(*tigp_buffer) *
- fs->sect_perblk, 0, fs->blksz,
- (char *)tip_buffer);
- for (j = 0; j < fs->blksz / sizeof(int); j++) {
- if (*tip_buffer == 0)
- break;
- bg_idx = *tip_buffer / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = *tip_buffer % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
-
- ext4fs_reset_block_bmap(*tip_buffer,
- fs->blk_bmaps[bg_idx],
- bg_idx);
-
- tip_buffer++;
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- status =
- ext4fs_devread(
- (lbaint_t)
- bgd[bg_idx].block_id *
- fs->sect_perblk, 0,
- fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].
- block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- }
- free(tipb_start_addr);
- tipb_start_addr = NULL;
-
- /*
- * removing the grand parent blocks
- * which is connected to inode
- */
- bg_idx = *tigp_buffer / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = *tigp_buffer % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(*tigp_buffer,
- fs->blk_bmaps[bg_idx], bg_idx);
-
- tigp_buffer++;
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- memset(journal_buffer, '\0', fs->blksz);
- status =
- ext4fs_devread((lbaint_t)
- bgd[bg_idx].block_id *
- fs->sect_perblk, 0,
- fs->blksz, journal_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- }
-
- /* removing the grand parent triple indirect block */
- blknr = inode->b.blocks.triple_indir_block;
- bg_idx = blknr / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = blknr % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(blknr, fs->blk_bmaps[bg_idx], bg_idx);
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- memset(journal_buffer, '\0', fs->blksz);
- status = ext4fs_devread((lbaint_t)bgd[bg_idx].block_id *
- fs->sect_perblk, 0, fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- debug("tigp buffer itself releasing %ld\n", blknr);
- }
-fail:
- free(tib_start_addr);
- free(tipb_start_addr);
- free(journal_buffer);
-}
-
-static int ext4fs_delete_file(int inodeno)
-{
- struct ext2_inode inode;
- short status;
- int i;
- int remainder;
- long int blknr;
- int bg_idx;
- int ibmap_idx;
- char *read_buffer = NULL;
- char *start_block_address = NULL;
- unsigned int no_blocks;
-
- static int prev_bg_bmap_idx = -1;
- unsigned int inodes_per_block;
- long int blkno;
- unsigned int blkoff;
- unsigned int blk_per_grp = ext4fs_root->sblock.blocks_per_group;
- unsigned int inode_per_grp = ext4fs_root->sblock.inodes_per_group;
- struct ext2_inode *inode_buffer = NULL;
- struct ext2_block_group *bgd = NULL;
- struct ext_filesystem *fs = get_fs();
- char *journal_buffer = zalloc(fs->blksz);
- if (!journal_buffer)
- return -ENOMEM;
- /* get the block group descriptor table */
- bgd = (struct ext2_block_group *)fs->gdtable;
- status = ext4fs_read_inode(ext4fs_root, inodeno, &inode);
- if (status == 0)
- goto fail;
-
- /* read the block no allocated to a file */
- no_blocks = inode.size / fs->blksz;
- if (inode.size % fs->blksz)
- no_blocks++;
-
- if (le32_to_cpu(inode.flags) & EXT4_EXTENTS_FL) {
- struct ext2fs_node *node_inode =
- zalloc(sizeof(struct ext2fs_node));
- if (!node_inode)
- goto fail;
- node_inode->data = ext4fs_root;
- node_inode->ino = inodeno;
- node_inode->inode_read = 0;
- memcpy(&(node_inode->inode), &inode, sizeof(struct ext2_inode));
-
- for (i = 0; i < no_blocks; i++) {
- blknr = read_allocated_block(&(node_inode->inode), i);
- bg_idx = blknr / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = blknr % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(blknr, fs->blk_bmaps[bg_idx],
- bg_idx);
- debug("EXT4_EXTENTS Block releasing %ld: %d\n",
- blknr, bg_idx);
-
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
-
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- status =
- ext4fs_devread((lbaint_t)
- bgd[bg_idx].block_id *
- fs->sect_perblk, 0,
- fs->blksz, journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- }
- if (node_inode) {
- free(node_inode);
- node_inode = NULL;
- }
- } else {
-
- delete_single_indirect_block(&inode);
- delete_double_indirect_block(&inode);
- delete_triple_indirect_block(&inode);
-
- /* read the block no allocated to a file */
- no_blocks = inode.size / fs->blksz;
- if (inode.size % fs->blksz)
- no_blocks++;
- for (i = 0; i < no_blocks; i++) {
- blknr = read_allocated_block(&inode, i);
- bg_idx = blknr / blk_per_grp;
- if (fs->blksz == 1024) {
- remainder = blknr % blk_per_grp;
- if (!remainder)
- bg_idx--;
- }
- ext4fs_reset_block_bmap(blknr, fs->blk_bmaps[bg_idx],
- bg_idx);
- debug("ActualB releasing %ld: %d\n", blknr, bg_idx);
-
- bgd[bg_idx].free_blocks++;
- fs->sb->free_blocks++;
- /* journal backup */
- if (prev_bg_bmap_idx != bg_idx) {
- memset(journal_buffer, '\0', fs->blksz);
- status = ext4fs_devread((lbaint_t)
- bgd[bg_idx].block_id
- * fs->sect_perblk,
- 0, fs->blksz,
- journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer,
- bgd[bg_idx].block_id))
- goto fail;
- prev_bg_bmap_idx = bg_idx;
- }
- }
- }
-
- /* from the inode no to blockno */
- inodes_per_block = fs->blksz / fs->inodesz;
- ibmap_idx = inodeno / inode_per_grp;
-
- /* get the block no */
- inodeno--;
- blkno = __le32_to_cpu(bgd[ibmap_idx].inode_table_id) +
- (inodeno % __le32_to_cpu(inode_per_grp)) / inodes_per_block;
-
- /* get the offset of the inode */
- blkoff = ((inodeno) % inodes_per_block) * fs->inodesz;
-
- /* read the block no containing the inode */
- read_buffer = zalloc(fs->blksz);
- if (!read_buffer)
- goto fail;
- start_block_address = read_buffer;
- status = ext4fs_devread((lbaint_t)blkno * fs->sect_perblk,
- 0, fs->blksz, read_buffer);
- if (status == 0)
- goto fail;
-
- if (ext4fs_log_journal(read_buffer, blkno))
- goto fail;
-
- read_buffer = read_buffer + blkoff;
- inode_buffer = (struct ext2_inode *)read_buffer;
- memset(inode_buffer, '\0', sizeof(struct ext2_inode));
-
- /* write the inode to original position in inode table */
- if (ext4fs_put_metadata(start_block_address, blkno))
- goto fail;
-
- /* update the respective inode bitmaps */
- inodeno++;
- ext4fs_reset_inode_bmap(inodeno, fs->inode_bmaps[ibmap_idx], ibmap_idx);
- bgd[ibmap_idx].free_inodes++;
- fs->sb->free_inodes++;
- /* journal backup */
- memset(journal_buffer, '\0', fs->blksz);
- status = ext4fs_devread((lbaint_t)bgd[ibmap_idx].inode_id *
- fs->sect_perblk, 0, fs->blksz, journal_buffer);
- if (status == 0)
- goto fail;
- if (ext4fs_log_journal(journal_buffer, bgd[ibmap_idx].inode_id))
- goto fail;
-
- ext4fs_update();
- ext4fs_deinit();
- ext4fs_reinit_global();
-
- if (ext4fs_init() != 0) {
- printf("error in File System init\n");
- goto fail;
- }
-
- free(start_block_address);
- free(journal_buffer);
-
- return 0;
-fail:
- free(start_block_address);
- free(journal_buffer);
-
- return -1;
-}
-
-int ext4fs_init(void)
-{
- short status;
- int i;
- unsigned int real_free_blocks = 0;
- struct ext_filesystem *fs = get_fs();
-
- /* populate fs */
- fs->blksz = EXT2_BLOCK_SIZE(ext4fs_root);
- fs->inodesz = INODE_SIZE_FILESYSTEM(ext4fs_root);
- fs->sect_perblk = fs->blksz >> fs->dev_desc->log2blksz;
-
- /* get the superblock */
- fs->sb = zalloc(SUPERBLOCK_SIZE);
- if (!fs->sb)
- return -ENOMEM;
- if (!ext4_read_superblock((char *)fs->sb))
- goto fail;
-
- /* init journal */
- if (ext4fs_init_journal())
- goto fail;
-
- /* get total no of blockgroups */
- fs->no_blkgrp = (uint32_t)ext4fs_div_roundup(
- (ext4fs_root->sblock.total_blocks -
- ext4fs_root->sblock.first_data_block),
- ext4fs_root->sblock.blocks_per_group);
-
- /* get the block group descriptor table */
- fs->gdtable_blkno = ((EXT2_MIN_BLOCK_SIZE == fs->blksz) + 1);
- if (ext4fs_get_bgdtable() == -1) {
- printf("Error in getting the block group descriptor table\n");
- goto fail;
- }
- fs->bgd = (struct ext2_block_group *)fs->gdtable;
-
- /* load all the available bitmap block of the partition */
- fs->blk_bmaps = zalloc(fs->no_blkgrp * sizeof(char *));
- if (!fs->blk_bmaps)
- goto fail;
- for (i = 0; i < fs->no_blkgrp; i++) {
- fs->blk_bmaps[i] = zalloc(fs->blksz);
- if (!fs->blk_bmaps[i])
- goto fail;
- }
-
- for (i = 0; i < fs->no_blkgrp; i++) {
- status =
- ext4fs_devread((lbaint_t)fs->bgd[i].block_id *
- fs->sect_perblk, 0,
- fs->blksz, (char *)fs->blk_bmaps[i]);
- if (status == 0)
- goto fail;
- }
-
- /* load all the available inode bitmap of the partition */
- fs->inode_bmaps = zalloc(fs->no_blkgrp * sizeof(unsigned char *));
- if (!fs->inode_bmaps)
- goto fail;
- for (i = 0; i < fs->no_blkgrp; i++) {
- fs->inode_bmaps[i] = zalloc(fs->blksz);
- if (!fs->inode_bmaps[i])
- goto fail;
- }
-
- for (i = 0; i < fs->no_blkgrp; i++) {
- status = ext4fs_devread((lbaint_t)fs->bgd[i].inode_id *
- fs->sect_perblk,
- 0, fs->blksz,
- (char *)fs->inode_bmaps[i]);
- if (status == 0)
- goto fail;
- }
-
- /*
- * check filesystem consistency with free blocks of file system
- * some time we observed that superblock freeblocks does not match
- * with the blockgroups freeblocks when improper
- * reboot of a linux kernel
- */
- for (i = 0; i < fs->no_blkgrp; i++)
- real_free_blocks = real_free_blocks + fs->bgd[i].free_blocks;
- if (real_free_blocks != fs->sb->free_blocks)
- fs->sb->free_blocks = real_free_blocks;
-
- return 0;
-fail:
- ext4fs_deinit();
-
- return -1;
-}
-
-void ext4fs_deinit(void)
-{
- int i;
- struct ext2_inode inode_journal;
- struct journal_superblock_t *jsb;
- long int blknr;
- struct ext_filesystem *fs = get_fs();
-
- /* free journal */
- char *temp_buff = zalloc(fs->blksz);
- if (temp_buff) {
- ext4fs_read_inode(ext4fs_root, EXT2_JOURNAL_INO,
- &inode_journal);
- blknr = read_allocated_block(&inode_journal,
- EXT2_JOURNAL_SUPERBLOCK);
- ext4fs_devread((lbaint_t)blknr * fs->sect_perblk, 0, fs->blksz,
- temp_buff);
- jsb = (struct journal_superblock_t *)temp_buff;
- jsb->s_start = cpu_to_be32(0);
- put_ext4((uint64_t) ((uint64_t)blknr * (uint64_t)fs->blksz),
- (struct journal_superblock_t *)temp_buff, fs->blksz);
- free(temp_buff);
- }
- ext4fs_free_journal();
-
- /* get the superblock */
- ext4_read_superblock((char *)fs->sb);
- fs->sb->feature_incompat &= ~EXT3_FEATURE_INCOMPAT_RECOVER;
- put_ext4((uint64_t)(SUPERBLOCK_SIZE),
- (struct ext2_sblock *)fs->sb, (uint32_t)SUPERBLOCK_SIZE);
- free(fs->sb);
- fs->sb = NULL;
-
- if (fs->blk_bmaps) {
- for (i = 0; i < fs->no_blkgrp; i++) {
- free(fs->blk_bmaps[i]);
- fs->blk_bmaps[i] = NULL;
- }
- free(fs->blk_bmaps);
- fs->blk_bmaps = NULL;
- }
-
- if (fs->inode_bmaps) {
- for (i = 0; i < fs->no_blkgrp; i++) {
- free(fs->inode_bmaps[i]);
- fs->inode_bmaps[i] = NULL;
- }
- free(fs->inode_bmaps);
- fs->inode_bmaps = NULL;
- }
-
-
- free(fs->gdtable);
- fs->gdtable = NULL;
- fs->bgd = NULL;
- /*
- * reinitiliazed the global inode and
- * block bitmap first execution check variables
- */
- fs->first_pass_ibmap = 0;
- fs->first_pass_bbmap = 0;
- fs->curr_inode_no = 0;
- fs->curr_blkno = 0;
-}
-
-static int ext4fs_write_file(struct ext2_inode *file_inode,
- int pos, unsigned int len, char *buf)
-{
- int i;
- int blockcnt;
- unsigned int filesize = __le32_to_cpu(file_inode->size);
- struct ext_filesystem *fs = get_fs();
- int log2blksz = fs->dev_desc->log2blksz;
- int log2_fs_blocksize = LOG2_BLOCK_SIZE(ext4fs_root) - log2blksz;
- int previous_block_number = -1;
- int delayed_start = 0;
- int delayed_extent = 0;
- int delayed_next = 0;
- char *delayed_buf = NULL;
-
- /* Adjust len so it we can't read past the end of the file. */
- if (len > filesize)
- len = filesize;
-
- blockcnt = ((len + pos) + fs->blksz - 1) / fs->blksz;
-
- for (i = pos / fs->blksz; i < blockcnt; i++) {
- long int blknr;
- int blockend = fs->blksz;
- int skipfirst = 0;
- blknr = read_allocated_block(file_inode, i);
- if (blknr < 0)
- return -1;
-
- blknr = blknr << log2_fs_blocksize;
-
- if (blknr) {
- if (previous_block_number != -1) {
- if (delayed_next == blknr) {
- delayed_extent += blockend;
- delayed_next += blockend >> log2blksz;
- } else { /* spill */
- put_ext4((uint64_t)
- ((uint64_t)delayed_start << log2blksz),
- delayed_buf,
- (uint32_t) delayed_extent);
- previous_block_number = blknr;
- delayed_start = blknr;
- delayed_extent = blockend;
- delayed_buf = buf;
- delayed_next = blknr +
- (blockend >> log2blksz);
- }
- } else {
- previous_block_number = blknr;
- delayed_start = blknr;
- delayed_extent = blockend;
- delayed_buf = buf;
- delayed_next = blknr +
- (blockend >> log2blksz);
- }
- } else {
- if (previous_block_number != -1) {
- /* spill */
- put_ext4((uint64_t) ((uint64_t)delayed_start <<
- log2blksz),
- delayed_buf,
- (uint32_t) delayed_extent);
- previous_block_number = -1;
- }
- memset(buf, 0, fs->blksz - skipfirst);
- }
- buf += fs->blksz - skipfirst;
- }
- if (previous_block_number != -1) {
- /* spill */
- put_ext4((uint64_t) ((uint64_t)delayed_start << log2blksz),
- delayed_buf, (uint32_t) delayed_extent);
- previous_block_number = -1;
- }
-
- return len;
-}
-
-int ext4fs_write(const char *fname, unsigned char *buffer,
- unsigned long sizebytes)
-{
- int ret = 0;
- struct ext2_inode *file_inode = NULL;
- unsigned char *inode_buffer = NULL;
- int parent_inodeno;
- int inodeno;
- time_t timestamp = 0;
-
- uint64_t bytes_reqd_for_file;
- unsigned int blks_reqd_for_file;
- unsigned int blocks_remaining;
- int existing_file_inodeno;
- char *temp_ptr = NULL;
- long int itable_blkno;
- long int parent_itable_blkno;
- long int blkoff;
- struct ext2_sblock *sblock = &(ext4fs_root->sblock);
- unsigned int inodes_per_block;
- unsigned int ibmap_idx;
- struct ext_filesystem *fs = get_fs();
- ALLOC_CACHE_ALIGN_BUFFER(char, filename, 256);
- memset(filename, 0x00, sizeof(filename));
-
- g_parent_inode = zalloc(sizeof(struct ext2_inode));
- if (!g_parent_inode)
- goto fail;
-
- if (ext4fs_init() != 0) {
- printf("error in File System init\n");
- return -1;
- }
- inodes_per_block = fs->blksz / fs->inodesz;
- parent_inodeno = ext4fs_get_parent_inode_num(fname, filename, F_FILE);
- if (parent_inodeno == -1)
- goto fail;
- if (ext4fs_iget(parent_inodeno, g_parent_inode))
- goto fail;
- /* check if the filename is already present in root */
- existing_file_inodeno = ext4fs_filename_check(filename);
- if (existing_file_inodeno != -1) {
- ret = ext4fs_delete_file(existing_file_inodeno);
- fs->first_pass_bbmap = 0;
- fs->curr_blkno = 0;
-
- fs->first_pass_ibmap = 0;
- fs->curr_inode_no = 0;
- if (ret)
- goto fail;
- }
- /* calucalate how many blocks required */
- bytes_reqd_for_file = sizebytes;
- blks_reqd_for_file = lldiv(bytes_reqd_for_file, fs->blksz);
- if (do_div(bytes_reqd_for_file, fs->blksz) != 0) {
- blks_reqd_for_file++;
- debug("total bytes for a file %u\n", blks_reqd_for_file);
- }
- blocks_remaining = blks_reqd_for_file;
- /* test for available space in partition */
- if (fs->sb->free_blocks < blks_reqd_for_file) {
- printf("Not enough space on partition !!!\n");
- goto fail;
- }
-
- ext4fs_update_parent_dentry(filename, &inodeno, FILETYPE_REG);
- /* prepare file inode */
- inode_buffer = zalloc(fs->inodesz);
- if (!inode_buffer)
- goto fail;
- file_inode = (struct ext2_inode *)inode_buffer;
- file_inode->mode = S_IFREG | S_IRWXU |
- S_IRGRP | S_IROTH | S_IXGRP | S_IXOTH;
- /* ToDo: Update correct time */
- file_inode->mtime = timestamp;
- file_inode->atime = timestamp;
- file_inode->ctime = timestamp;
- file_inode->nlinks = 1;
- file_inode->size = sizebytes;
-
- /* Allocate data blocks */
- ext4fs_allocate_blocks(file_inode, blocks_remaining,
- &blks_reqd_for_file);
- file_inode->blockcnt = (blks_reqd_for_file * fs->blksz) >>
- fs->dev_desc->log2blksz;
-
- temp_ptr = zalloc(fs->blksz);
- if (!temp_ptr)
- goto fail;
- ibmap_idx = inodeno / ext4fs_root->sblock.inodes_per_group;
- inodeno--;
- itable_blkno = __le32_to_cpu(fs->bgd[ibmap_idx].inode_table_id) +
- (inodeno % __le32_to_cpu(sblock->inodes_per_group)) /
- inodes_per_block;
- blkoff = (inodeno % inodes_per_block) * fs->inodesz;
- ext4fs_devread((lbaint_t)itable_blkno * fs->sect_perblk, 0, fs->blksz,
- temp_ptr);
- if (ext4fs_log_journal(temp_ptr, itable_blkno))
- goto fail;
-
- memcpy(temp_ptr + blkoff, inode_buffer, fs->inodesz);
- if (ext4fs_put_metadata(temp_ptr, itable_blkno))
- goto fail;
- /* copy the file content into data blocks */
- if (ext4fs_write_file(file_inode, 0, sizebytes, (char *)buffer) == -1) {
- printf("Error in copying content\n");
- goto fail;
- }
- ibmap_idx = parent_inodeno / ext4fs_root->sblock.inodes_per_group;
- parent_inodeno--;
- parent_itable_blkno = __le32_to_cpu(fs->bgd[ibmap_idx].inode_table_id) +
- (parent_inodeno %
- __le32_to_cpu(sblock->inodes_per_group)) / inodes_per_block;
- blkoff = (parent_inodeno % inodes_per_block) * fs->inodesz;
- if (parent_itable_blkno != itable_blkno) {
- memset(temp_ptr, '\0', fs->blksz);
- ext4fs_devread((lbaint_t)parent_itable_blkno * fs->sect_perblk,
- 0, fs->blksz, temp_ptr);
- if (ext4fs_log_journal(temp_ptr, parent_itable_blkno))
- goto fail;
-
- memcpy(temp_ptr + blkoff, g_parent_inode,
- sizeof(struct ext2_inode));
- if (ext4fs_put_metadata(temp_ptr, parent_itable_blkno))
- goto fail;
- free(temp_ptr);
- } else {
- /*
- * If parent and child fall in same inode table block
- * both should be kept in 1 buffer
- */
- memcpy(temp_ptr + blkoff, g_parent_inode,
- sizeof(struct ext2_inode));
- gd_index--;
- if (ext4fs_put_metadata(temp_ptr, itable_blkno))
- goto fail;
- free(temp_ptr);
- }
- ext4fs_update();
- ext4fs_deinit();
-
- fs->first_pass_bbmap = 0;
- fs->curr_blkno = 0;
- fs->first_pass_ibmap = 0;
- fs->curr_inode_no = 0;
- free(inode_buffer);
- free(g_parent_inode);
- g_parent_inode = NULL;
-
- return 0;
-fail:
- ext4fs_deinit();
- free(inode_buffer);
- free(g_parent_inode);
- g_parent_inode = NULL;
-
- return -1;
-}
diff --git a/qemu/roms/u-boot/fs/ext4/ext4fs.c b/qemu/roms/u-boot/fs/ext4/ext4fs.c
deleted file mode 100644
index 417ce7b63..000000000
--- a/qemu/roms/u-boot/fs/ext4/ext4fs.c
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * (C) Copyright 2011 - 2012 Samsung Electronics
- * EXT4 filesystem implementation in Uboot by
- * Uma Shankar <uma.shankar@samsung.com>
- * Manjunatha C Achar <a.manjunatha@samsung.com>
- *
- * ext4ls and ext4load : Based on ext2 ls and load support in Uboot.
- * Ext4 read optimization taken from Open-Moko
- * Qi bootloader
- *
- * (C) Copyright 2004
- * esd gmbh <www.esd-electronics.com>
- * Reinhard Arlt <reinhard.arlt@esd-electronics.com>
- *
- * based on code from grub2 fs/ext2.c and fs/fshelp.c by
- * GRUB -- GRand Unified Bootloader
- * Copyright (C) 2003, 2004 Free Software Foundation, Inc.
- *
- * ext4write : Based on generic ext4 protocol.
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
-
-#include <common.h>
-#include <ext_common.h>
-#include <ext4fs.h>
-#include "ext4_common.h"
-
-int ext4fs_symlinknest;
-struct ext_filesystem ext_fs;
-
-struct ext_filesystem *get_fs(void)
-{
- return &ext_fs;
-}
-
-void ext4fs_free_node(struct ext2fs_node *node, struct ext2fs_node *currroot)
-{
- if ((node != &ext4fs_root->diropen) && (node != currroot))
- free(node);
-}
-
-/*
- * Taken from openmoko-kernel mailing list: By Andy green
- * Optimized read file API : collects and defers contiguous sector
- * reads into one potentially more efficient larger sequential read action
- */
-int ext4fs_read_file(struct ext2fs_node *node, int pos,
- unsigned int len, char *buf)
-{
- struct ext_filesystem *fs = get_fs();
- int i;
- lbaint_t blockcnt;
- int log2blksz = fs->dev_desc->log2blksz;
- int log2_fs_blocksize = LOG2_BLOCK_SIZE(node->data) - log2blksz;
- int blocksize = (1 << (log2_fs_blocksize + log2blksz));
- unsigned int filesize = __le32_to_cpu(node->inode.size);
- lbaint_t previous_block_number = -1;
- lbaint_t delayed_start = 0;
- lbaint_t delayed_extent = 0;
- lbaint_t delayed_skipfirst = 0;
- lbaint_t delayed_next = 0;
- char *delayed_buf = NULL;
- short status;
-
- /* Adjust len so it we can't read past the end of the file. */
- if (len > filesize)
- len = filesize;
-
- blockcnt = ((len + pos) + blocksize - 1) / blocksize;
-
- for (i = pos / blocksize; i < blockcnt; i++) {
- lbaint_t blknr;
- int blockoff = pos % blocksize;
- int blockend = blocksize;
- int skipfirst = 0;
- blknr = read_allocated_block(&(node->inode), i);
- if (blknr < 0)
- return -1;
-
- blknr = blknr << log2_fs_blocksize;
-
- /* Last block. */
- if (i == blockcnt - 1) {
- blockend = (len + pos) % blocksize;
-
- /* The last portion is exactly blocksize. */
- if (!blockend)
- blockend = blocksize;
- }
-
- /* First block. */
- if (i == pos / blocksize) {
- skipfirst = blockoff;
- blockend -= skipfirst;
- }
- if (blknr) {
- int status;
-
- if (previous_block_number != -1) {
- if (delayed_next == blknr) {
- delayed_extent += blockend;
- delayed_next += blockend >> log2blksz;
- } else { /* spill */
- status = ext4fs_devread(delayed_start,
- delayed_skipfirst,
- delayed_extent,
- delayed_buf);
- if (status == 0)
- return -1;
- previous_block_number = blknr;
- delayed_start = blknr;
- delayed_extent = blockend;
- delayed_skipfirst = skipfirst;
- delayed_buf = buf;
- delayed_next = blknr +
- (blockend >> log2blksz);
- }
- } else {
- previous_block_number = blknr;
- delayed_start = blknr;
- delayed_extent = blockend;
- delayed_skipfirst = skipfirst;
- delayed_buf = buf;
- delayed_next = blknr +
- (blockend >> log2blksz);
- }
- } else {
- if (previous_block_number != -1) {
- /* spill */
- status = ext4fs_devread(delayed_start,
- delayed_skipfirst,
- delayed_extent,
- delayed_buf);
- if (status == 0)
- return -1;
- previous_block_number = -1;
- }
- memset(buf, 0, blocksize - skipfirst);
- }
- buf += blocksize - skipfirst;
- }
- if (previous_block_number != -1) {
- /* spill */
- status = ext4fs_devread(delayed_start,
- delayed_skipfirst, delayed_extent,
- delayed_buf);
- if (status == 0)
- return -1;
- previous_block_number = -1;
- }
-
- return len;
-}
-
-int ext4fs_ls(const char *dirname)
-{
- struct ext2fs_node *dirnode;
- int status;
-
- if (dirname == NULL)
- return 0;
-
- status = ext4fs_find_file(dirname, &ext4fs_root->diropen, &dirnode,
- FILETYPE_DIRECTORY);
- if (status != 1) {
- printf("** Can not find directory. **\n");
- return 1;
- }
-
- ext4fs_iterate_dir(dirnode, NULL, NULL, NULL);
- ext4fs_free_node(dirnode, &ext4fs_root->diropen);
-
- return 0;
-}
-
-int ext4fs_exists(const char *filename)
-{
- int file_len;
-
- file_len = ext4fs_open(filename);
- return file_len >= 0;
-}
-
-int ext4fs_read(char *buf, unsigned len)
-{
- if (ext4fs_root == NULL || ext4fs_file == NULL)
- return 0;
-
- return ext4fs_read_file(ext4fs_file, 0, len, buf);
-}
-
-int ext4fs_probe(block_dev_desc_t *fs_dev_desc,
- disk_partition_t *fs_partition)
-{
- ext4fs_set_blk_dev(fs_dev_desc, fs_partition);
-
- if (!ext4fs_mount(fs_partition->size)) {
- ext4fs_close();
- return -1;
- }
-
- return 0;
-}
-
-int ext4_read_file(const char *filename, void *buf, int offset, int len)
-{
- int file_len;
- int len_read;
-
- if (offset != 0) {
- printf("** Cannot support non-zero offset **\n");
- return -1;
- }
-
- file_len = ext4fs_open(filename);
- if (file_len < 0) {
- printf("** File not found %s **\n", filename);
- return -1;
- }
-
- if (len == 0)
- len = file_len;
-
- len_read = ext4fs_read(buf, len);
-
- return len_read;
-}