📄 ts101ezflash.c
字号:
//
//////////////////////////////////////////////////////////////
bool ReadFlash( long lOffset, int *pnValue )
{
// temp holder
int nValue = 0x0;
asm("xr0 = j4;;"); // xr0 = source index, j4 = nOffset
asm("xr1 = 0x00010001;;"); // count = 1, modify = 1
asm("xr2 = 0x0;;"); // not used
asm("xr3 = 0xc3000000;;"); // boot rom,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
asm("xr4 = _temp_stor;;"); // xr4 = destination index
asm("xr5 = 0x00010001;;"); // count = 1, modify = 1
asm("xr6 = 0x0;;"); // not used
asm("xr7 = 0x43000000;;"); // int mem,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
do_dma();
// put the value at the location passed in
*pnValue = temp_stor;
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool PollToggleBit()
//
// Polls to see if the value read equals the value written
//
// Inputs: int nOffset - offset to read from
// int nValue - value of data written
//
//////////////////////////////////////////////////////////////
bool PollToggleBit(long lOffset, int nValue )
{
bool bError = FALSE; // flag to indicate error
// read valid address in the range written to
asm ("POLL_TOGGLE_BIT:");
asm("xr0 = j4;;"); // xr0 = source index, j4 = lOffset
asm("xr1 = 0x00010001;;"); // count = 1, modify = 1
asm("xr2 = 0x0;;"); // not used
asm("xr3 = 0xc3000000;;"); // boot rom,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
asm("xr4 = _temp_stor;;"); // xr4 = destination index
asm("xr5 = 0x00010001;;"); // count = 1, modify = 1
asm("xr6 = 0x0;;"); // not used
asm("xr7 = 0x43000000;;"); // int mem,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
do_dma(); // read the value
asm("j0 = [j31 + _temp_stor];;"); // get data that was read
asm("xr0 = j0;;"); // need to be in compute block regs
asm("xr1 = j5;;"); // put data being set into xr1
asm("r1 = r0 xor r1;;"); // find out what bits toggled
// see if the data is toggling
asm ("BITEST r1 by 7;;");
asm("if xSEQ, jump DONE_TOGGLE_BIT; nop; nop; nop;;");
// see if there was an error
asm ("BITEST r0 by 5;;");
asm("if xSEQ, jump POLL_TOGGLE_BIT; nop; nop; nop;;");
// do another read
asm("xr0 = j4;;"); // xr0 = source index, j4 = lOffset
asm("xr1 = 0x00010001;;"); // count = 1, modify = 1
asm("xr2 = 0x0;;"); // not used
asm("xr3 = 0xc3000000;;"); // boot rom,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
asm("xr4 = _temp_stor;;"); // xr4 = destination index
asm("xr5 = 0x00010001;;"); // count = 1, modify = 1
asm("xr6 = 0x0;;"); // not used
asm("xr7 = 0x43000000;;"); // int mem,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
do_dma(); // read the value
asm("j0 = [j31 + _temp_stor];;"); // get data read
asm("xr0 = j0;;"); // need to be in compute block regs
asm("xr1 = j5;;"); // put data being set into xr1
asm("r1 = r0 xor r1;;"); // find out what bits toggled
// see if data is still toggling
asm ("BITEST r1 by 7;;");
asm("if xSEQ, jump DONE_TOGGLE_BIT; nop; nop; nop;;");
// else we have failed, restore page, set error flag, and reset
bError = TRUE;
ResetFlash();
asm ("DONE_TOGGLE_BIT:");
// we can return
return !bError;
}
//////////////////////////////////////////////////////////////
// bool ResetFlash()
//
// Sends a "reset" command to the flash.
//
//////////////////////////////////////////////////////////////
bool ResetFlash()
{
// send the reset command to the flash
WriteFlash( 0x0AAA, 0xf0 );
// reset should be complete
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool EraseFlash()
//
// Sends an "erase all" command to the flash.
//
//////////////////////////////////////////////////////////////
bool EraseFlash()
{
// erase contents in Main Flash Array
WriteFlash( 0x0aaa, 0xaa );
WriteFlash( 0x0555, 0x55 );
WriteFlash( 0x0aaa, 0x80 );
WriteFlash( 0x0aaa, 0xaa );
WriteFlash( 0x0555, 0x55 );
WriteFlash( 0x0aaa, 0x10 );
// poll until the command has completed
PollToggleBit(0x0000, 0x80);
// erase should be complete
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool EraseBlock()
//
// Sends an "erase block" command to the flash.
//
// Inputs: int nBlock - block to erase
//
//////////////////////////////////////////////////////////////
bool EraseBlock( int nBlock )
{
long lSectorOff = 0x0;
// if the block is invalid just return
if ( (nBlock < 0) || (nBlock > AFP_NumSectors) )
return FALSE;
// block is in valid Flash Array
if ( (nBlock >= 0) && (nBlock < 34) )
{
// send the erase block command to the flash
WriteFlash( 0x0aaa, 0xaa );
WriteFlash( 0x0555, 0x55 );
WriteFlash( 0x0aaa, 0x80 );
WriteFlash( 0x0aaa, 0xaa );
WriteFlash( 0x0555, 0x55 );
// the last write has to be at an address in the block
// we want to erase
lSectorOff = (nBlock * AFP_SectorSize1);
WriteFlash( lSectorOff, 0x30 );
// poll until the command has completed
PollToggleBit(lSectorOff, 0x80);
}
// block is in Boot Flash Array
else
{
}
// block erase should be complete
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool UnlockFlash()
//
// Sends an "unlock" command to the flash to allow the flash
// to be programmed.
//
// Inputs: long lOffset - offset to unlock
//
//////////////////////////////////////////////////////////////
bool UnlockFlash(long lOffset)
{
long lOffsetAddr = lOffset;
lOffsetAddr &= 0x000F0000;
// send the unlock command to the flash
// ORed with lOffsetAddr so we know what block we are in
WriteFlash( (0x0aaa | lOffsetAddr), 0xaa );
WriteFlash( (0x0555 | lOffsetAddr), 0x55 );
WriteFlash( (0x0aaa | lOffsetAddr), 0xa0 );
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool GetCodes()
//
// Sends an "auto select" command to the flash which will allow
// us to get the manufacturer and device codes.
//
//////////////////////////////////////////////////////////////
bool GetCodes()
{
int tmp;
// send the auto select command to the flash
WriteFlash( 0x0aaa, 0xaa );
WriteFlash( 0x0555, 0x55 );
WriteFlash( 0x0aaa, 0x90 );
// now we can read the codes
ReadFlash( 0x0000, &AFP_DevCode );
tmp = AFP_DevCode;
AFP_DevCode = (tmp>>16) & 0x00FF;
// there is no ManCode that can be read so make it 0x20
AFP_ManCode = tmp & 0x00FF;
// we need to issue another command to get the part out
// of auto select mode so issue a reset which just puts
// the device back in read mode
ResetFlash();
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool GetSectorNumber()
//
// Gets a sector number based on the offset.
//
// Inputs: long lOffset - offset in the sector
// int *pnSector - sector number
//
//////////////////////////////////////////////////////////////
bool GetSectorNumber( long lOffset, int *pnSector )
{
int nSector = 0;
// determine the sector
nSector = lOffset & 0xffff0000;
nSector = lOffset >> 16;
nSector = nSector & 0x00007;
// if it is a valid sector, set it
if ( (nSector >= 0) && (nSector < AFP_NumSectors) )
*pnSector = nSector;
// else it is an invalid sector
else
return FALSE;
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// void dma_int_0( int nothing )
//
// DMA interrupt handler, we come in here after the data block
// is done being DMAed
//
//////////////////////////////////////////////////////////////
void dma_int_0( int nothing )
{
return;
}
//////////////////////////////////////////////////////////////
// void do_dma()
//
// sets up our DMA registers and does the DMA
//
//////////////////////////////////////////////////////////////
void do_dma()
{
asm("DCS0 = xr3:0;;"); // setup DMA sourse
asm("DCD0 = xr7:4;;"); // setup DMA destination
asm("idle;;"); // wait for dma to finish
}
//////////////////////////////////////////////////////////////
// bool ReadToInternal()
//
// Used to DMA flash memory to internal memory so that the
// contents of flash can be viewed because the flash is not
// memory mapped
//
// Inputs: long lOffset - offset in flash to start the reads at
// long lCount - number of elements to read, in this case bytes
// long lStride - number of locations to skip between writes
//
//////////////////////////////////////////////////////////////
bool ReadToInternal(long lOffset, long lCount, long lStride)
{
// we only allocate 0x8FFF locations for debugging so
// check count to make sure we don't overwrite memory
if( lCount > 0x1FFF )
asm("j5 = 0x1FFF;;");
asm("xr1 = j5;;"); // j5 is the count
asm("xr1 = ashift r1 by 16;;"); // shift the count to upper 16
asm("xr2 = j6;;"); // j6 is the stride
asm("xr1 = r1 OR r2;;"); // OR in stride
asm("xr5 = xr1;;"); // set destination register the same
asm("xr0 = j4;;"); // xr0 = source index, j4 = nOffset
asm("xr2 = 0x0;;"); // not used
asm("xr3 = 0xc3000000;;"); // boot rom,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
asm("xr4 = 0x83000;;"); // xr4 = destination index / needs to change if debug section moves
asm("xr6 = 0x0;;"); // not used
asm("xr7 = 0x43000000;;"); // int mem,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
do_dma(); // set up dma registers
// ok
return TRUE;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -