急!!谁有MCU读写FLASH的汇编源代码????(FLASH型号不限)
急!!谁有MCU读写FLASH的汇编源代码????(FLASH型号不限) 问题点数:0、回复次数:6Top
1 楼baichunyu123(black)回复于 2005-06-09 15:33:21 得分 0
你去google去艘呀,要不我给你发一个:
是430单片机的
Top
2 楼baichunyu123(black)回复于 2005-06-09 15:33:59 得分 0
#include "msp430x44x.h"
;---------RAM初始化----------------------------------------------------------
;----------------------------------------------------------------------------
rxtx12c equ 301h ; 要发送的数据缓存
txrx12c equ 302h ;要接收的数据缓存
addrpa1 equ 304h ;页被寻地址高地址字节
addrpa0 equ 303h ;;页被寻址低地址字节(末位为位地址)
addrba1 equ 305h ;;位被寻址低地址字节
bit12c equ 306h ;数据位计数寄存器
code equ 307h ; 指令代码存储器
pout_data equ 308h ; 要发送的数据个数
pin_data equ 309h ; 要接收的数据个数
rx_point equ 310h ;接收数据存放地址寄存器
tx_point equ 312h ;发送数据存放地址寄存器
;-----------------------------------------------------------------------------
;---------- 端口定义----------------------------------------------------------
;-----------------------------------------------------------------------------
wp equ 001h ;P6.0 WP
rset equ 002h ;P6.1 RESET
rd_busy equ 004h ;P6.2 RD_BUSY
so equ 008h ;P6.3 SO
si equ 010h ;P6.4 SI
sck equ 020h ;P6.5 SCK
cs equ 040h ;P6.6 CS
;-----------------------------------------------------------------------------
;---------- 程序开始处--------------------------------------------------------
;-----------------------------------------------------------------------------
ORG 01100h
RESET mov.w #0a00h,SP ; 指定堆栈开始处
Init_Sys mov.w #WDTPW+WDTHOLD,&WDTCTL ; 禁止看门狗
bis.b #SELM_A+FLL_DIV_8,&FLL_CTL1 ;时钟初始化
main
bic.b #si+so+cs+wp+rset+sck+rd_busy,&P6DIR; ;端口初始化
bic.b #si+so+cs+wp+rset+sck+rd_busy,&P6SEL
bis.b #rset+wp+cs+sck,&P6DIR ;WP,RESET ,cs ,sck置高
bis.b #rset+wp+cs+sck,&P6OUT
clr.b r14
mov.w #250h,rx_point ;接收数据存放地址首地址为250h
mov.b #0fh,pin_data ;要接收数据个数为15个
mov.b #0fh,pout_data ;要发送数据个数为15个
;------------------------------------------------------------------------------
;----------写数据子程序 --------------------------------------------------------
;将TAB中的15个数据写DATA FLASH--------------------------------------------------
;------------------------------------------------------------------------------
write_data mov.b #84h,code ;要执行的指令
mov.b #00h,addrpa1 ;要写入页高地址
mov.b #00h,addrpa0 ;要写入页低地址
mov.b #01ah,addrba1 ;要写入位低地址
bis.b #cs,P6DIR ;选通cs
mov.b code,rxtx12c
bic.b #cs,P6OUT
nop
nop
call #DF_star ;启动AT45DB041
mov.b addrpa1,rxtx12c
call #DF_tx ;写页高地址
mov.b addrpa0,rxtx12c
call #DF_tx ;写页低地址
mov.b addrba1,rxtx12c ;写段地址(起始地址)
call #DF_tx
mov #tab,tx_point ;要发送数据表格的首地址
mov &tx_point,R14 ;将首地址给R14
loop_tx1
mov.b 0(r14),&rxtx12c ;将发送数据送入发送缓存
loop_tx2
call #DF_tx ;发送数据
inc.w r14
dec.b pout_data
jnz loop_tx1 ;判断是否发送完了
call #DF_stop ;完了,停止数据传输
;------------------------------------------------------------------------------------
;-----------延时子程序----------------------------------------------------------------
;------------------------------------------------------------------------------------
mov #0ffffh,r15
delay dec.b r15
jnz delay
;------------------------------------------------------------------------------------
;读数据子程序?
;把刚写入的数据读出并放入250H为首地址的去RAM中
;------------------------------------------------------------------------------------
Read_DATA
mov.b #54h,code ;要执行的指令
mov.b #00h,addrpa1 ;要写入页高地址
mov.b #00h,addrpa0 ;要写入页低地址
mov.b #01ah,addrba1 ;要写入段地址
bis.b #cs,P6DIR;选通cs
mov rx_point,r15 ;将接收数据存放区首地址给R15
mov.b code,rxtx12c
bic.b #cs,P6OUT
nop
nop
call #DF_star
mov.b addrpa1,rxtx12c
call #DF_tx
mov.b addrpa0,rxtx12c
call #DF_tx
mov.b addrba1,rxtx12c
call #DF_tx
mov.b #0ffh,rxtx12c ;些54H命令的附加脉冲
call #DF_tx
loop_rx
call #DF_rx ;开始接收数据
mov.b txrx12c,0(R15) ;将接收到数据送入接收数据存放区
inc.w R15
dec.b pin_data
jnz loop_rx ;判断是否接收完
call #DF_stop
nop
nop
jmp $ ;暂停程序,如果要继续,再jmp $前加;
jmp main ;程序返回RESET
ret
;--------------------------------------------------------------------------------------
Top
3 楼baichunyu123(black)回复于 2005-06-09 15:34:13 得分 0
;-------- 启动AT45DB041---------------------------------------------------------------
;--------------------------------------------------------------------------------------
DF_star bic.b #si+sck,&P6DIR
bis.b #si,&P6DIR
bis.b #sck,&P6DIR
bis.b #sck,&P6OUT
nop
nop
call #DF_tx
ret
;--------------------------------------------------------------------------------------
;----------发送一字节子程序------------------------------------------------------------
;--------------------------------------------------------------------------------------
DF_tx mov.b #08,bit12c
DF_CLK bic.b #sck,&P6OUT
DF_send rla.b rxtx12c
jc DF_send1
DF_send0 bic.b #si,&P6OUT
jmp DF_sx
DF_send1 bis.b #si,&P6OUT
DF_sx
bis.b #sck,&P6OUT
dec.b bit12c
jnz DF_CLK
ret
;-------------------------------------------------------------------------------------
;----------接收一字节子----------------------------------------------------------------
;-------------------------------------------------------------------------------------
DF_rx bis.b #sck,&P6DIR
bic.b #so,&P6DIR
mov.b #08h,bit12c
DF_sck bic.b #sck,&P6OUT
bis.b #sck,&P6OUT
nop
nop
bit.b #so, &P6IN
jnz bit1
bit0 bic.b #01h,txrx12c
jmp bit_sx
bit1 bis.b #01h,txrx12c
bit_sx bic.b #sck,&P6OUT
dec.b bit12c
jnz move_bite
jmp ret_1
move_bite rla.b txrx12c
jmp DF_sck
ret_1
ret
;-------------------------------------------------------------------------------------
;----------结束子程序 --------------------------------------------------------------
;-------------------------------------------------------------------------------------
DF_stop bic.b #si+so+cs+wp+rset+sck+rd_busy,&P6DIR
bis.b #rset+wp+cs+sck,&P6DIR;WP,RESET, CS+SCK 置高
bis.b #rset+wp+cs+sck,&P6OUT
ret
;------------------------------------------------------------------------------------
;----------定义TAB表-----------------------------------------------------------------
;------------------------------------------------------------------------------------
even
tab db 01h,02h,03h,04h,05h,06h,07h,08h,09h,0ah,0bh,0ch,0dh,0eh,0fh;
;------------------------------------------------------------------------------------
;--------定义中断向量---------------------------------------------------------------
;-----------------------------------------------------------------------------------
ORG 0FFFEH
DW RESET
END
Top
4 楼hansin(将冰山劈开)回复于 2005-06-09 15:48:25 得分 0
你的MCU是什么的?
随便选中你的flash,在MOVX就行了Top
5 楼domhuang(不名)回复于 2005-06-09 15:50:58 得分 0
www.ti.com.cn
msp 430 的Top
6 楼romyks(小强)回复于 2005-06-14 08:31:20 得分 0
给你一个C语言的.
//flash.c
WORD RamEraseBlock(DWORD addr)
{
long *p,*q;
p=(long*)((addr+BLOCK_SIZE-1)/BLOCK_SIZE *BLOCK_SIZE);
q=(long*)((long)p+BLOCK_SIZE);
while(p<q)
*p++=0xffffffff;
return 0;
}
WORD RamWrite(DWORD addr,DWORD size,BYTE_PTR buf)
{
char *p;
p=(char*)addr;
memcpy(p,buf,size);
// while(size-->0)
// *p++&=*buf++;
return 0;
}
#define USE_DISABLE unsigned short sr;unsigned long imr
#define DISABLE7 {asm(" move sr,{sr}");asm(" ori.w #0x700,sr");imr=*(long*)0xfffff304;*(long*)0xfffff304|=1<<23;}
#define ENABLE {asm(" move {sr},sr");*(long*)0xfffff304=imr;}
//j3 and c3 lock and unlock
void IntelLock(WORD *ba)
{
*ba=0x6060;
*ba=0x0101;
}
void IntelUnlock(WORD *ba) // J3 will clear all block's lock status , so J3 not good for lock and unlock
{
*ba=0x6060;
*ba=0xd0d0;
}
WORD IntelJ3EraseBlock(DWORD addr)
{
USE_DISABLE;
volatile WORD *ba;
int counter=0x100000;
// DISABLE7;
ba=(WORD*)(addr&0xfffffffe);
IntelUnlock(ba);
*ba=0xffff;
*ba=0x5050;
*ba=0x2020;
*ba=0xd0d0;
while(!(*ba&0x80));
*ba=0x5050;
IntelLock(ba);
*ba=0xffff;
// ENABLE;
return 0;
}
int nreadall,nwriteall;
char FlashDevReadChar(DWORD addr) // for quick read , no check
{ //, porting version (e.g NAND) should call FlashDevRead()
return *(char*)addr;
}
WORD FlashDevReadWord(DWORD addr)
{
return *(WORD*)addr;
}
DWORD FlashDevReadLong(DWORD addr)
{
return *(long*)addr;
}
WORD FlashDevRead(DWORD addr,DWORD size,BYTE_PTR buf)
{
volatile char *p;
volatile WORD *ba;
nreadall+=size;
ba=(WORD*)(addr&0xfffffffe);
//shoul not do it here, system should promise readable *ba=0xffff;
p=(char*)addr;
memcpy(buf,p,size);
// while(size-->0)
// *buf++=*p++;
return 0;
}
#define USE_BYTEWORD_PROGRAM
// C3 not support block write
WORD IntelJ3Write(DWORD addr,DWORD size,BYTE_PTR buf)
{
USE_DISABLE;
volatile WORD *p;
volatile WORD *ba;
WORD d;
WORD wbuffer[16],nwrite;
int i,writed=0;
nwriteall+=size;
ba=(WORD*)(addr&0xfffffffe);
IntelUnlock(ba);
// DISABLE7;
#ifdef USE_BYTEWORD_PROGRAM
// use byte/word program comand
// too slow , 5-10k bytes /sec
// C3 only support byteword program
if(addr&1) //
{
p=(WORD*)(addr-1);
// *p=0xffff;
// d=*p&0xff00;
d=0xff00; // lower byte write 0xff
d|=*buf;
buf++;
size--;
*p=0x5050; // clear status
*p=0x4040;
*p=d;
while(1)
{
*p=0x7070;
if(*p&0x80)
break;
}
p++;
}
else
p=(WORD*)addr;
while(size>1)
{
if((long)buf&1)
{
d=*buf++;
d<<=8;
d|=*buf++;
}
else
{
d=*(WORD*)buf;
buf+=2;
}
size-=2;
*p=0x5050; // clear status
*p=0x4040;
*p=d;
while(1)
{
*p=0x7070;
if(*p&0x80)
break;
}
p++;
}
if(size)// ==1
{
d=*buf;
d<<=8;
d|=0xff;// up byte write 0xff
*p=0x5050; // clear status
*p=0x4040;
*p=d;
while(1)
{
*p=0x7070;
if(*p&0x80)
break;
}
}
#else
// use write buffer program
*ba=0xffff;
*ba=0x5050;
nwrite=0;
if(addr&1) //
{
p=(WORD*)(addr-1);
d=0xff00; // lower byte write 0xff
d|=*buf;
buf++;
size--;
wbuffer[nwrite++]=d;
}
else
p=(WORD*)addr;
while(size>1)
{
if((long)buf&1)
{
d=*buf++;
d<<=8;
d|=*buf++;
}
else
{
d=*(WORD*)buf;
buf+=2;
}
size-=2;
addbuffer:
wbuffer[nwrite++]=d;
if(nwrite==16 || size==0)
{
if(writed)
{
*ba=0x7070;
while(!(*ba&0x80));
}
*p=0xe8e8;
while(!(*ba&0x80));
*p=(nwrite-1)|((nwrite-1)<<8);
for(i=0;i<nwrite;i++)
*p++=wbuffer[i];
*ba=0xd0d0;
nwrite=0;
writed=1;
}
}
if(size==1)
{
d=*buf;
d<<=8;
d|=0xff;// up byte write 0xff
size--;
goto addbuffer;
}
// p--; //because the last write maybe at flash end , so p will overflow
*ba=0x7070;
while(!(*ba&0x80));
#endif
*ba=0x5050;
IntelLock(ba);
*ba=0xffff;
// ENABLE;
return 0;
}
void WriteBlock ( BYTE *Dst,BYTE *Src,int len); // at fl_sst.c
int Erase_One_Block (BYTE *Dst);
int Erase_One_Sector (BYTE *Dst);
static short ramcall_Erase_One_Block[64],ramcall_Erase_One_Sector[64],ramcall_WriteBlock[64];
static char flash_write_buf[128];
WORD SSTWrite(DWORD addr,DWORD size,BYTE_PTR buf)
{
typedef void f_WriteBlock ( BYTE *Dst,BYTE *Src,int len); // at fl_sst.c
int nc;
unsigned short sr;
asm(" move sr,{sr}");asm(" ori.w #0x700,sr");
if(!ramcall_WriteBlock[0]) // copy code to flash ,avoid run code at flash
memcpy(ramcall_WriteBlock,(char*)&WriteBlock,128);
if(buf<0x1000000)
((f_WriteBlock*)ramcall_WriteBlock)(addr,buf,size);
else // source is also at flash , copy to ram then write
while(size>0)
{
if(size>128)
nc=128;
else
nc=size;
memcpy(flash_write_buf,buf,nc);
((f_WriteBlock*)ramcall_WriteBlock)(addr,flash_write_buf,nc);
addr+=nc;
buf+=nc;
size-=nc;
}
asm(" move {sr},sr");
// WriteBlock(addr,buf,size); //change to ramcall
return 0;
}
WORD SSTEraseBlock(DWORD addr)
{
typedef int f_Erase_One_Block (BYTE *Dst);
unsigned short sr;
asm(" move sr,{sr}");asm(" ori.w #0x700,sr");
if(!ramcall_Erase_One_Block[0])
memcpy(ramcall_Erase_One_Block,(char*)Erase_One_Block,128);
((f_Erase_One_Block*)ramcall_Erase_One_Block)(addr);
asm(" move {sr},sr");
// Erase_One_Block(addr);
return 0;
}
WORD SSTEraseSector(DWORD addr)
{
typedef int f_Erase_One_Sector (BYTE *Dst);
unsigned short sr;
asm(" move sr,{sr}");asm(" ori.w #0x700,sr");
if(!ramcall_Erase_One_Sector[0])
memcpy(ramcall_Erase_One_Sector,(char*)Erase_One_Sector,128);
((f_Erase_One_Sector*)ramcall_Erase_One_Sector)(addr);
asm(" move {sr},sr");
// Erase_One_Block(addr);
return 0;
}
#define DEVICE_NUMBER 1
typedef WORD fDevEraseBlock(DWORD addr);
typedef WORD fDevWrite(DWORD addr,DWORD size,BYTE_PTR buf);
struct _blockdevice{
char rootDir[8];
unsigned long beginAddr;
unsigned long size; //in byte
WORD BLOCK_COUNT;
WORD MAX_VSB;
fDevEraseBlock *erase;
fDevWrite *write;
// read method , to be extended ( read method is for NAND flash)
WORD *VSBTable;
WORD SpareBlock; /* Current spare block for each component */
WORD VSBLastFree,VSBLastAlloc; // find after them
int nVSBFree,nVSBValid,nVSBDiscarded; // maintain this table at:
WORD PhysicalVSBLastAlloc;
// write method , erase method, to be extended
}deviceTable[DEVICE_NUMBER+1]={
{
"/",COMPONENT_OFFSET,COMPONENT_SIZE,COMPONENT_SIZE/BLOCK_SIZE,(COMPONENT_SIZE/BLOCK_SIZE-1)*(VSB_PER_BLOCK-1),
SSTEraseBlock,SSTWrite},
// "/",COMPONENT_OFFSET,COMPONENT_SIZE,COMPONENT_SIZE/BLOCK_SIZE,(COMPONENT_SIZE/BLOCK_SIZE-1)*(VSB_PER_BLOCK-1),
// IntelJ3EraseBlock,IntelJ3Write},
// {"/RAM/",0x800000,0x800000,0x800000/BLOCK_SIZE,(0x800000/BLOCK_SIZE-1)*(VSB_PER_BLOCK-1),
// RamEraseBlock,RamWrite},
{NULL,0,0,0,},
};
WORD DeviceEraseBlock(DWORD addr)
{
struct _blockdevice *thisd;
thisd=deviceTable;
while(thisd->size)
{
if(addr>=thisd->beginAddr && addr<thisd->beginAddr+thisd->size)
return thisd->erase(addr);
else
thisd++;
}
return 0;//fail
}
WORD DeviceWrite(DWORD addr,DWORD size,BYTE_PTR buf)
{
struct _blockdevice *thisd;
thisd=deviceTable;
while(thisd->size)
{
if(addr>=thisd->beginAddr && addr<thisd->beginAddr+thisd->size)
return thisd->write(addr,size,buf);
else
thisd++;
}
return 0;//fail
}
int freeFlashSize(void)
{
return (deviceTable[0].nVSBFree+deviceTable[0].nVSBDiscarded)*VSB_SIZE;
}
int entireFlashSize(void) // only that use for flash file system
{
return COMPONENT_SIZE;
}
Top




