📄 flash_amd.c
字号:
/************************************************************************
*
* FLASH_AMD_set_fileflash_read
* Description :
* -------------
* Set file flash device in read mode.
*
*
* Parameters :
* ------------
*
* -
*
*
* Return values :
* ---------------
*
* 'OK' = 0x00: File FLASH set to read mode
* ERROR_FLASH_PROGRAM_ERROR Flash device failure
*
*
************************************************************************/
static
INT32 FLASH_AMD_set_fileflash_read( void )
{
int rcode ;
UINT32 bank ;
volatile UINT32 *pw ;
pw = (UINT32*) KSEG1(fileflash_phys_start) ;
/* The first reset will take us out of any command modes */
REG32(pw) = 0x00f000f0;
/* The second reset will reset all banks in flash to read mode */
REG32(pw) = 0x00f000f0;
return( OK ) ;
}
/************************************************************************
*
* FLASH_AMD_set_monitorflash_read
* Description :
* -------------
* Set monitor flash device in read mode.
*
*
* Parameters :
* ------------
*
* -
*
*
* Return values :
* ---------------
*
* 'OK' = 0x00: File FLASH set to read mode
* ERROR_FLASH_PROGRAM_ERROR Flash device failure
*
*
************************************************************************/
static
INT32 FLASH_AMD_set_monitorflash_read( void )
{
int rcode ;
UINT32 bank ;
volatile UINT32 *pw ;
pw = (UINT32*) KSEG1(monitorflash_phys_start) ;
/* The first reset will take us out of any command modes */
*pw = 0x00f000f0;
/* The second reset will reset all banks in flash to read mode */
*pw = 0x00f000f0;
return( OK ) ;
}
//
// erase_AMD_flash
//
INT32 erase_AMD_flash(UINT32 startaddr, UINT32 endaddr)
{
int rcode = ERROR_FLASH_INVALID_ADDRESS;
#ifndef FLASH_16BIT
volatile long *fptr = (volatile long *)KSEG1(startaddr);
#define FL_CMD(c) ((c) | ((c) << 16))
#else
volatile short *fptr = (volatile short *)KSEG1(startaddr);
#define FL_CMD(c) (c)
#endif
endaddr = KSEG1(endaddr);
startaddr = KSEG1(startaddr);
// printf(" AMD Flash: erasing from %08x to %08x\n",startaddr,endaddr);
while( (UINT32)fptr < endaddr )
{
fptr[0x555] = FL_CMD(0xaa);
fptr[0x2AA] = FL_CMD(0x55);
fptr[0x555] = FL_CMD(0x80);
fptr[0x555] = FL_CMD(0xaa);
fptr[0x2AA] = FL_CMD(0x55);
fptr[0] = FL_CMD(0x30);
/* await completion */
rcode = FLASH_AMD_wait_ready( (void *)fptr, ERASE_DATA);
if (rcode != OK)
{
printf("erase error.\n");
break ;
}
/* next block */
(long)fptr += systemflash_block_size;
}
return rcode;
}
/************************************************************************
*
* FLASH_AMD_erase_systemflash
* Description :
* -------------
* Erase complete system flash.
*
*
* Parameters :
* ------------
*
* -
*
* Return values :
* ---------------
*
* 'OK' = 0x00: System FLASH erased succesfully
* ERROR_FLASH_PROGRAM_ERROR Flash device failure
*
*
************************************************************************/
static
INT32 FLASH_AMD_erase_systemflash( void )
{
return erase_AMD_flash(systemflash_phys_start, systemflash_phys_end);
}
/************************************************************************
*
* FLASH_AMD_erase_fileflash
* Description :
* -------------
* Erase file flash, which is the last block (in each FLASH device)
* of the monitor flash.
*
*
* Parameters :
* ------------
*
* -
*
* Return values :
* ---------------
*
* 'OK' = 0x00: File FLASH erased succesfully
* ERROR_FLASH_PROGRAM_ERROR Flash device failure
*
*
************************************************************************/
static
INT32 FLASH_AMD_erase_fileflash( void )
{
return erase_AMD_flash(fileflash_phys_start, fileflash_phys_end);
}
/************************************************************************
*
* FLASH_AMD_erase_flasharea
* Description :
* -------------
* Erase flash area; i.e. the driver erases the flash blocks inside
* the specified memory area.
*
*
* Parameters :
* ------------
*
* 'p_param', IN, variable of type, t_FLASH_ctrl_descriptor.
*
*
* Return values :
* ---------------
*
* 'OK' = 0x00: FLASH erased succesfully
* ERROR_FLASH_PROGRAM_ERROR Flash device failure
* ERROR_FLASH_INVALID_ADDRESS Address area not inside FLASH
* devices
*
*
************************************************************************/
static
INT32 FLASH_AMD_erase_flasharea( t_FLASH_ctrl_descriptor *p_param )
{
int rcode = OK ;
long startaddr, endaddr;
/* calculate committed FLASH area */
startaddr = KSEG1(p_param->user_physadr);
endaddr = KSEG1(p_param->user_physadr) + p_param->user_length - 1;
return erase_AMD_flash(startaddr,endaddr);
}
/************************************************************************
*
* FLASH_AMD_inquire_flasharea
* Description :
* -------------
* Inquire flash area; i.e. the driver calculates the effective flash
* block area covering the specified memory area.
*
*
* Parameters :
* ------------
*
* 'p_param', IN, variable of type, t_FLASH_ctrl_descriptor.
*
*
* Return values :
* ---------------
*
* 'OK' = 0x00: Area specified inside valid
* FLASH device area
* ERROR_FLASH_INVALID_ADDRESS Address area not inside FLASH
* devices
*
*
************************************************************************/
static
INT32 FLASH_AMD_inquire_flasharea( t_FLASH_ctrl_descriptor *p_param )
{
UINT32 blocksize, start, end ;
// printf(" FLASH_AMD_inquire_flasharea: %x, %x\n", p_param->user_physadr, p_param->user_length ) ;
switch (FLASH_AMD_devicetype(p_param->user_physadr))
{
case FLASH_SYSTEMFLASH_DEVICE:
/* system FLASH */
/* validate upper boundary */
if ( FLASH_AMD_devicetype( p_param->user_physadr +
p_param->user_length - 1 )
!= FLASH_SYSTEMFLASH_DEVICE )
{
return( ERROR_FLASH_INVALID_ADDRESS ) ;
}
blocksize = systemflash_block_size ;
break ;
case FLASH_FILEFLASH_DEVICE:
/* Reject programming of FILE FLASH */
memset( flash_diag_msg, 0, sizeof(flash_diag_msg) ) ;
sprintf( flash_diag_msg, "Environment FLASH: map = (0x%08x,0x%08x), user = 0x%08x",
(UINT32) fileflash_phys_start,
(UINT32) fileflash_phys_end,
(UINT32) PHYS(p_param->user_physadr) ) ;
return( ERROR_FLASH_FILE_FLASH_PROT ) ;
break ;
case FLASH_MONITORFLASH_DEVICE:
/* Monitor FLASH */
/* validate upper boundary */
if ( FLASH_AMD_devicetype( p_param->user_physadr +
p_param->user_length - 1 )
!= FLASH_MONITORFLASH_DEVICE )
{
return( ERROR_FLASH_INVALID_ADDRESS ) ;
}
blocksize = monitorflash_block_size ;
break ;
case FLASH_BOOT_DEVICE:
/* Boot device */
memset( flash_diag_msg, 0, sizeof(flash_diag_msg) ) ;
sprintf( flash_diag_msg, "MIPS boot media: map = (0x%08x,0x%08x), user = 0x%08x",
(UINT32) boot_phys_start,
(UINT32) boot_phys_end,
(UINT32) PHYS(p_param->user_physadr) ) ;
return( ERROR_FLASH_BOOT_WRITE_PROTECTED ) ;
break ;
default:
return( ERROR_FLASH_INVALID_ADDRESS ) ;
break ;
}
/* calculate committed FLASH area */
start = (KSEG1(p_param->user_physadr)/blocksize) * blocksize ;
end = ((((KSEG1(p_param->user_physadr) +
p_param->user_length)/blocksize)) * blocksize) - 1 ;
if ( ((KSEG1(p_param->user_physadr)+p_param->user_length) % blocksize) != 0)
{
end = end + blocksize ;
}
/* return committed area to user */
p_param->driver_physadr = PHYS(start) ;
p_param->driver_length = (end - start) + 1 ;
return( OK ) ;
}
/************************************************************************
*
* FLASH_AMD_test_systemflash
* Description :
* -------------
* Test complete file flash (just one block)
*
*
* Parameters :
* ------------
*
* -
*
* Return values :
* ---------------
*
* 'OK' = 0x00: System FLASH OK
* ERROR_FLASH_LOCKED Some sector(s) locked
* ERROR_FLASH_ERASE_ERROR Some sector(s) have erase error
*
*
************************************************************************/
static
INT32 FLASH_AMD_test_systemflash( void )
{
int rcode = OK ;
UINT32 block, bank ;
volatile UINT32 *pw ;
return OK; // *** kludge ***
pw = (UINT32 *) 0xbf800000;
/* issue 'QUERY' command */
REG32(pw + 0x55) = 0x00980098;
#ifdef FLASH_DEBUG
sprintf( msg, "\n\r FLASH_AMD_test_systemflash: Adr= 0x%08x, Sta= 0x%08x\n\r",
(UINT32)pw, REG32( ((UINT32)pw+FLASH_BLOCKSTATUS_OFS) ) ) ;
PUTS( DEFAULT_PORT, msg ) ;
#endif
/* Verify 'Q' char of the Query-unique ASCII string, part of CFI spec. */
if ( REG32(pw + 0x10) != FLASH_QUERYQCHAR )
{
memset( flash_diag_msg, 0, sizeof(flash_diag_msg) ) ;
sprintf( flash_diag_msg, "Adr= %08x, (Adr)= %08x",(UINT32)pw+FLASH_QUERYQCHAR_OFS,
REG32(((UINT32)pw+FLASH_QUERYQCHAR_OFS)) ) ;
rcode = ERROR_FLASH_QRY_NOT_FOUND ;
}
/* Verify 'R' char of the Query-unique ASCII string, part of CFI spec. */
if ( REG32(pw + 0x11) != FLASH_QUERYRCHAR )
{
memset( flash_diag_msg, 0, sizeof(flash_diag_msg) ) ;
sprintf( flash_diag_msg, "Adr= %08x, (Adr)= %08x",(UINT32)pw+FLASH_QUERYRCHAR_OFS,
REG32(((UINT32)pw+FLASH_QUERYRCHAR_OFS)) ) ;
rcode = ERROR_FLASH_QRY_NOT_FOUND ;
}
/* Verify 'Y' char of the Query-unique ASCII string, part of CFI spec. */
if ( REG32(pw + 0x12) != FLASH_QUERYYCHAR )
{
memset( flash_diag_msg, 0, sizeof(flash_diag_msg) ) ;
sprintf( flash_diag_msg, "Adr= %08x, (Adr)= %08x",(UINT32)pw+FLASH_QUERYYCHAR_OFS,
REG32(((UINT32)pw+FLASH_QUERYYCHAR_OFS)) ) ;
rcode = ERROR_FLASH_QRY_NOT_FOUND ;
}
/* Issue Reset Command to return to read mode */
REG32(pw) = 0x00f000f0;
return( rcode ) ;
}
/************************************************************************
*
* FLASH_AMD_test_fileflash
* Description :
* -------------
* Test complete file flash.
*
*
* Parameters :
* ------------
*
* -
*
* Return values :
* ---------------
*
* 'OK' = 0x00: System FLASH OK
* ERROR_FLASH_LOCKED Some sector(s) locked
* ERROR_FLASH_ERASE_ERROR Some sector(s) have erase error
*
*
************************************************************************/
static
INT32 FLASH_AMD_test_fileflash( void )
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -