linux下对dataflash设备操作(擦除、写入文件)的应用程序,注意,所有的操作必须要使用mtdx的字符设备。
放出这个程序,帮助大家理解一些mtdchar的字符设备驱动!
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <fcntl.h>
#include <time.h>
#include <sys/ioctl.h>
#include <sys/mount.h>
#include <linux/compiler.h>
#include <mtd/mtd-user.h>
int non_region_erase(int Fd, int start, int count, int unlock)
{
mtd_info_t meminfo;
if (ioctl(Fd,MEMGETINFO,&meminfo) == 0)
{
erase_info_t erase;
erase.start = start;
erase.length = meminfo.erasesize;
for (; count > 0; count--) {
printf("/rPerforming Flash Erase of length %u at offset 0x%x",
erase.length, erase.start);
fflush(stdout);
if(unlock != 0)
{
//Unlock the sector first.
printf("/rPerforming Flash unlock at offset 0x%x",erase.start);
if(ioctl(Fd, MEMUNLOCK, &erase) != 0)
{
perror("/nMTD Unlock failure");
close(Fd);
return 8;
}
}
if (ioctl(Fd,MEMERASE,&erase) != 0)
{
perror("/nMTD Erase failure");
close(Fd);
return 8;
}
erase.start += meminfo.erasesize;
}
printf(" done/n");
}
return 0;
}
int main(int argc, char *argv[])
{
int fd,ifd;
int i,j;
char *cmd;
char *img;
struct mtd_info_user info;
int regcount;
int res = 0,cnt,write_cnt;
int imglen,imglen1;
int readlen=0;
char *write_buf;
if(3>argc)
{
printf("You must specify a device!/n");
return 16;
}
cmd=argv[1];
if (argc > 3)
{
img=argv[3];
}
// Open and size the device
if ((fd = open(argv[2],O_RDWR)) < 0)
{
fprintf(stderr,"File open error/n");
return 8;
}
else
{
ioctl(fd,MEMGETINFO,&info);
printf("info.size=%d/n info.erasesize=%d/n info.writesize=%d/n info.oobsize=%d /n",info.size,info.erasesize,info.writesize,info.oobsize);
}
if (ioctl(fd,MEMGETREGIONCOUNT,®count) == 0)
{
printf("regcount=%d/n",regcount);
}
/*erase the device*/
if (strcmp(cmd, "erase") == 0)
{
if(regcount == 0)
{
res = non_region_erase(fd,0,(info.size/info.erasesize),0);
}
printf("erase!/n");
}
/*write file to this device*/
if (strcmp(cmd, "write") == 0)
{
printf("write!/n");
if((ifd=open(img,O_RDONLY))==-1)
{
printf("open input file error!/n");
return 9;
}
else
{
imglen=lseek(ifd,0,SEEK_END);
lseek(ifd,0,SEEK_SET);
printf("The input file image len is %d!/n",imglen);
}
readlen=info.writesize;
write_buf=malloc(readlen);
if(write_buf==NULL)
{
printf("can't allocate memory!/n");
return 10;
}
else
printf("Write buf is ok!/n");
imglen1=imglen;
while(imglen)
{
memset(write_buf,0xff,readlen);
if((cnt=read(ifd,write_buf,readlen))!=readlen)
{
if(cnt<readlen)
printf("the file is end!/n");
else
{
printf("File I/O error on input file");
return 11;
}
}
if((write_cnt=write(fd,write_buf,readlen))!=readlen)
{
printf("write mtd device error! startaddr=%d/n",(imglen1-imglen));
return 12;
}
else
printf("/rwrite mtd device ok!startaddr=%d",(imglen1-imglen));
imglen-=cnt;
}
printf("/n");
return 0;
}
if (strcmp(cmd, "read") == 0)
{
printf("read!/n");
}
return 1;
}
命令格式:
擦除命令:
dataflash_ioctl erase /dev/mtd6
info.size=1968384
info.erasesize=528
info.writesize=528
info.oobsize=0
regcount=0
Performing Flash Erase of length 528 at offset 0x1e06f0 done
erase!
写入文件命令:
dataflash_ioctl write /dev/mtd6 /modules/uImage2.6.21
info.size=1968384
info.erasesize=528
info.writesize=528
info.oobsize=0
regcount=0
write!
The input file image len is 1406740!
Write buf is ok!
write mtd device ok!startaddr=1406064the file is write ok!
write mtd device ok!startaddr=1406592
修改u-boot的启动参数
cp.b d023f700 20400000 158000
其中d023f700是mtd6在flash中,u-boot识别的地址,20400000是内存地址,0x158000是长度!
放出这个程序,帮助大家理解一些mtdchar的字符设备驱动!
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <fcntl.h>
#include <time.h>
#include <sys/ioctl.h>
#include <sys/mount.h>
#include <linux/compiler.h>
#include <mtd/mtd-user.h>
int non_region_erase(int Fd, int start, int count, int unlock)
{
mtd_info_t meminfo;
if (ioctl(Fd,MEMGETINFO,&meminfo) == 0)
{
erase_info_t erase;
erase.start = start;
erase.length = meminfo.erasesize;
for (; count > 0; count--) {
printf("/rPerforming Flash Erase of length %u at offset 0x%x",
erase.length, erase.start);
fflush(stdout);
if(unlock != 0)
{
//Unlock the sector first.
printf("/rPerforming Flash unlock at offset 0x%x",erase.start);
if(ioctl(Fd, MEMUNLOCK, &erase) != 0)
{
perror("/nMTD Unlock failure");
close(Fd);
return 8;
}
}
if (ioctl(Fd,MEMERASE,&erase) != 0)
{
perror("/nMTD Erase failure");
close(Fd);
return 8;
}
erase.start += meminfo.erasesize;
}
printf(" done/n");
}
return 0;
}
int main(int argc, char *argv[])
{
int fd,ifd;
int i,j;
char *cmd;
char *img;
struct mtd_info_user info;
int regcount;
int res = 0,cnt,write_cnt;
int imglen,imglen1;
int readlen=0;
char *write_buf;
if(3>argc)
{
printf("You must specify a device!/n");
return 16;
}
cmd=argv[1];
if (argc > 3)
{
img=argv[3];
}
// Open and size the device
if ((fd = open(argv[2],O_RDWR)) < 0)
{
fprintf(stderr,"File open error/n");
return 8;
}
else
{
ioctl(fd,MEMGETINFO,&info);
printf("info.size=%d/n info.erasesize=%d/n info.writesize=%d/n info.oobsize=%d /n",info.size,info.erasesize,info.writesize,info.oobsize);
}
if (ioctl(fd,MEMGETREGIONCOUNT,®count) == 0)
{
printf("regcount=%d/n",regcount);
}
/*erase the device*/
if (strcmp(cmd, "erase") == 0)
{
if(regcount == 0)
{
res = non_region_erase(fd,0,(info.size/info.erasesize),0);
}
printf("erase!/n");
}
/*write file to this device*/
if (strcmp(cmd, "write") == 0)
{
printf("write!/n");
if((ifd=open(img,O_RDONLY))==-1)
{
printf("open input file error!/n");
return 9;
}
else
{
imglen=lseek(ifd,0,SEEK_END);
lseek(ifd,0,SEEK_SET);
printf("The input file image len is %d!/n",imglen);
}
readlen=info.writesize;
write_buf=malloc(readlen);
if(write_buf==NULL)
{
printf("can't allocate memory!/n");
return 10;
}
else
printf("Write buf is ok!/n");
imglen1=imglen;
while(imglen)
{
memset(write_buf,0xff,readlen);
if((cnt=read(ifd,write_buf,readlen))!=readlen)
{
if(cnt<readlen)
printf("the file is end!/n");
else
{
printf("File I/O error on input file");
return 11;
}
}
if((write_cnt=write(fd,write_buf,readlen))!=readlen)
{
printf("write mtd device error! startaddr=%d/n",(imglen1-imglen));
return 12;
}
else
printf("/rwrite mtd device ok!startaddr=%d",(imglen1-imglen));
imglen-=cnt;
}
printf("/n");
return 0;
}
if (strcmp(cmd, "read") == 0)
{
printf("read!/n");
}
return 1;
}
命令格式:
擦除命令:
dataflash_ioctl erase /dev/mtd6
info.size=1968384
info.erasesize=528
info.writesize=528
info.oobsize=0
regcount=0
Performing Flash Erase of length 528 at offset 0x1e06f0 done
erase!
写入文件命令:
dataflash_ioctl write /dev/mtd6 /modules/uImage2.6.21
info.size=1968384
info.erasesize=528
info.writesize=528
info.oobsize=0
regcount=0
write!
The input file image len is 1406740!
Write buf is ok!
write mtd device ok!startaddr=1406064the file is write ok!
write mtd device ok!startaddr=1406592
修改u-boot的启动参数
cp.b d023f700 20400000 158000
其中d023f700是mtd6在flash中,u-boot识别的地址,20400000是内存地址,0x158000是长度!