📄 ts101ezflash.c
字号:
///////////////////////////////////////////////////////////////
//
// TS101EzFlash.c
//
// Analog Devices, Inc. - 2002
//
// Rev - 1.00.0
//
// Fixes in this Release
//
//
// Change Log
//
// 1.00.0
// - initial release
//
// VisualDSP++ "Flash Programmer" flash driver for use with the
// ADSP-TS101S EZ-KIT Lite containing the STMicroelectronics DSM2150
// flash device.
//
// NOTE: In order to use inline assembly the compiler otion
// -flags-compiler --allow_asm must be added in project options.
// Also, there are warnings for each line ofinline assembly, which
// is supposed to be addressed in VisualDSP 3.0 for TigerSHARC.
// The warnings should not affect the functionality of our driver.
//
///////////////////////////////////////////////////////////////
#include <signal.h>
#include <defts101.h>
// #defines
#define TRUE 0x1
#define FALSE 0x0
#define NULL 0x0
#define BUFFER_SIZE 0x2000
// Flash Programmer commands
#define NO_COMMAND 0
#define GET_CODES 1
#define RESET 2
#define WRITE 3
#define FILL 4
#define ERASE_ALL 5
#define ERASE_SECT 6
#define READ 7
#define GET_SECTNUM 8
// function prototypes
bool SetupForFlash();
bool GetCodes();
bool PollToggleBit(long lOffset, int nValue);
bool ResetFlash();
bool EraseFlash();
bool EraseBlock( int nBlock );
bool UnlockFlash(long lOffset);
bool WriteData( long lStart, long lCount, long lStride, int *pnData );
bool FillData( long lStart, long lCount, long lStride, int *pnData );
bool ReadData( long lStart, long lCount, long lStride, int *pnData );
bool ReadFlash( long lOffset, int *pnValue );
bool WriteFlash( long lOffset, int nValue );
bool GetSectorNumber( long lOffset, int *pnSector );
// used for debugging purposes
bool ReadToInternal(long lOffset, long lCount, long lStride);
// DMA interrupt handler
void dma_int_0( int nothing );
// sets up DMA registers
void do_dma();
// global data for use with the VisualDSP++ plug-in
char AFP_Title[] = "ADSP-TS101 MP SYSTEM";
char AFP_Description[] = "HY. 29LV160";
int AFP_Command = NO_COMMAND;
int AFP_ManCode = -1; // 0x20 = STMicroelectronics
int AFP_DevCode = -1; // 0xE8 = DSM2150V
long AFP_Offset = 0x0;
int *AFP_Buffer;
long AFP_Size = BUFFER_SIZE;
long AFP_Count = -1;
long AFP_Stride = -1;
int AFP_NumSectors = 34;
long AFP_SectorSize1 = 0x10000;
int AFP_Sector = -1;
// this is a temporary storage variable
section ("data1") int
temp_stor;
// exit flag
bool bExit = FALSE;
main()
{
// by making AFP_Buffer as big as possible the plug-in can send and
// receive more data at a time making the data transfer quicker
//
// by allocating it on the heap the compiler does not create an
// initialized array therefore making the driver image smaller
// and faster to load
//
// we have modified the linker description file (LDF) so that the heap
// is large enough to store BUFFER_SIZE elements at this point
AFP_Buffer = (int *)malloc(BUFFER_SIZE);
// AFP_Buffer will be NULL if we could not allocate storage for the
// buffer
// setup the flash so the DSP can access it
SetupForFlash();
// command processing loop
while ( !bExit )
{
// the plug-in will set a breakpoint at "AFP_BreakReady" so it knows
// when we are ready for a new command because the DSP will halt
//
// the jump is used so that the label will be part of the debug
// information in the driver image otherwise it may be left out
// since the label is not referenced anywhere
asm("AFP_BreakReady:");
if ( FALSE )
asm("jump AFP_BreakReady;;");
// switch on the command
switch ( AFP_Command )
{
// get manufacturer and device codes
case GET_CODES:
GetCodes();
break;
// reset
case RESET:
ResetFlash();
break;
// write
case WRITE:
WriteData( AFP_Offset, AFP_Count, AFP_Stride, AFP_Buffer );
ReadToInternal(AFP_Offset, AFP_Count, AFP_Stride);
break;
// fill
case FILL:
FillData( AFP_Offset, AFP_Count, AFP_Stride, AFP_Buffer );
ReadToInternal(AFP_Offset, AFP_Count, AFP_Stride);
break;
// erase all
case ERASE_ALL:
EraseFlash();
break;
// erase sector
case ERASE_SECT:
EraseBlock( AFP_Sector );
break;
// read
case READ:
ReadData( AFP_Offset, AFP_Count, AFP_Stride, AFP_Buffer );
break;
// get sector number based on address
case GET_SECTNUM:
GetSectorNumber( AFP_Offset, &AFP_Sector );
// no command or unknown command do nothing
case NO_COMMAND:
default:
break;
}
// clear the command
AFP_Command = NO_COMMAND;
}
// free the buffer if we were able to allocate one
if ( AFP_Buffer )
free( AFP_Buffer );
// all done
return 0;
}
//////////////////////////////////////////////////////////////
// bool SetupForFlash()
//
// Perform necessary setup for the processor to talk to the
// flash such as external memory interface registers, etc.
//
//////////////////////////////////////////////////////////////
bool SetupForFlash()
{
asm("#include <defines.h>");
asm("xr0 = IMASKL;;"); // read current value
asm("xr0 = bset r0 by INTDMA0;;"); // set DMA0 interrupt mask
asm("IMASKL = xr0;;"); // set new value in IMASKL
asm("xr0 = IMASKH;;"); // read current value
asm("xr0 = bset r0 by INTGLOBAL;;"); // set global interrupts
asm("IMASKH = xr0;;"); // set new value in IMASKH
interrupt( SIGDMA0, dma_int_0 ); // set DMA interrupt vector
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool WriteData()
//
// Write a buffer to flash.
//
// Inputs: long lStart - offset in flash to start the writes at
// long lCount - number of elements to write, in this case bytes
// long lStride - number of locations to skip between writes
// int *pnData - pointer to data buffer
//
//////////////////////////////////////////////////////////////
bool WriteData( long lStart, long lCount, long lStride, int *pnData )
{
long i = 0; // loop counter
long lOffset = lStart; // current offset to write
long temp = 0;
// write the buffer up to BUFFER_SIZE items
for (i = 0; (i < lCount) && (i < BUFFER_SIZE); i++, lOffset += lStride)
{
// unlock the flash, do the write, and wait for completion
UnlockFlash( lOffset );
WriteFlash( lOffset, pnData[i] );
PollToggleBit( lOffset, pnData[i] );
}
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool FillData()
//
// Fill flash with a value.
//
// Inputs: long lStart - offset in flash to start the writes at
// long lCount - number of elements to write, in this case bytes
// long lStride - number of locations to skip between writes
// int *pnData - pointer to data buffer
//
//////////////////////////////////////////////////////////////
bool FillData( long lStart, long lCount, long lStride, int *pnData )
{
long i = 0; // loop counter
long lOffset = lStart; // current offset to write
// fill the value
for (i = 0; i < lCount; i++, lOffset += lStride)
{
// unlock the flash, do the write, and wait for completion
UnlockFlash( lOffset );
WriteFlash( lOffset, pnData[0] );
PollToggleBit( lOffset, pnData[0] );
}
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool ReadData()
//
// Read a buffer from flash.
//
// Inputs: long lStart - 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 reads
// int *pnData - pointer to data buffer to fill
//
//////////////////////////////////////////////////////////////
bool ReadData( long lStart, long lCount, long lStride, int *pnData )
{
long i = 0; // loop counter
long lOffset = lStart; // current offset to write
// read the buffer up to BUFFER_SIZE items
for (i = 0; (i < lCount) && (i < BUFFER_SIZE); i++, lOffset += lStride)
{
// do the read
ReadFlash( lOffset, &pnData[i] );
}
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool WriteFlash()
//
// Write a value to an offset in flash.
//
// Inputs: long lOffset - offset to write to
// int nValue - value to write
//
//////////////////////////////////////////////////////////////
bool WriteFlash( long lOffset, int nValue )
{
asm("[j31 + _temp_stor] = j5;;"); // put the data into _temp_stor
asm("xr0 = _temp_stor;;"); // xr0 = source index
asm("xr1 = 0x00010001;;"); // count = 1, modify = 1
asm("xr2 = 0x0;;"); // not used
asm("xr3 = 0x43000000;;"); // int mem,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
asm("xr4 = j4;;"); // xr4 = destination index
asm("xr5 = 0x00010001;;"); // count = 1, modify = 1
asm("xr6 = 0x0;;"); // not used
asm("xr7 = 0xc3000000;;"); // boot rom,prio=norm,2D=no,word=norm,int=yes,RQ=dsbl,chain=no
do_dma(); // do dma transfer
// ok
return TRUE;
}
//////////////////////////////////////////////////////////////
// bool ReadFlash()
//
// Read a value from an offset in flash.
//
// Inputs: long lOffset - offset to read from
// int pnValue - pointer to store value read from flash
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -