📄 flashmenu.c
字号:
//
// 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.
//
//------------------------------------------------------------------------------
//
// File: menu.c
//
#include <eboot.h>
//------------------------------------------------------------------------------
//
// Define: dimof
//
#ifdef dimof
#undef dimof
#endif
#define dimof(x) (sizeof(x)/sizeof(x[0]))
//------------------------------------------------------------------------------
static VOID ShowFlashGeometry(OAL_BLMENU_ITEM *pMenu);
static VOID EraseFlash(OAL_BLMENU_ITEM *pMenu);
static VOID EraseFlashBlock(OAL_BLMENU_ITEM *pMenu);
static VOID DumpFlash(OAL_BLMENU_ITEM *pMenu);
static UINT32 OALStringToUINT32(LPCWSTR psz);
//------------------------------------------------------------------------------
OAL_BLMENU_ITEM g_menuFlash[] = {
{
L'1', L"Show flash geometry", ShowFlashGeometry,
NULL, NULL, NULL
}, {
L'2', L"Erase flash", EraseFlash,
NULL, NULL, NULL
}, {
L'3', L"Dump flash sector", DumpFlash,
NULL, NULL, NULL
}, {
L'4', L"Erase flash block", EraseFlashBlock,
NULL, NULL, NULL
}, {
L'5', L"Clean registry", OALBLMenuEnable,
L"clean registry", &g_bootCfg.cleanhive, NULL
}, {
L'0', L"Exit and Continue", NULL,
NULL, NULL, NULL
}, {
0, NULL, NULL,
NULL, NULL, NULL
}
};
//------------------------------------------------------------------------------
VOID ShowFlashGeometry(OAL_BLMENU_ITEM *pMenu)
{
HANDLE hFMD;
FlashInfo flashInfo;
LPCWSTR pszType;
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);
if (g_bootCfg.cleanhive)
OALLog(L" Clean hive: Enabled\r\n");
else
OALLog(L" Clean hive: Disabled\r\n");
cleanUp:
if (hFMD != NULL) FMD_Deinit(hFMD);
return;
}
//------------------------------------------------------------------------------
VOID EraseFlash(OAL_BLMENU_ITEM *pMenu)
{
WCHAR key;
HANDLE hFMD = NULL;
FlashInfo flashInfo;
BLOCK_ID block;
UINT32 status;
OALLog(L" Do you want 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;
// 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) {
block++;
continue;
}
// Skip bad blocks
if ((status & BLOCK_STATUS_BAD) != 0) {
OALLog(L" Skip bad block %d\r\n", block);
block++;
continue;
}
// Erase block
if (!FMD_EraseBlock(block)) {
OALLog(L" Opps, can't erase block %d - set it as bad\r\n", block);
FMD_SetBlockStatus(block, BLOCK_STATUS_BAD);
}
block++;
}
OALLog(L" Done\r\n");
cleanUp:
if (hFMD != NULL) FMD_Deinit(hFMD);
return;
}
//------------------------------------------------------------------------------
VOID EraseFlashBlock(OAL_BLMENU_ITEM *pMenu)
{
WCHAR key;
HANDLE hFMD = NULL;
FlashInfo flashInfo;
WCHAR szInputLine[16];
BLOCK_ID block;
UINT32 status;
OALLog(L" Do you want erase a flash block [-/y]? ");
// Get key
key = OALBLMenuReadKey(TRUE);
OALLog(L"%c\r\n", key);
// Depending on result
if (key != L'y' && key != L'Y') goto cleanUp;
// 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;
}
while (TRUE) {
OALLog(L"\r\n Block Number to Erase: ");
if (OALBLMenuReadLine(szInputLine, dimof(szInputLine)) == 0) break;
// Get sector number
block = OALStringToUINT32(szInputLine);
// Check block number
if (block >= flashInfo.dwNumBlocks) {
OALLog(L" Oops, too big block number\r\n");
continue;
}
// Get block status
status = FMD_GetBlockStatus(block);
// Don't erase bad blocks
if ((status & BLOCK_STATUS_BAD) != 0) {
OALLog(L" Opps, can't erase block %d - it is set as bad\r\n", block);
continue;
}
// Erase block
if (!FMD_EraseBlock(block)) {
OALLog(L" Opps, can't erase block %d - set it as bad\r\n", block);
FMD_SetBlockStatus(block, BLOCK_STATUS_BAD);
}
else
{
OALLog(L" Block Erased!\r\n");
}
}
cleanUp:
if (hFMD != NULL) FMD_Deinit(hFMD);
return;
}
//------------------------------------------------------------------------------
VOID DumpFlash(OAL_BLMENU_ITEM *pMenu)
{
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) {
OALLog(L"\r\n Sector Number: ");
if (OALBLMenuReadLine(szInputLine, dimof(szInputLine)) == 0) break;
// Get sector number
sector = OALStringToUINT32(szInputLine);
// Check sector number
if (sector > flashInfo.dwNumBlocks * flashInfo.wSectorsPerBlock) {
OALLog(L" Oops, too big sector number\r\n");
continue;
}
if (!FMD_ReadSector(sector, buffer, §orInfo, 1)) {
OALLog(L" Oops, sector read failed\r\n");
continue;
}
OALLog(
L"\r\nSector %d (sector %d in block %d)\r\n", sector,
sector%flashInfo.wSectorsPerBlock, sector/flashInfo.wSectorsPerBlock
);
OALLog(
L"Reserved1: %08x OEMReserved: %02x Bad: %02x Reserved2: %04x\r\n",
sectorInfo.dwReserved1, sectorInfo.bOEMReserved,
sectorInfo.bBadBlock, sectorInfo.wReserved2
);
for (i = 0; i < flashInfo.wDataBytesPerSector; i += 16) {
OALLog(L"%04x ", i);
for (j = i; j < i + 16 && j < flashInfo.wDataBytesPerSector; j++) {
OALLog(L" %02x", buffer[j]);
}
OALLog(L" ");
for (j = i; j < i + 16 && j < flashInfo.wDataBytesPerSector; j++) {
if (buffer[j] >= ' ' && buffer[j] < 127) {
OALLog(L"%c", buffer[j]);
} else {
OALLog(L".");
}
}
OALLog(L"\r\n");
}
}
cleanUp:
if (hFMD != NULL) FMD_Deinit(hFMD);
return;
}
//------------------------------------------------------------------------------
UINT32 OALStringToUINT32(LPCWSTR psz)
{
UINT32 i = 0;
// Replace the dots with NULL terminators
while (psz != NULL && *psz != L'\0') {
if (*psz < L'0' || *psz > L'9') break;
i = i * 10 + (*psz - L'0');
psz++;
}
return i;
}
//------------------------------------------------------------------------------
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -