http://git.infradead.org/mtd-utils.git?a=blob;f=flash_erase.c;h=fdf991852e7a723a846f67ac6a16e1b60b35e7e5;hb=HEAD
[mtd-utils.git] / flash_erase.c
1 /*
2 * flash_erase.c -- erase parts of a MTD device
3 */
4
5 #include <unistd.h>
6 #include <stdlib.h>
7 #include <stdio.h>
8 #include <fcntl.h>
9 #include <time.h>
10 #include <string.h>
11 #include <sys/ioctl.h>
12 #include <sys/mount.h>
13 #include <mtd/mtd-user.h>
14
15 int region_erase(int Fd, int start, int count, int unlock, int
regcount)
16 {
17 int i, j;
18 region_info_t * reginfo;
19
20 reginfo = calloc(regcount, sizeof(region_info_t));
21
22 for(i = 0; i < regcount; i++)
23 {
24 reginfo[i].regionindex = i;
25 if(ioctl(Fd,MEMGETREGIONINFO,&(reginfo[i])) != 0)
26 return 8;
27 else
28 printf("Region %d is at %d of %d sector and
with sector "
29 "size %x\n", i,
reginfo[i].offset, reginfo[i].numblocks,
30 reginfo[i].erasesize);
31 }
32
33 // We have all the information about the chip we need.
34
35 for(i = 0; i < regcount; i++)
36 { //Loop through the regions
37 region_info_t * r = &(reginfo[i]);
38
39 if((start >= reginfo[i].offset) &&
40 (start < (r->offset +
r->numblocks*r->erasesize)))
41 break;
42 }
43
44 if(i >= regcount)
45 {
46 printf("Starting offset %x not within chip.\n", start);
47 return 8;
48 }
49
50 //We are now positioned within region i of the chip, so
start erasing
51 //count sectors from there.
52
53 for(j = 0; (j < count)&&(i < regcount); j++)
54 {
55 erase_info_t erase;
56 region_info_t * r = &(reginfo[i]);
57
58 erase.start = start;
59 erase.length = r->erasesize;
60
61 if(unlock != 0)
62 { //Unlock the sector first.
63 if(ioctl(Fd, MEMUNLOCK, &erase) != 0)
64 {
65 perror("\nMTD Unlock failure");
66 close(Fd);
67 return 8;
68 }
69 }
70 printf("\rPerforming Flash Erase of length %u at
offset 0x%x",
71 erase.length, erase.start);
72 fflush(stdout);
73 if(ioctl(Fd, MEMERASE, &erase) != 0)
74 {
75 perror("\nMTD Erase failure");
76 close(Fd);
77 return 8;
78 }
79
80
81 start += erase.length;
82 if(start >= (r->offset + r->numblocks*r->erasesize))
83 { //We finished region i so move to region i+1
84 printf("\nMoving to region %d\n", i+1);
85 i++;
86 }
87 }
88
89 printf(" done\n");
90
91 return 0;
92 }
93
94 int non_region_erase(int Fd, int start, int count, int unlock)
95 {
96 mtd_info_t meminfo;
97
98 if (ioctl(Fd,MEMGETINFO,&meminfo) == 0)
99 {
100 erase_info_t erase;
101
102 erase.start = start;
103
104 erase.length = meminfo.erasesize;
105
106 for (; count > 0; count--) {
107 printf("\rPerforming Flash Erase of length
%u at offset 0x%x",
108 erase.length, erase.start);
109 fflush(stdout);
110
111 if(unlock != 0)
112 {
113 //Unlock the sector first.
114 printf("\rPerforming Flash unlock
at offset 0x%x",erase.start);
115 if(ioctl(Fd, MEMUNLOCK, &erase) != 0)
116 {
117 perror("\nMTD Unlock failure");
118 close(Fd);
119 return 8;
120 }
121 }
122
123 if (ioctl(Fd,MEMERASE,&erase) != 0)
124 {
125 perror("\nMTD Erase failure");
126 close(Fd);
127 return 8;
128 }
129 erase.start += meminfo.erasesize;
130 }
131 printf(" done\n");
132 }
133 return 0;
134 }
135
136 int main(int argc,char *argv[])
137 {
138 int regcount;
139 int Fd;
140 int start;
141 int count;
142 int unlock;
143 int res = 0;
144
145 if (1 >= argc || !strcmp(argv[1], "-h") || !strcmp
(argv[1], "--help") ) {
146 printf("Usage: flash_erase MTD-device [start] [cnt
(# erase blocks)] [lock]\n"
147 " flash_erase -h | --help\n") ;
148 return 16 ;
149 }
150
151 if (argc > 2)
152 start = strtol(argv[2], NULL, 0);
153 else
154 start = 0;
155
156 if (argc > 3)
157 count = strtol(argv[3], NULL, 0);
158 else
159 count = 1;
160
161 if(argc > 4)
162 unlock = strtol(argv[4], NULL, 0);
163 else
164 unlock = 0;
165
166
167 // Open and size the device
168 if ((Fd = open(argv[1],O_RDWR)) < 0)
169 {
170 fprintf(stderr,"File open error\n");
171 return 8;
172 }
173
174 printf("Erase Total %d Units\n", count);
175
176 if (ioctl(Fd,MEMGETREGIONCOUNT,®count) == 0)
177 {
178 if(regcount == 0)
179 {
180 res = non_region_erase(Fd, start, count,
unlock);
181 }
182 else
183 {
184 res = region_erase(Fd, start, count,
unlock, regcount);
185 }
186 }
187
188 return res;
189 }