FreeCalypso > hg > freecalypso-tools
diff ffstools/tiffs-rd/basics.c @ 0:e7502631a0f9
initial import from freecalypso-sw rev 1033:5ab737ac3ad7
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Sat, 11 Jun 2016 00:13:35 +0000 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ffstools/tiffs-rd/basics.c Sat Jun 11 00:13:35 2016 +0000 @@ -0,0 +1,155 @@ +/* + * This C module implements the "basics" of TIFFS image analysis. + */ + +#include <sys/types.h> +#include <sys/file.h> +#include <sys/stat.h> +#include <sys/mman.h> +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <string.h> +#include <strings.h> +#include "types.h" +#include "struct.h" +#include "globals.h" + +u8 tiffs_header[6] = {'F', 'f', 's', '#', 0x10, 0x02}; + +read_ffs_image() +{ + int fd; + struct stat st; + + fd = open(imgfile, O_RDONLY); + if (fd < 0) { + perror(imgfile); + exit(1); + } + fstat(fd, &st); + if (!S_ISREG(st.st_mode)) { + fprintf(stderr, "error: %s is not a regular file\n", imgfile); + exit(1); + } + if (st.st_size < imgfile_offset) { + fprintf(stderr, + "error: offset given with -o exceeds the size of the file\n"); + exit(1); + } + if (st.st_size - imgfile_offset < total_ffs_size) { + fprintf(stderr, + "error: %s is shorter than FFS size of 0x%lx bytes\n", + imgfile, (u_long)total_ffs_size); + exit(1); + } + image = mmap(NULL, total_ffs_size, PROT_READ, MAP_PRIVATE, fd, + imgfile_offset); + if (image == MAP_FAILED) { + perror("mmap"); + exit(1); + } + close(fd); +} + +cmd_blkhdr() +{ + int blk; + u8 *blkhdr; + + read_ffs_image(); + for (blk = 0; blk < total_blocks; blk++) { + printf("Block %3d: ", blk); + blkhdr = image + blk * eraseblk_size; + if (bcmp(blkhdr, tiffs_header, sizeof tiffs_header)) { + printf("No TIFFS header\n"); + continue; + } + printf("age %02X%02X, type/status %02X\n", + blkhdr[7], blkhdr[6], blkhdr[8]); + } + exit(0); +} + +find_inode_block() +{ + int i, abcnt; + u8 *ptr; + + if (index_blk_num >= 0) { + if (index_blk_num >= total_blocks) { + fprintf(stderr, + "invalid block # given with the -a option\n"); + exit(1); + } + ptr = image + index_blk_num * eraseblk_size; + if (bcmp(ptr, tiffs_header, sizeof tiffs_header)) { + fprintf(stderr, + "error: block specified with -a has no TIFFS header\n"); + exit(1); + } + if (ptr[8] != 0xAB) { + fprintf(stderr, + "error: block specified with -a is not an AB block\n"); + exit(1); + } + inode_block = ptr; + return(0); + } + abcnt = 0; + for (ptr = image, i = 0; i < total_blocks; i++, ptr += eraseblk_size) { + if (bcmp(ptr, tiffs_header, sizeof tiffs_header)) { + fprintf(stderr, + "warning: no TIFFS signature in erase block #%d (offset %x)\n", + i, ptr - image); + continue; + } + switch (ptr[8]) { + case 0xAB: + if (verbose) + fprintf(stderr, + "Found AB index in erase block #%d (offset %x)\n", + i, ptr - image); + index_blk_num = i; + inode_block = ptr; + abcnt++; + continue; + case 0xBD: + case 0xBF: + continue; + } + fprintf(stderr, + "warning: unexpected block type/status %02X at offset %x\n", + ptr[8], ptr - image); + } + if (!inode_block) { + fprintf(stderr, + "error: could not find an active inode block in %s\n", + imgfile); + exit(1); + } + if (abcnt > 1) { + fprintf(stderr, + "error: found more than one AB block; use -a\n"); + exit(1); + } + return(0); +} + +cmd_fsinfo() +{ + read_ffs_image(); + find_inode_block(); + printf("Active inode block (AB) is block #%d\n", index_blk_num); + alloc_inode_table(); + find_root_inode(); + printf("Root inode is #%x\n", root_inode); + if (validate_obj_name(root_inode, 1)) { + printf("Root inode (format) name: %s\n", + inode_info[root_inode]->dataptr); + exit(0); + } else { + printf("No valid name found in the root inode!\n"); + exit(1); + } +}