blob: 8a405012b67210c5b92d6da2115a6ddad7141be5 [file] [log] [blame]
Theodore Ts'o3839e651997-04-26 13:21:57 +00001/*
2 * badblocks.c --- routines to manipulate the bad block structure
3 *
4 * Copyright (C) 1994 Theodore Ts'o. This file may be redistributed
5 * under the terms of the GNU Public License.
6 */
7
8#include <stdio.h>
9#include <string.h>
10#include <unistd.h>
11#include <stdlib.h>
12#include <fcntl.h>
13#include <time.h>
14#include <sys/stat.h>
15#include <sys/types.h>
16
Theodore Ts'o3839e651997-04-26 13:21:57 +000017#include <linux/ext2_fs.h>
18
19#include "ext2fs.h"
20
21/*
22 * This procedure create an empty badblocks list.
23 */
24errcode_t badblocks_list_create(badblocks_list *ret, int size)
25{
26 badblocks_list bb;
27
28 bb = malloc(sizeof(struct struct_badblocks_list));
29 if (!bb)
30 return ENOMEM;
31 memset(bb, 0, sizeof(struct struct_badblocks_list));
Theodore Ts'of3db3561997-04-26 13:34:30 +000032 bb->magic = EXT2_ET_MAGIC_BADBLOCKS_LIST;
Theodore Ts'o3839e651997-04-26 13:21:57 +000033 bb->size = size ? size : 10;
34 bb->list = malloc(bb->size * sizeof(blk_t));
35 if (!bb->list) {
36 free(bb);
37 return ENOMEM;
38 }
39 *ret = bb;
40 return 0;
41}
42
43/*
44 * This procedure frees a badblocks list.
45 */
46void badblocks_list_free(badblocks_list bb)
47{
Theodore Ts'of3db3561997-04-26 13:34:30 +000048 if (bb->magic != EXT2_ET_MAGIC_BADBLOCKS_LIST)
49 return;
50
Theodore Ts'o3839e651997-04-26 13:21:57 +000051 if (bb->list)
52 free(bb->list);
53 bb->list = 0;
54 free(bb);
55}
56
57/*
58 * This procedure adds a block to a badblocks list.
59 */
60errcode_t badblocks_list_add(badblocks_list bb, blk_t blk)
61{
62 int i;
63
Theodore Ts'of3db3561997-04-26 13:34:30 +000064 EXT2_CHECK_MAGIC(bb, EXT2_ET_MAGIC_BADBLOCKS_LIST);
65
Theodore Ts'o3839e651997-04-26 13:21:57 +000066 for (i=0; i < bb->num; i++)
67 if (bb->list[i] == blk)
68 return 0;
69
70 if (bb->num >= bb->size) {
71 bb->size += 10;
72 bb->list = realloc(bb->list, bb->size * sizeof(blk_t));
73 if (!bb->list) {
74 bb->size = 0;
75 bb->num = 0;
76 return ENOMEM;
77 }
78 }
79
80 bb->list[bb->num++] = blk;
81 return 0;
82}
83
84/*
85 * This procedure tests to see if a particular block is on a badblocks
86 * list.
87 */
88int badblocks_list_test(badblocks_list bb, blk_t blk)
89{
90 int i;
91
Theodore Ts'of3db3561997-04-26 13:34:30 +000092 EXT2_CHECK_MAGIC(bb, EXT2_ET_MAGIC_BADBLOCKS_LIST);
93
Theodore Ts'o3839e651997-04-26 13:21:57 +000094 for (i=0; i < bb->num; i++)
95 if (bb->list[i] == blk)
96 return 1;
97
98 return 0;
99}
100
101errcode_t badblocks_list_iterate_begin(badblocks_list bb,
102 badblocks_iterate *ret)
103{
104 badblocks_iterate iter;
105
Theodore Ts'of3db3561997-04-26 13:34:30 +0000106 EXT2_CHECK_MAGIC(bb, EXT2_ET_MAGIC_BADBLOCKS_LIST);
107
Theodore Ts'o3839e651997-04-26 13:21:57 +0000108 iter = malloc(sizeof(struct struct_badblocks_iterate));
109 if (!iter)
110 return ENOMEM;
111
Theodore Ts'of3db3561997-04-26 13:34:30 +0000112 iter->magic = EXT2_ET_MAGIC_BADBLOCKS_ITERATE;
Theodore Ts'o3839e651997-04-26 13:21:57 +0000113 iter->bb = bb;
114 iter->ptr = 0;
115 *ret = iter;
116 return 0;
117}
118
119int badblocks_list_iterate(badblocks_iterate iter, blk_t *blk)
120{
Theodore Ts'of3db3561997-04-26 13:34:30 +0000121 badblocks_list bb;
122
123 if (iter->magic != EXT2_ET_MAGIC_BADBLOCKS_ITERATE)
124 return 0;
125
126 bb = iter->bb;
127
128 if (bb->magic != EXT2_ET_MAGIC_BADBLOCKS_LIST)
129 return 0;
Theodore Ts'o3839e651997-04-26 13:21:57 +0000130
131 if (iter->ptr < bb->num) {
132 *blk = bb->list[iter->ptr++];
133 return 1;
134 }
135 *blk = 0;
136 return 0;
137}
138
139void badblocks_list_iterate_end(badblocks_iterate iter)
140{
Theodore Ts'of3db3561997-04-26 13:34:30 +0000141 if (!iter || (iter->magic != EXT2_ET_MAGIC_BADBLOCKS_ITERATE))
142 return;
143
Theodore Ts'o3839e651997-04-26 13:21:57 +0000144 iter->bb = 0;
145 free(iter);
146}
147
148
149
150
151