flashmenu.c
来自「mx27 f14v2 源代码。包括ADS板上诸多驱动的源码。」· C语言 代码 · 共 1,008 行 · 第 1/2 页
C
1,008 行
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
//
// Use of this sample source code is subject to the terms of the Microsoft
// license agreement under which you licensed this sample source code. If
// you did not accept the terms of the license agreement, you are not
// authorized to use this sample source code. For the terms of the license,
// please see the license agreement between you and Microsoft or, if applicable,
// see the LICENSE.RTF on your install media or the root of your tools installation.
// THE SAMPLE SOURCE CODE IS PROVIDED "AS IS", WITH NO WARRANTIES OR INDEMNITIES.
//
//------------------------------------------------------------------------------
//
// File: menu.c
//
#include <windows.h>
#include <blcommon.h>
#include "loader.h"
#include <fmd.h>
#include "bsp.h"
//------------------------------------------------------------------------------
//
// Define: dimof
//
#ifdef dimof
#undef dimof
#endif
#define dimof(x) (sizeof(x)/sizeof(x[0]))
//------------------------------------------------------------------------------
static VOID ShowFlashGeometry(void);
static VOID EraseFlash(void);
static VOID MenuEraseBlock(void);
static VOID SetBadBlock(void);
static VOID DumpFlash(void);
static UINT32 OALStringToUINT32(LPCWSTR psz);
static VOID ReservedBlocks(void);
static VOID DumpBlocks(void);
static BOOL ReservedSpareArea(BLOCK_ID start, int NoOfBlocks);
WCHAR OALBLMenuReadKey(BOOL wait)
{
CHAR key;
while ((key = OEMReadDebugByte()) == OEM_DEBUG_READ_NODATA && wait);
if (key == OEM_DEBUG_READ_NODATA) key = 0;
return (WCHAR)key;
}
UINT32 OALBLMenuReadLine(LPWSTR szBuffer, size_t CharCount)
{
UINT32 count;
WCHAR key;
count = 0;
while (count < CharCount) {
key = OALBLMenuReadKey(TRUE);
if (key == L'\r' || key == L'\n') {
OALLog(L"\r\n");
break;
} if (key == L'\b' && count > 0) {
OALLog(L"\b \b");
count--;
} else if (key >= L' ' && key < 128 && count < (CharCount - 1)) {
szBuffer[count++] = key;
OALLog(L"%c", key);
}
}
szBuffer[count] = '\0';
return count;
}
//------------------------------------------------------------------------------
VOID NANDTest(void)
{
UINT16 InChar = 0;
BOOL fExit = FALSE;
while (!fExit) {
KITLOutputDebugString ( "\r\nNAND : \r\n");
KITLOutputDebugString ( "(0) Show flash geometry \r\n");
KITLOutputDebugString ( "(1) Dump flash sector \r\n");
KITLOutputDebugString ( "(2) Erase flash \r\n");
KITLOutputDebugString ( "(3) Erase block range \r\n");
KITLOutputDebugString ( "(4) Set bad blocks \r\n");
KITLOutputDebugString ( "(5) Set reserved blocks \r\n");
KITLOutputDebugString ( "(6) Dump block ranges \r\n");
KITLOutputDebugString ( "(Q) Quit \r\n");
{
InChar = OALBLMenuReadKey(TRUE);
switch (InChar) {
case L'0':
ShowFlashGeometry();
break;
case L'1':
DumpFlash();
break;
case L'2':
EraseFlash();
break;
case L'3':
MenuEraseBlock();
break;
case L'4':
SetBadBlock();
break;
case L'5':
ReservedBlocks();
break;
case L'6':
DumpBlocks();
break;
case L'Q':
case L'q':
fExit = TRUE;
break;
default:
break;
}
}
}
return;
}
//------------------------------------------------------------------------------
VOID
ShowFlashGeometry(void)
{
HANDLE hFMD;
FlashInfo flashInfo;
LPCWSTR pszType;
BLOCK_ID block;
UINT32 status;
UINT32 listmode=0;
hFMD = FMD_Init(NULL, NULL, NULL);
if (hFMD == NULL)
{
OALLog(L" Oops, can't open FMD driver\r\n");
goto cleanUp;
}
if (!FMD_GetInfo(&flashInfo))
{
OALLog(L" Oops, can't get flash geometry info\r\n");
goto cleanUp;
}
switch (flashInfo.flashType)
{
case NAND:
pszType = L"NAND";
break;
case NOR:
pszType = L"NOR";
break;
default:
pszType = L"Unknown";
}
OALLog(L"\r\n");
OALLog(L" Flash Type: %s\r\n", pszType);
OALLog(L" Blocks: %d\r\n", flashInfo.dwNumBlocks);
OALLog(L" Bytes/block: %d\r\n", flashInfo.dwBytesPerBlock);
OALLog(L" Sectors/block: %d\r\n", flashInfo.wSectorsPerBlock);
OALLog(L" Bytes/sector: %d\r\n", flashInfo.wDataBytesPerSector);
// now list bad/reserved sectors
OALLog(L"\r\nScanning flash ... \r\n");
// First offset given
block = 0;
while (block < flashInfo.dwNumBlocks)
{
#if 0
if (!(block & 0x3F))
{
OALLog(L".");
}
#endif
// If block is bad, we have to offset it
status = FMD_GetBlockStatus(block);
// bad block
if ((status & BLOCK_STATUS_BAD) != 0)
{
if (listmode!=1)
{
OALLog(L"\r\n[bad] ");
listmode=1;
}
OALLog(L" %d", block);
block++;
continue;
}
// reserved block
if ((status & BLOCK_STATUS_RESERVED) != 0)
{
if (listmode!=2)
{
OALLog(L"\r\n[reserved]");
listmode=2;
}
OALLog(L" %d", block);
block++;
continue;
}
block++;
}
OALLog(L" Done\r\n");
cleanUp:
if (hFMD != NULL)
{
FMD_Deinit(hFMD);
}
return;
}
//------------------------------------------------------------------------------
VOID EraseFlash(void)
{
WCHAR key;
HANDLE hFMD = NULL;
FlashInfo flashInfo;
BLOCK_ID block;
UINT32 status;
BOOL fEraseReserved = FALSE;
BOOL fEraseBadBlock = FALSE;
BOOL fEraseFailCont = FALSE;
OALLog(L" Do you want to erase unreserved blocks [-/y]? ");
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key != L'y' && key != L'Y') goto cleanUp;
OALLog(L" Erase reserved block [-/y]? ");
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key == L'y' || key == L'Y')
fEraseReserved = TRUE;
OALLog(L" Try to erase bad blocks [-/y]? ");
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key == L'y' || key == L'Y')
fEraseBadBlock = TRUE;
OALLog(L" Erase Continue on failed [-/y]? ");
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key == L'y' || key == L'Y')
fEraseFailCont = TRUE;
// Open FMD
hFMD = FMD_Init(NULL, NULL, NULL);
if (hFMD == NULL)
{
OALLog(L" Oops, can't open FMD driver\r\n");
goto cleanUp;
}
if (!FMD_GetInfo(&flashInfo))
{
OALLog(L" Oops, can't get flash geometry info\r\n");
goto cleanUp;
}
// First offset given
block = 0;
while (block < flashInfo.dwNumBlocks)
{
// If block is bad, we have to offset it
status = FMD_GetBlockStatus(block);
// Skip reserved blocks
if (((status & BLOCK_STATUS_RESERVED) != 0) && (!fEraseReserved))
{
OALLog(L" Skip reserved block %d\r\n", block);
block++;
continue;
}
// Skip bad blocks
if (((status & BLOCK_STATUS_BAD) != 0) && (!fEraseBadBlock))
{
OALLog(L" Skip bad block %d\r\n", block);
block++;
continue;
}
// Erase block
if (!FMD_EraseBlock(block) && !fEraseFailCont)
{
OALLog(L" Oops, can't erase block %d\r\n", block);
break;
}
block++;
OALLog(L".");
}
OALLog(L"\r\nDone\r\n");
cleanUp:
if (hFMD != NULL) FMD_Deinit(hFMD);
return;
}
//------------------------------------------------------------------------------
VOID MenuEraseBlock(void)
{
WCHAR key;
HANDLE hFMD = NULL;
FlashInfo flashInfo;
BLOCK_ID firstblock, lastblock=0;
WCHAR szInputLine[16];
UINT32 status;
OALLog(L"\r\n First Block Number: ");
if (OALBLMenuReadLine(szInputLine, dimof(szInputLine)) == 0)
{
goto cleanUp;
}
// Get block number
firstblock = OALStringToUINT32(szInputLine);
OALLog(L"\r\n Last Block Number: ");
if (OALBLMenuReadLine(szInputLine, dimof(szInputLine)) != 0)
{
// Get block number
lastblock = OALStringToUINT32(szInputLine);
}
if (lastblock < firstblock)
{
lastblock=firstblock;
}
// Open FMD
hFMD = FMD_Init(NULL, NULL, NULL);
if (hFMD == NULL)
{
OALLog(L" Oops, can't open FMD driver\r\n");
goto cleanUp;
}
if (!FMD_GetInfo(&flashInfo))
{
OALLog(L" Oops, can't get flash geometry info\r\n");
goto cleanUp;
}
if (lastblock >= flashInfo.dwNumBlocks)
{
OALLog(L" Oops, too big block number\r\n");
goto cleanUp;
}
OALLog(L" Do you want erase block %d-%d [-/y]? ", firstblock, lastblock);
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key != L'y' && key != L'Y')
{
goto cleanUp;
}
while (firstblock<=lastblock)
{
// If block is bad, we have to offset it
status = FMD_GetBlockStatus(firstblock);
// ask before erasing reserved blocks
if ((status & BLOCK_STATUS_RESERVED) != 0)
{
OALLog(L" Do you want to erase reserved block %d [-/y]? ", firstblock);
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key != L'y' && key != L'Y')
{
firstblock++;
continue;
}
}
// ask before erasing bad blocks
if ((status & BLOCK_STATUS_BAD) != 0)
{
OALLog(L" Do you want to erase bad block %d [-/y]? ", firstblock);
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key != L'y' && key != L'Y')
{
firstblock++;
continue;
}
}
// Erase block
if (!FMD_EraseBlock(firstblock))
{
OALLog(L" Oops, can't erase block %d - mark as bad\r\n", firstblock);
FMD_SetBlockStatus(firstblock, BLOCK_STATUS_BAD);
}
firstblock++;
OALLog(L".");
}
OALLog(L" Done\r\n");
cleanUp:
if (hFMD != NULL) FMD_Deinit(hFMD);
return;
}
//------------------------------------------------------------------------------
VOID DumpFlash(void)
{
HANDLE hFMD = NULL;
FlashInfo flashInfo;
SectorInfo sectorInfo;
SECTOR_ADDR sector;
WCHAR szInputLine[16];
UINT8 buffer[512];
UINT32 i, j;
// Open FMD
hFMD = FMD_Init(NULL, NULL, NULL);
if (hFMD == NULL)
{
OALLog(L" Oops, can't open FMD driver\r\n");
goto cleanUp;
}
if (!FMD_GetInfo(&flashInfo))
{
OALLog(L" Oops, can't get flash geometry info\r\n");
goto cleanUp;
}
if (flashInfo.wDataBytesPerSector > sizeof(buffer))
{
OALLog(L" Oops, sector size larger than my buffer\r\n");
goto cleanUp;
}
while (TRUE)
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?