diff options
author | robi <robi> | 2011-10-23 12:24:44 +0000 |
---|---|---|
committer | robi <robi> | 2011-10-23 12:24:44 +0000 |
commit | 43108fe26c6c7c2168fe2253fbf7c30db0f8bab7 (patch) | |
tree | 5d781593b50024fe3ded04c9ed8f591cf8618636 /src/imap_search.c | |
parent | e19aee9ba2dd89c142329e1fe7cd1109149cba4d (diff) |
type sorted file names with extension in MAGIC-2/
Diffstat (limited to 'src/imap_search.c')
-rw-r--r-- | src/imap_search.c | 150 |
1 files changed, 145 insertions, 5 deletions
diff --git a/src/imap_search.c b/src/imap_search.c index 54578a2..0ed06db 100644 --- a/src/imap_search.c +++ b/src/imap_search.c @@ -27,9 +27,120 @@ #include "inode.h" #include <sys/stat.h> #include <errno.h> +#include "magic.h" extern ext2_filsys current_fs; +struct privat { + int count; + int error; + unsigned char* buf; + char flag; +}; + + +//Subfunction for "local_block_iterate3()" for load the first blocks to identify filetype +int first_blocks ( ext2_filsys fs, blk_t *blocknr, e2_blkcnt_t blockcnt, + blk_t /*ref_blk*/x, int /*ref_offset*/y, void *priv ) +{ + char *charbuf = NULL; + ((struct privat*)priv)->buf; + __u32 nbytes; + errcode_t retval; + int blocksize = fs->blocksize; + + if ((blockcnt >= 12) || ((struct privat*)priv)->count >=12) + return BLOCK_ABORT; + charbuf = ((struct privat*)priv)->buf + (blocksize * blockcnt); + + if (((struct privat*)priv)->flag){ + int allocated = ext2fs_test_block_bitmap ( fs->block_map, *blocknr ); + if ( allocated ){ + ((struct privat*)priv)->error = BLOCK_ABORT | BLOCK_ERROR ; + return (BLOCK_ABORT | BLOCK_ERROR); + } + } + + retval = io_channel_read_blk ( fs->io, *blocknr, 1, charbuf ); + ((struct privat*)priv)->count = blockcnt; + if (retval){ + ((struct privat*)priv)->error = BLOCK_ERROR ; + return (BLOCK_ERROR); + } +return retval; +} + + +static char* get_pathname(blk_t inode_nr, char* i_pathname, char *magic_buf, unsigned char* buf){ + struct found_data_t *help_data = NULL; + int str_len; + __u32 name_len; + char *c; + int def_len = 22; + char name_str[22]; + __u32 scan = 0; + + help_data = malloc(sizeof(struct found_data_t)); + if (!help_data) return NULL; + memset (help_data,0, sizeof(struct found_data_t)); + + if ( ident_file(help_data,&scan,magic_buf,buf)){ + help_data->type = scan; + str_len = strlen(magic_buf) + 1; + c = strpbrk(magic_buf,";:, "); + if (c){ + *c = 0; + name_len = c - magic_buf + def_len; + } + else + name_len = str_len + def_len; + + help_data->scan_result = malloc(str_len); + help_data->name = malloc(name_len); + if((!help_data->name) || (!help_data->scan_result)){ + free_file_data( help_data ); + fprintf(stderr,"ERROR: allocate memory\n"); + } + else{ + strcpy(help_data->scan_result,magic_buf); + strncpy(help_data->name, magic_buf , name_len - def_len+1); + sprintf(name_str,"/I_%010lu",inode_nr); + strcat(help_data->name,name_str); + get_file_property(help_data); + } + i_pathname = malloc(name_len); + if (i_pathname) + strncpy (i_pathname,help_data->name,name_len); + } + free_file_data(help_data); +return i_pathname; +} + + +static magic_t cookie = 0; + + +char* identify_filename(char* i_pathname, unsigned char *tmp_buf, struct ext2_inode* inode, blk_t inode_nr){ + struct privat priv ; + char magic_buf[100]; + int retval= 0; + + priv.count = priv.error = priv.flag = 0; + priv.buf = tmp_buf; + memset(magic_buf,0,100); + if ((inode->i_mode & LINUX_S_IFMT) == LINUX_S_IFREG){ + memset(tmp_buf,0,12 * current_fs->blocksize); + // iterate first 12 Data Blocks + retval = local_block_iterate3 ( current_fs, *inode, BLOCK_FLAG_DATA_ONLY, NULL, first_blocks, &priv ); + if (priv.count <12){ + strncpy(magic_buf, magic_buffer(cookie , tmp_buf, + ((inode->i_size < 12 * current_fs->blocksize) ? inode->i_size : (12 * current_fs->blocksize))), 60); + i_pathname = get_pathname(inode_nr, i_pathname, magic_buf, tmp_buf); + } + } + return i_pathname; +} + // search inode by use imap (step1: flag 1 = only directory ; step2: flag 0 = only file) static void search_imap_inode(char* des_dir, __u32 t_after, __u32 t_before, int flag) @@ -41,7 +152,9 @@ struct ring_buf* i_list = NULL; r_item* item = NULL; int zero_flag, retval, load, x ,i ; char *pathname = NULL; +char *i_pathname = NULL; char *buf= NULL; +unsigned char *tmp_buf = NULL; __u32 blocksize, inodesize, inode_max, inode_per_group, block_count; __u16 inode_per_block , inode_block_group, group; blk_t block_nr; @@ -55,6 +168,16 @@ inodesize = current_fs->super->s_inode_size; inode_max = current_fs->super->s_inodes_count; inode_per_group = current_fs->super->s_inodes_per_group; buf = malloc(blocksize); +if (! (flag & 0x01) ){ + tmp_buf = malloc (12 * blocksize); + if (!tmp_buf) + goto errout; + cookie = magic_open(MAGIC_MIME | MAGIC_NO_CHECK_COMPRESS | MAGIC_NO_CHECK_ELF | MAGIC_CONTINUE); + if ((! cookie) || magic_load(cookie, NULL)){ + fprintf(stderr,"ERROR: can't find libmagic\n"); + goto errout; + } +} inode_per_block = blocksize / inodesize; inode_block_group = inode_per_group / inode_per_block; @@ -115,7 +238,7 @@ for (group = 0 ; group < current_fs->group_desc_count ; group++){ } } // 1. magical step - if (LINUX_S_ISDIR(mode) && ( flag & 0x01) ){ + if (LINUX_S_ISDIR(mode) && ( flag & 0x01) && (pathname)){ sprintf(pathname,"<%lu>",inode_nr); @@ -132,7 +255,7 @@ for (group = 0 ; group < current_fs->group_desc_count ; group++){ else{ //search for all dir = get_dir3(NULL,0, inode_nr , "MAGIC-1",pathname, t_after,t_before, DELETED_OPT); if (dir) { - lookup_local(des_dir, dir,t_after,t_before, DELETED_OPT | RECOV_ALL | LOST_DIR_SEARCH ); + lookup_local(des_dir,dir,t_after,t_before,DELETED_OPT|RECOV_ALL|LOST_DIR_SEARCH); clear_dir_list(dir); } } @@ -148,8 +271,15 @@ for (group = 0 ; group < current_fs->group_desc_count ; group++){ if (item) { if (! LINUX_S_ISDIR(item->inode->i_mode) ) { + i_pathname = identify_filename(i_pathname, tmp_buf, + (struct ext2_inode*)item->inode, inode_nr); sprintf(pathname,"<%lu>",inode_nr); - recover_file(des_dir,"MAGIC-2", pathname, (struct ext2_inode*)item->inode, inode_nr, 0); + recover_file(des_dir,"MAGIC-2", ((i_pathname)?i_pathname : pathname), + (struct ext2_inode*)item->inode, inode_nr, 0); + if(i_pathname){ + free(i_pathname); + i_pathname = NULL; + } } } if (i_list) ring_del(i_list); @@ -159,6 +289,7 @@ for (group = 0 ; group < current_fs->group_desc_count ; group++){ } } } +errout: if (pathname) free(pathname); @@ -166,6 +297,15 @@ for (group = 0 ; group < current_fs->group_desc_count ; group++){ free(buf); buf = NULL; } + + if (tmp_buf){ + free(tmp_buf); + tmp_buf = NULL; + } + if (cookie){ + magic_close(cookie); + cookie = 0; + } return; } @@ -196,7 +336,7 @@ if (recovername && dirname){ } else{ if(check_dir(dirname)){ - fprintf(stderr,"Unknown error at target directory by file: %s\ntrying to continue normal\n", dirname); + fprintf(stderr,"Unknown error at target directory by file: %s\ntrying to continue normal\n", dirname); }else{ retval = rename(recovername, dirname); rename_hardlink_path(recovername, dirname); @@ -217,7 +357,7 @@ return retval; //2 step search for journalinode, will find some lost directory and files void imap_search(char* des_dir, __u32 t_after, __u32 t_before , int disaster ){ printf("MAGIC-1 : start lost directory search\n"); - search_imap_inode(des_dir, t_after, t_before, 1 | disaster ); //search for lost fragments of directorys +// search_imap_inode(des_dir, t_after, t_before, 1 | disaster ); //search for lost fragments of directorys printf("MAGIC-2 : start lost file search\n"); search_imap_inode(des_dir, t_after, t_before, 0 | disaster ); //search for lost files return; |