1 /*
2
3 File: ext2p.c
4
5 Copyright (C) 2007-2008 Christophe GRENIER <grenier@cgsecurity.org>
6
7 This software is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License along
18 with this program; if not, write the Free Software Foundation, Inc., 51
19 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20
21 */
22 #ifdef HAVE_CONFIG_H
23 #include <config.h>
24 #endif
25 #include <stdio.h>
26 #ifdef HAVE_STDLIB_H
27 #include <stdlib.h>
28 #endif
29 #ifdef HAVE_STRING_H
30 #include <string.h>
31 #endif
32 #include "types.h"
33 #include "common.h"
34 #include "list.h"
35 #include "filegen.h"
36 #include "intrf.h"
37 #include "dir.h"
38 #ifdef HAVE_EXT2FS_EXT2_FS_H
39 #include "ext2fs/ext2_fs.h"
40 #endif
41 #ifdef HAVE_EXT2FS_EXT2FS_H
42 #include "ext2fs/ext2fs.h"
43 #endif
44 #include "ext2p.h"
45 #include "ext2_inc.h"
46 #include "ext2_dir.h"
47 #include "log.h"
48 #include "log_part.h"
49
50 #ifdef HAVE_LIBEXT2FS
ext2_remove_used_space(disk_t * disk,const partition_t * partition,alloc_data_t * list_search_space)51 unsigned int ext2_remove_used_space(disk_t *disk, const partition_t *partition, alloc_data_t *list_search_space)
52 {
53 dir_data_t dir_data;
54 switch(dir_partition_ext2_init(disk, partition, &dir_data, 0))
55 {
56 case DIR_PART_ENOIMP:
57 case DIR_PART_ENOSYS:
58 return 0;
59 case DIR_PART_EIO:
60 log_partition(disk, partition);
61 log_error("Can't open filesystem. Filesystem seems damaged.\n");
62 return 0;
63 case DIR_PART_OK:
64 break;
65 }
66 {
67 const unsigned int sizeof_buffer=512;
68 struct ext2_dir_struct *ls=(struct ext2_dir_struct *)dir_data.private_dir_data;
69 unsigned char *buffer;
70 uint64_t start_free=0;
71 uint64_t end_free=0;
72 unsigned long int block;
73 unsigned long int start,end;
74 const unsigned int blocksize=ls->current_fs->blocksize;
75 ext2fs_block_bitmap bitmap;
76 if(ext2fs_read_block_bitmap(ls->current_fs))
77 {
78 log_error("ext2fs_read_block_bitmap failed\n");
79 return 0;
80 }
81 bitmap=ls->current_fs->block_map;
82 if(bitmap==NULL)
83 return 0;
84 #ifdef HAVE_EXT2FS_GET_GENERIC_BITMAP_START
85 start=ext2fs_get_generic_bitmap_start(bitmap);
86 end=ext2fs_get_generic_bitmap_end(bitmap);
87 #else
88 start=bitmap->start;
89 end=bitmap->end;
90 #endif
91 log_trace("ext2_remove_used_space %lu-%lu\n", start, end);
92 buffer=(unsigned char *)MALLOC(sizeof_buffer);
93 for(block=start;block<=end;block++)
94 {
95 #ifdef HAVE_EXT2FS_GET_GENERIC_BITMAP_START
96 if(ext2fs_test_generic_bitmap(bitmap,block)!=0)
97 #else
98 if(ext2fs_test_bit(block - bitmap->start, bitmap->bitmap)!=0)
99 #endif
100 {
101 /* Not free */
102 if(end_free+1==partition->part_offset+(uint64_t)block*blocksize)
103 end_free+=blocksize;
104 else
105 {
106 if(start_free != end_free)
107 del_search_space(list_search_space, start_free, end_free);
108 start_free=partition->part_offset+(uint64_t)block*blocksize;
109 end_free=start_free+(uint64_t)blocksize-1;
110 }
111 }
112 }
113 free(buffer);
114 if(start_free != end_free)
115 del_search_space(list_search_space, start_free, end_free);
116 dir_data.close(&dir_data);
117 return blocksize;
118 }
119 }
120 #endif
121