Add safety checks for loaded FIRM modules
This commit is contained in:
parent
a0531b7930
commit
62f7a06192
@ -38,23 +38,31 @@ bool loadSplash(void)
|
||||
*bottomSplashFile = "splashbottom.bin";
|
||||
|
||||
bool isTopSplashValid = getFileSize(topSplashFile) == SCREEN_TOP_FBSIZE,
|
||||
isBottomSplashValid = getFileSize(bottomSplashFile) == SCREEN_BOTTOM_FBSIZE;
|
||||
isBottomSplashValid = getFileSize(bottomSplashFile) == SCREEN_BOTTOM_FBSIZE,
|
||||
ret;
|
||||
|
||||
//Don't delay boot nor init the screens if no splash images or invalid splash images are on the SD
|
||||
if(!isTopSplashValid && !isBottomSplashValid)
|
||||
return false;
|
||||
|
||||
if(!isTopSplashValid && !isBottomSplashValid) ret = false;
|
||||
else
|
||||
{
|
||||
initScreens();
|
||||
clearScreens(true, true, true);
|
||||
|
||||
if(isTopSplashValid) fileRead(fbs[1].top_left, topSplashFile, SCREEN_TOP_FBSIZE);
|
||||
if(isBottomSplashValid) fileRead(fbs[1].bottom, bottomSplashFile, SCREEN_BOTTOM_FBSIZE);
|
||||
if(isTopSplashValid) isTopSplashValid = fileRead(fbs[1].top_left, topSplashFile, SCREEN_TOP_FBSIZE) == SCREEN_TOP_FBSIZE;
|
||||
if(isBottomSplashValid) isBottomSplashValid = fileRead(fbs[1].bottom, bottomSplashFile, SCREEN_BOTTOM_FBSIZE) == SCREEN_BOTTOM_FBSIZE;
|
||||
|
||||
if(!isTopSplashValid && !isBottomSplashValid) ret = false;
|
||||
else
|
||||
{
|
||||
swapFramebuffers(true);
|
||||
|
||||
chrono(3);
|
||||
|
||||
return true;
|
||||
ret = true;
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void drawCharacter(char character, bool isTopScreen, u32 posX, u32 posY, u32 color)
|
||||
|
@ -285,18 +285,20 @@ u32 patch1x2xNativeAndSafeFirm(u32 devMode)
|
||||
|
||||
static inline void copySection0AndInjectSystemModules(FirmwareType firmType, bool loadFromStorage)
|
||||
{
|
||||
u32 srcModuleSize,
|
||||
u32 maxModuleSize = firmType == NATIVE_FIRM ? 0x80000 : 0x600000,
|
||||
srcModuleSize,
|
||||
dstModuleSize;
|
||||
|
||||
for(u8 *src = (u8 *)firm + firm->section[0].offset, *srcEnd = src + firm->section[0].size, *dst = firm->section[0].address;
|
||||
src < srcEnd; src += srcModuleSize, dst += dstModuleSize)
|
||||
src < srcEnd; src += srcModuleSize, dst += dstModuleSize, maxModuleSize -= dstModuleSize)
|
||||
{
|
||||
srcModuleSize = ((Cxi *)src)->ncch.contentSize * 0x200;
|
||||
const char *moduleName = ((Cxi *)src)->exHeader.systemControlInfo.appTitle;
|
||||
|
||||
u32 fileSize;
|
||||
bool loadedModule;
|
||||
|
||||
if(loadFromStorage)
|
||||
if(!loadFromStorage) loadedModule = false;
|
||||
else
|
||||
{
|
||||
char fileName[24] = "sysmodules/";
|
||||
const char *ext = ".cxi";
|
||||
@ -305,12 +307,23 @@ static inline void copySection0AndInjectSystemModules(FirmwareType firmType, boo
|
||||
concatenateStrings(fileName, moduleName);
|
||||
concatenateStrings(fileName, ext);
|
||||
|
||||
fileSize = fileRead(dst, fileName, 2 * srcModuleSize);
|
||||
}
|
||||
else fileSize = 0;
|
||||
dstModuleSize = getFileSize(fileName);
|
||||
|
||||
if(fileSize > 0) dstModuleSize = fileSize;
|
||||
if(dstModuleSize == 0) loadedModule = false;
|
||||
else
|
||||
{
|
||||
if(dstModuleSize <= sizeof(Cxi) + 0x200 ||
|
||||
dstModuleSize > maxModuleSize ||
|
||||
fileRead(dst, fileName, dstModuleSize) != dstModuleSize ||
|
||||
memcmp(((Cxi *)dst)->ncch.magic, "NCCH", 4) != 0 ||
|
||||
memcmp(moduleName, ((Cxi *)dst)->exHeader.systemControlInfo.appTitle, sizeof(((Cxi *)dst)->exHeader.systemControlInfo.appTitle)) != 0)
|
||||
error("An external FIRM module is invalid.");
|
||||
|
||||
loadedModule = true;
|
||||
}
|
||||
}
|
||||
|
||||
if(!loadedModule)
|
||||
{
|
||||
const u8 *module;
|
||||
|
||||
@ -325,6 +338,8 @@ static inline void copySection0AndInjectSystemModules(FirmwareType firmType, boo
|
||||
dstModuleSize = srcModuleSize;
|
||||
}
|
||||
|
||||
if(dstModuleSize > maxModuleSize) error("The FIRM modules section is full.");
|
||||
|
||||
memcpy(dst, module, dstModuleSize);
|
||||
}
|
||||
}
|
||||
|
@ -139,10 +139,13 @@ bool verifyPin(u32 pinMode)
|
||||
if(messageSize > 0 && messageSize <= 800)
|
||||
{
|
||||
char message[messageSize + 1];
|
||||
fileRead(message, messageFile, messageSize);
|
||||
|
||||
if(fileRead(message, messageFile, messageSize) == messageSize)
|
||||
{
|
||||
message[messageSize] = 0;
|
||||
drawString(message, false, 10, 10, COLOR_WHITE);
|
||||
}
|
||||
}
|
||||
|
||||
while(!unlock)
|
||||
{
|
||||
|
Reference in New Issue
Block a user