mirror of
https://github.com/CloverHackyColor/CloverBootloader.git
synced 2024-11-23 11:35:19 +01:00
Prevent "log loop" a better way.
Do not depend on Self instance for opening log file. Rework on Self to share code with BootLog.cpp.
This commit is contained in:
parent
36e63bd7f0
commit
c0fa72e2ed
@ -1 +1 @@
|
||||
Subproject commit 9ecf06dc98cdc6169991d4033417bd3ff0da0355
|
||||
Subproject commit 704c042bdb9be1e14d207276403127b7b46f4007
|
@ -15,12 +15,6 @@
|
||||
#include "../Settings/Self.h"
|
||||
#include "../Platform/guid.h"
|
||||
|
||||
//Slice - if I set NEW_LOG to 0 then I will work with debug.log as in 5103
|
||||
// but it is not working somehow.
|
||||
// my purpose is to make debug.log open and close every second to see crashes.
|
||||
// currently it is not happen. debug.log is not created at crash.
|
||||
#define NEW_LOG 1
|
||||
|
||||
#ifndef DEBUG_ALL
|
||||
#define DEBUG_BOOTLOG 0
|
||||
#else
|
||||
@ -82,6 +76,8 @@ static XStringW debugLogFileName;
|
||||
static EFI_FILE_PROTOCOL* gLogFile = NULL;
|
||||
// Do not keep a pointer to MemLogBuffer. Because a reallocation, it could become invalid.
|
||||
|
||||
int g_OpeningLogFile = 0;
|
||||
|
||||
|
||||
// Avoid debug looping. TO be able to call DBG from inside function that DBG calls, we need to suspend callback to avoid a loop.
|
||||
// Just instanciante this, the destructor will restore the callback.
|
||||
@ -99,7 +95,6 @@ public:
|
||||
#if DEBUG_BOOTLOG == 0
|
||||
#define DGB_nbCallback(...)
|
||||
#else
|
||||
//Slice - it crashes at legacy boot
|
||||
#define DGB_nbCallback(...) do { SuspendMemLogCallback smc; DBG(__VA_ARGS__); } while (0)
|
||||
#endif
|
||||
|
||||
@ -116,7 +111,13 @@ void closeDebugLog()
|
||||
//DGB_nbCallback("closeDebugLog() -> %s\n", efiStrError(Status));
|
||||
}
|
||||
|
||||
#if NEW_LOG
|
||||
/*
|
||||
* Use (or not) self.getCloverDir() to open log file.
|
||||
* Not using self has the advantage of being able to generate a log even after uninitreflib().
|
||||
* The only thing needed is gImageHandle. But because it's a parameter to main entry point, value can't be wrong.
|
||||
* Drawback is that code to find current working directory has to be duplicated.
|
||||
*/
|
||||
//#define USE_SELF_INSTANCE
|
||||
static UINTN GetDebugLogFile()
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
@ -124,21 +125,11 @@ static UINTN GetDebugLogFile()
|
||||
|
||||
if ( gLogFile ) return 0;
|
||||
|
||||
// // get RootDir from device we are loaded from
|
||||
// Status = gBS->HandleProtocol(gImageHandle, &gEfiLoadedImageProtocolGuid, (VOID **) &LoadedImage);
|
||||
// if (EFI_ERROR(Status)) {
|
||||
// DGB_nbCallback(" GetDebugLogFile() -> HandleProtocol : %s\n", efiStrError(Status));
|
||||
// }
|
||||
// RootDir = EfiLibOpenRoot(LoadedImage->DeviceHandle);
|
||||
// if (RootDir == NULL) {
|
||||
// DGB_nbCallback(" GetDebugLogFile() -> EfiLibOpenRoot : %s\n", efiStrError(Status));
|
||||
// }
|
||||
//
|
||||
// // Open log file from current root
|
||||
// Status = RootDir->Open(RootDir, &LogFile, SWPrintf("%ls\\%ls", self.getCloverDirFullPath().wc_str(), DEBUG_LOG).wc_str(),
|
||||
// EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE, 0);
|
||||
#ifdef USE_SELF_INSTANCE
|
||||
if ( !self.isInitialized() ) return 0;
|
||||
#endif
|
||||
|
||||
if ( !self.isInitialized() ) return 0;
|
||||
g_OpeningLogFile = 1;
|
||||
|
||||
EFI_TIME Now;
|
||||
Status = gRT->GetTime(&Now, NULL);
|
||||
@ -146,27 +137,40 @@ static UINTN GetDebugLogFile()
|
||||
DBG("GetTime return %s\n", efiStrError(Status));
|
||||
}
|
||||
|
||||
#ifdef USE_SELF_INSTANCE
|
||||
const EFI_FILE_PROTOCOL& CloverDir = self.getCloverDir();
|
||||
const XString& efiFileName = self.getCloverEfiFileName();
|
||||
#else
|
||||
XStringW efiFileName;
|
||||
const EFI_FILE_PROTOCOL* CloverDirPtr = Self::getCloverDirAndEfiFileName(gImageHandle, &efiFileName);
|
||||
if ( CloverDirPtr == NULL ) return 0;
|
||||
const EFI_FILE_PROTOCOL& CloverDir = *CloverDirPtr;
|
||||
#endif
|
||||
|
||||
if ( debugLogFileName.isEmpty() )
|
||||
{
|
||||
debugLogFileName = S8Printf("misc\\%04d-%02d-%02d_%02d-%02d_%ls.log", Now.Year, Now.Month, Now.Day, Now.Hour, Now.Minute, self.getCloverEfiFileName().wc_str());
|
||||
Status = self.getCloverDir().Open(&self.getCloverDir(), &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
debugLogFileName = S8Printf("misc\\%04d-%02d-%02d_%02d-%02d_%ls.log", Now.Year, Now.Month, Now.Day, Now.Hour, Now.Minute, efiFileName.wc_str());
|
||||
Status = CloverDir.Open(&CloverDir, &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
if ( !EFI_ERROR(Status) ) LogFile->Close(LogFile); // DO NOT modify Status here.
|
||||
INTN i=1;
|
||||
while ( Status != EFI_NOT_FOUND && (i < MAX_INTN) ) {
|
||||
debugLogFileName = S8Printf("misc\\%04d-%02d-%02d_%02d-%02d_%ls(%lld).log", Now.Year, Now.Month, Now.Day, Now.Hour, Now.Minute, self.getCloverEfiFileName().wc_str(), i);
|
||||
Status = self.getCloverDir().Open(&self.getCloverDir(), &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
debugLogFileName = S8Printf("misc\\%04d-%02d-%02d_%02d-%02d_%ls(%lld).log", Now.Year, Now.Month, Now.Day, Now.Hour, Now.Minute, efiFileName.wc_str(), i);
|
||||
Status = CloverDir.Open(&CloverDir, &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
if ( !EFI_ERROR(Status) ) LogFile->Close(LogFile); // DO NOT modify Status here.
|
||||
}
|
||||
if ( Status != EFI_NOT_FOUND ) {
|
||||
DBG("Cannot find a free debug log file name\n"); // I can't imagine that to happen...
|
||||
debugLogFileName.setEmpty(); // To allow to retry at the next call
|
||||
g_OpeningLogFile = 0;
|
||||
return 0;
|
||||
}
|
||||
Status = self.getCloverDir().Open(&self.getCloverDir(), &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE, 0);
|
||||
Status = CloverDir.Open(&CloverDir, &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE, 0);
|
||||
gLogFile = LogFile;
|
||||
g_OpeningLogFile = 0;
|
||||
return 0;
|
||||
}else{
|
||||
Status = self.getCloverDir().Open(&self.getCloverDir(), &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE, 0);
|
||||
Status = CloverDir.Open(&CloverDir, &LogFile, debugLogFileName.wc_str(), EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE, 0);
|
||||
g_OpeningLogFile = 0;
|
||||
|
||||
//// Jief : Instead of EfiLibFileInfo, let's use SetPosition to get the size.
|
||||
// if (!EFI_ERROR(Status)) {
|
||||
@ -200,79 +204,7 @@ static UINTN GetDebugLogFile()
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
#else
|
||||
EFI_FILE_PROTOCOL* GetDebugLogFile()
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_LOADED_IMAGE *LoadedImage;
|
||||
EFI_FILE_PROTOCOL *RootDir;
|
||||
EFI_FILE_PROTOCOL *LogFile;
|
||||
|
||||
// get RootDir from device we are loaded from
|
||||
Status = gBS->HandleProtocol(gImageHandle, &gEfiLoadedImageProtocolGuid, (VOID **) &LoadedImage);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return NULL;
|
||||
}
|
||||
RootDir = EfiLibOpenRoot(LoadedImage->DeviceHandle);
|
||||
if (RootDir == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Open log file from current root
|
||||
Status = RootDir->Open(RootDir, &LogFile, debugLogFileName.wc_str(),
|
||||
EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE, 0);
|
||||
|
||||
// If the log file is not found try to create it
|
||||
if (Status == EFI_NOT_FOUND) {
|
||||
Status = RootDir->Open(RootDir, &LogFile, debugLogFileName.wc_str(),
|
||||
EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE, 0);
|
||||
}
|
||||
RootDir->Close(RootDir);
|
||||
RootDir = NULL;
|
||||
|
||||
if (EFI_ERROR(Status)) {
|
||||
// try on first EFI partition
|
||||
Status = egFindESP(&RootDir);
|
||||
if (!EFI_ERROR(Status)) {
|
||||
Status = RootDir->Open(RootDir, &LogFile, debugLogFileName.wc_str(),
|
||||
EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE, 0);
|
||||
// If the log file is not found try to create it
|
||||
if (Status == EFI_NOT_FOUND) {
|
||||
Status = RootDir->Open(RootDir, &LogFile, debugLogFileName.wc_str(),
|
||||
EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE, 0);
|
||||
}
|
||||
RootDir->Close(RootDir);
|
||||
RootDir = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
if (EFI_ERROR(Status)) {
|
||||
LogFile = NULL;
|
||||
}
|
||||
|
||||
return LogFile;
|
||||
}
|
||||
|
||||
// Jief : do we need that ?
|
||||
// if (EFI_ERROR(Status)) {
|
||||
// // try on first EFI partition
|
||||
// Status = egFindESP(&RootDir);
|
||||
// if (!EFI_ERROR(Status)) {
|
||||
// Status = RootDir->Open(RootDir, &LogFile, SWPrintf("%ls\\%ls", self.getCloverDirFullPath().wc_str(), DEBUG_LOG).wc_str(),
|
||||
// EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE, 0);
|
||||
// // If the log file is not found try to create it
|
||||
// if (Status == EFI_NOT_FOUND) {
|
||||
// Status = RootDir->Open(RootDir, &LogFile, SWPrintf("%ls\\%ls", self.getCloverDirFullPath().wc_str(), DEBUG_LOG).wc_str(),
|
||||
// EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE, 0);
|
||||
// }
|
||||
// RootDir->Close(RootDir);
|
||||
// RootDir = NULL;
|
||||
// }
|
||||
// }
|
||||
|
||||
#endif
|
||||
|
||||
#if NEW_LOG
|
||||
VOID SaveMessageToDebugLogFile(IN CHAR8 *LastMessage)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
@ -308,45 +240,6 @@ VOID SaveMessageToDebugLogFile(IN CHAR8 *LastMessage)
|
||||
// Not all Firmware implements Flush. So we have to close every time to force flush.
|
||||
closeDebugLog();
|
||||
}
|
||||
#else
|
||||
VOID SaveMessageToDebugLogFile(IN CHAR8 *LastMessage)
|
||||
{
|
||||
STATIC BOOLEAN FirstTimeSave = TRUE;
|
||||
// STATIC UINTN Position = 0;
|
||||
CHAR8 *MemLogBuffer;
|
||||
UINTN MemLogLen;
|
||||
CHAR8 *Text;
|
||||
UINTN TextLen;
|
||||
EFI_FILE_HANDLE LogFile;
|
||||
|
||||
MemLogBuffer = GetMemLogBuffer();
|
||||
MemLogLen = GetMemLogLen();
|
||||
Text = LastMessage;
|
||||
TextLen = AsciiStrLen(LastMessage);
|
||||
|
||||
/*UINTN lastWrittenOffset = GetDebugLogFile();*/
|
||||
LogFile = GetDebugLogFile();
|
||||
|
||||
// Write to the log file
|
||||
if (LogFile != NULL) {
|
||||
// Advance to the EOF so we append
|
||||
EFI_FILE_INFO *Info = EfiLibFileInfo(LogFile);
|
||||
if (Info) {
|
||||
LogFile->SetPosition(LogFile, Info->FileSize);
|
||||
// If we haven't had root before this write out whole log
|
||||
if (FirstTimeSave) {
|
||||
Text = MemLogBuffer;
|
||||
TextLen = MemLogLen;
|
||||
FirstTimeSave = FALSE;
|
||||
}
|
||||
// Write out this message
|
||||
LogFile->Write(LogFile, &TextLen, Text);
|
||||
}
|
||||
LogFile->Close(LogFile);
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
void EFIAPI MemLogCallback(IN INTN DebugMode, IN CHAR8 *LastMessage)
|
||||
{
|
||||
@ -380,28 +273,12 @@ void EFIAPI DebugLog(IN INTN DebugMode, IN CONST CHAR8 *FormatString, ...)
|
||||
MemLogfVA(TRUE, DebugMode, FormatString, Marker);
|
||||
VA_END(Marker);
|
||||
}
|
||||
#if NEW_LOG
|
||||
|
||||
void InitBooterLog(void)
|
||||
{
|
||||
SetMemLogCallback(MemLogCallback);
|
||||
}
|
||||
|
||||
#else
|
||||
void InitBooterLog(void)
|
||||
{
|
||||
EFI_TIME Now;
|
||||
EFI_STATUS Status;
|
||||
|
||||
Status = gRT->GetTime(&Now, NULL);
|
||||
if (!EFI_ERROR(Status)) {
|
||||
debugLogFileName = SWPrintf("misc\\%d-%d-%d_%d-%d-%d_%ls.log", Now.Year, Now.Month, Now.Day, Now.Hour, Now.Minute, Now.Second, self.getCloverEfiFileName().wc_str());
|
||||
} else {
|
||||
debugLogFileName = L"misc\\debug.log"_XSW;
|
||||
}
|
||||
|
||||
SetMemLogCallback(MemLogCallback);
|
||||
}
|
||||
#endif
|
||||
|
||||
EFI_STATUS SetupBooterLog(BOOLEAN AllowGrownSize)
|
||||
{
|
||||
|
@ -526,7 +526,11 @@ EFI_STATUS LoadPlist(const XStringW& ConfName, C* plist)
|
||||
XmlLiteParser xmlLiteParser;
|
||||
bool parsingOk = plist->parse((const CHAR8*)ConfigPtr, Size, ""_XS8, &xmlLiteParser);
|
||||
if ( xmlLiteParser.getErrorsAndWarnings().size() ) {
|
||||
DebugLog(2, "There is problems in plist '%ls'\n", configPlistPath.wc_str());
|
||||
if ( xmlLiteParser.getErrorsAndWarnings().size() > 1 ) {
|
||||
DebugLog(2, "There are problems in plist '%ls'\n", configPlistPath.wc_str());
|
||||
}else{
|
||||
DebugLog(2, "There is a problem in plist '%ls'\n", configPlistPath.wc_str());
|
||||
}
|
||||
for ( size_t idx = 0 ; idx < xmlLiteParser.getErrorsAndWarnings().size() ; idx++ ) {
|
||||
const XmlParserMessage& xmlMsg = xmlLiteParser.getErrorsAndWarnings()[idx];
|
||||
DebugLog(2, "%s: %s\n", xmlMsg.isError ? "Error" : "Warning", xmlMsg.msg.c_str());
|
||||
|
@ -21,6 +21,106 @@
|
||||
#define DBG(...) DebugLog(DEBUG_SELF, __VA_ARGS__)
|
||||
#endif
|
||||
|
||||
EFI_STATUS Self::__initialize(EFI_HANDLE SelfImageHandle, EFI_LOADED_IMAGE** SelfLoadedImagePtr, EFI_SIMPLE_FILE_SYSTEM_PROTOCOL** SelfSimpleVolumePtr, EFI_FILE** SelfVolumeRootDirPtr, XStringW* CloverDirFullPathPtr, XStringW* efiFileNamePtr, EFI_FILE** CloverDirPtr)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
Status = gBS->HandleProtocol(SelfImageHandle, &gEfiLoadedImageProtocolGuid, (void **)SelfLoadedImagePtr);
|
||||
if ( EFI_ERROR(Status) ) {
|
||||
*SelfLoadedImagePtr = NULL;
|
||||
return RETURN_LOAD_ERROR;
|
||||
}
|
||||
EFI_LOADED_IMAGE* SelfLoadedImage = *SelfLoadedImagePtr;
|
||||
if ( SelfLoadedImage->DeviceHandle == NULL ) {
|
||||
*SelfLoadedImagePtr = NULL;
|
||||
return RETURN_LOAD_ERROR;
|
||||
}
|
||||
|
||||
Status = gBS->HandleProtocol(SelfLoadedImage->DeviceHandle, &gEfiSimpleFileSystemProtocolGuid, (void**)SelfSimpleVolumePtr);
|
||||
if ( EFI_ERROR(Status) ) {
|
||||
*SelfSimpleVolumePtr = NULL;
|
||||
return RETURN_LOAD_ERROR;
|
||||
}
|
||||
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* SelfSimpleVolume = *SelfSimpleVolumePtr;
|
||||
|
||||
Status = SelfSimpleVolume->OpenVolume(SelfSimpleVolume, SelfVolumeRootDirPtr);
|
||||
if ( EFI_ERROR(Status) ) {
|
||||
*SelfVolumeRootDirPtr = NULL;
|
||||
return RETURN_LOAD_ERROR;
|
||||
}
|
||||
EFI_FILE* SelfVolumeRootDir = *SelfVolumeRootDirPtr;
|
||||
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("SelfVolumeRootDir = %lld\n", uintptr_t(SelfVolumeRootDir));
|
||||
#endif
|
||||
|
||||
// find the current directory
|
||||
*CloverDirFullPathPtr = FileDevicePathToXStringW(SelfLoadedImage->FilePath);
|
||||
if ( CloverDirFullPathPtr->isEmpty() ) {
|
||||
return RETURN_LOAD_ERROR;
|
||||
}
|
||||
XStringW& CloverDirFullPath = *CloverDirFullPathPtr;
|
||||
|
||||
// Do this before the next check.
|
||||
if ( !CloverDirFullPath.startWith('\\') ) {
|
||||
// Some firmware seems to not put a '\' at the begining. Do not panic anymore, just add it.
|
||||
CloverDirFullPath.insertAtPos('\\', 0);
|
||||
}
|
||||
|
||||
*efiFileNamePtr = CloverDirFullPath.basename();
|
||||
XStringW& efiFileName = *efiFileNamePtr;
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("efiFileName=%ls\n", efiFileName.wc_str());
|
||||
#endif
|
||||
|
||||
// History : if this Clover was started as BootX64.efi, redirect to /EFI/CLOVER
|
||||
if ( CloverDirFullPath.isEqualIC("\\EFI\\Boot\\BootX64.efi") ) { // keep getCloverDir() in sync !
|
||||
CloverDirFullPath.takeValueFrom("\\EFI\\CLOVER\\CloverX64.efi"); // keep getCloverDir() in sync !
|
||||
}
|
||||
|
||||
if ( CloverDirFullPath.lastChar() == U'\\' ) { // keep getCloverDir() in sync !
|
||||
log_technical_bug("CloverDirFullPath.lastChar() == U'\\'"); // Just to see if that happens.
|
||||
CloverDirFullPath.deleteCharsAtPos(CloverDirFullPath.length()-1, 1);
|
||||
}
|
||||
|
||||
size_t i = CloverDirFullPath.rindexOf(U'\\', SIZE_T_MAX-1); // keep getCloverDir() in sync !
|
||||
if ( i != SIZE_T_MAX && i > 0 ) CloverDirFullPath.deleteCharsAtPos(i, SIZE_T_MAX); // keep getCloverDir() in sync !
|
||||
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("SelfDirPath = %ls\n", CloverDirFullPath.wc_str());
|
||||
#endif
|
||||
|
||||
Status = SelfVolumeRootDir->Open(SelfVolumeRootDir, CloverDirPtr, CloverDirFullPath.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
if ( EFI_ERROR(Status) ) {
|
||||
*CloverDirPtr = NULL;
|
||||
return RETURN_LOAD_ERROR;
|
||||
}
|
||||
EFI_FILE* CloverDir = *CloverDirPtr;
|
||||
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("CloverDir = %lld\n", uintptr_t(CloverDir));
|
||||
#endif
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
const EFI_FILE_PROTOCOL* Self::getCloverDirAndEfiFileName(EFI_HANDLE ImageHandle, XStringW* efiFileName)
|
||||
{
|
||||
EFI_LOADED_IMAGE* SelfLoadedImage; // this efi.
|
||||
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* SelfSimpleVolume; // Volume containing this efi.
|
||||
EFI_FILE* SelfVolumeRootDir; // Root dir of the volume containing this efi.
|
||||
XStringW CloverDirFullPath; // full path of folder containing this efi.
|
||||
EFI_FILE* CloverDir; // opened folder containing this efi
|
||||
|
||||
/*EFI_STATUS Status = */__initialize(ImageHandle, &SelfLoadedImage, &SelfSimpleVolume, &SelfVolumeRootDir, &CloverDirFullPath, efiFileName, &CloverDir);
|
||||
if ( efiFileName->isEmpty() ) {
|
||||
if ( CloverDir != NULL ) CloverDir->Close(CloverDir);
|
||||
return NULL;
|
||||
}
|
||||
return CloverDir;
|
||||
}
|
||||
|
||||
|
||||
|
||||
Self self;
|
||||
|
||||
@ -42,84 +142,106 @@ EFI_STATUS Self::_openDir(const XStringW& path, bool* b, EFI_FILE** efiDir)
|
||||
|
||||
EFI_STATUS Self::_initialize()
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
// EFI_STATUS Status;
|
||||
|
||||
Status = gBS->HandleProtocol(m_SelfImageHandle, &gEfiLoadedImageProtocolGuid, (void **)&m_SelfLoadedImage);
|
||||
#ifdef DEBUG
|
||||
if ( EFI_ERROR(Status) ) panic("Cannot get SelfLoadedImage");
|
||||
if ( m_SelfLoadedImage->DeviceHandle == NULL ) panic("m_SelfLoadedImage->DeviceHandle == NULL");
|
||||
m_SelfDevicePath = DuplicateDevicePath(DevicePathFromHandle(m_SelfLoadedImage->DeviceHandle));
|
||||
if ( m_SelfDevicePath == NULL ) panic("m_SelfDevicePath == NULL");
|
||||
#else
|
||||
if ( EFI_ERROR(Status) ) return Status;
|
||||
if ( m_SelfLoadedImage->DeviceHandle == NULL ) return EFI_NOT_FOUND;
|
||||
m_SelfDevicePath = DuplicateDevicePath(DevicePathFromHandle(m_SelfLoadedImage->DeviceHandle));
|
||||
if ( m_SelfDevicePath == NULL ) return EFI_NOT_FOUND;
|
||||
#endif
|
||||
/*Status = */__initialize(m_SelfImageHandle, &m_SelfLoadedImage, &m_SelfSimpleVolume, &m_SelfVolumeRootDir, &m_CloverDirFullPath, &m_efiFileName, &m_CloverDir);
|
||||
if ( m_SelfLoadedImage == NULL ) log_technical_bug("Cannot get SelfLoadedImage");
|
||||
if ( m_SelfLoadedImage->DeviceHandle == NULL ) log_technical_bug("m_SelfLoadedImage->DeviceHandle == NULL");
|
||||
if ( m_SelfSimpleVolume == NULL ) log_technical_bug("Cannot get m_SelfSimpleVolume");
|
||||
if ( m_SelfVolumeRootDir == NULL ) log_technical_bug("Cannot get m_SelfVolumeRootDir");
|
||||
if ( m_CloverDirFullPath.isEmpty() ) log_technical_bug("Cannot get m_CloverDirFullPath");
|
||||
if ( m_efiFileName.isEmpty() ) log_technical_bug("Cannot get m_efiFileName");
|
||||
if ( m_CloverDir == NULL ) panic("Cannot open getSelfRootDir()"); // We have to panic, nothing would work without m_CloverDir
|
||||
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("Self DevicePath()=%ls @%llX\n", FileDevicePathToXStringW(m_SelfDevicePath).wc_str(), (uintptr_t)m_SelfLoadedImage->DeviceHandle);
|
||||
#endif
|
||||
Status = gBS->HandleProtocol(m_SelfLoadedImage->DeviceHandle, &gEfiSimpleFileSystemProtocolGuid, (void**)&m_SelfSimpleVolume);
|
||||
#ifdef DEBUG
|
||||
if ( EFI_ERROR(Status) ) panic("Cannot get m_SelfSimpleVolume");
|
||||
Status = m_SelfSimpleVolume->OpenVolume(m_SelfSimpleVolume, &m_SelfVolumeRootDir);
|
||||
if ( EFI_ERROR(Status) ) panic("Cannot get m_SelfRootDir");
|
||||
#else
|
||||
if ( EFI_ERROR(Status) ) return Status;
|
||||
Status = m_SelfSimpleVolume->OpenVolume(m_SelfSimpleVolume, &m_SelfVolumeRootDir);
|
||||
if ( EFI_ERROR(Status) ) return Status;
|
||||
#endif
|
||||
// find the current directory
|
||||
m_CloverDirFullPath = FileDevicePathToXStringW(m_SelfLoadedImage->FilePath);
|
||||
|
||||
// Do this before the next check.
|
||||
if ( !m_CloverDirFullPath.startWith('\\') ) {
|
||||
//CHAR16* f = ConvertDevicePathToText(m_SelfLoadedImage->FilePath, TRUE, TRUE);
|
||||
//panic("Bad format for m_CloverDirFullPath(%ls). It must start with a '\\'.\nConvertDevicePathToText=%ls", m_CloverDirFullPath.wc_str(), f);
|
||||
//
|
||||
// Somefirmware seems to not put a '\' at the begining. Do not panic anymore, just add it.
|
||||
m_CloverDirFullPath.insertAtPos('\\', 0);
|
||||
m_SelfDevicePath = NULL;
|
||||
if ( m_SelfLoadedImage && m_SelfLoadedImage->DeviceHandle ) {
|
||||
m_SelfDevicePath = FileDevicePath(m_SelfLoadedImage->DeviceHandle, m_CloverDirFullPath + '\\' + m_efiFileName);
|
||||
}
|
||||
|
||||
m_efiFileName = m_CloverDirFullPath.basename();
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("m_efiFileName=%ls\n", m_efiFileName.wc_str());
|
||||
#endif
|
||||
|
||||
// History : if this Clover was started as BootX64.efi, redirect to /EFI/CLOVER
|
||||
if ( m_CloverDirFullPath.isEqualIC("\\EFI\\Boot\\BootX64.efi") ) {
|
||||
m_CloverDirFullPath.takeValueFrom("\\EFI\\CLOVER\\CloverX64.efi");
|
||||
if ( m_SelfDevicePath == NULL ) {
|
||||
log_technical_bug("m_SelfDevicePath == NULL"); // not sure what can work without m_SelfDevicePath
|
||||
}else{
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("Self DevicePath()=%ls @%llX\n", FileDevicePathToXStringW(m_SelfDevicePath).wc_str(), (uintptr_t)m_SelfLoadedImage->DeviceHandle);
|
||||
#endif
|
||||
}
|
||||
#ifdef DEBUG
|
||||
if ( m_CloverDirFullPath.isEmpty() ) panic("m_CloverDirFullPath.isEmpty()");
|
||||
#else
|
||||
if ( m_CloverDirFullPath.isEmpty() ) return EFI_NOT_FOUND;
|
||||
#endif
|
||||
m_SelfDevicePath = FileDevicePath(m_SelfLoadedImage->DeviceHandle, m_CloverDirFullPath);
|
||||
m_SelfDevicePathAsXStringW = FileDevicePathToXStringW(m_SelfDevicePath);
|
||||
|
||||
#ifdef DEBUG
|
||||
if ( m_CloverDirFullPath.lastChar() == U'\\' ) panic("m_CloverDirFullPath.lastChar() == U'\\'");
|
||||
//if ( m_CloverDirFullPath.endsWith('\\') ) panic("m_CloverDirFullPath.endsWith('\\')");
|
||||
#else
|
||||
if ( m_CloverDirFullPath.lastChar() == U'\\' ) return EFI_NOT_FOUND;
|
||||
#endif
|
||||
|
||||
|
||||
size_t i = m_CloverDirFullPath.rindexOf(U'\\', SIZE_T_MAX-1);
|
||||
if ( i != SIZE_T_MAX && i > 0 ) m_CloverDirFullPath.deleteCharsAtPos(i, SIZE_T_MAX);
|
||||
|
||||
#ifdef JIEF_DEBUG
|
||||
DBG("SelfDirPath = %ls\n", m_CloverDirFullPath.wc_str());
|
||||
#endif
|
||||
Status = m_SelfVolumeRootDir->Open(m_SelfVolumeRootDir, &m_CloverDir, m_CloverDirFullPath.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
if ( EFI_ERROR(Status) ) panic("Cannot open getSelfRootDir()");
|
||||
|
||||
// m_SelfDevicePathAsXStringW = FileDevicePathToXStringW(m_SelfDevicePath);
|
||||
|
||||
_openDir(THEMES_DIRNAME, &m_ThemesDirExists, &m_ThemesDir); // don't need to check returned status as it's ok to not have a themes dir.
|
||||
|
||||
return EFI_SUCCESS;
|
||||
|
||||
|
||||
//
|
||||
//
|
||||
// Status = gBS->HandleProtocol(m_SelfImageHandle, &gEfiLoadedImageProtocolGuid, (void **)&m_SelfLoadedImage);
|
||||
// if ( EFI_ERROR(Status) ) panic("Cannot get SelfLoadedImage"); // We have to panic, nothing would work without m_CloverDir, and m_SelfImageHandle is needed to get it
|
||||
// if ( m_SelfLoadedImage->DeviceHandle == NULL ) panic("m_SelfLoadedImage->DeviceHandle == NULL"); // We have to panic, nothing would work without m_CloverDir, and m_SelfLoadedImage->DeviceHandle is needed to get it
|
||||
// m_SelfDevicePath = DuplicateDevicePath(DevicePathFromHandle(m_SelfLoadedImage->DeviceHandle));
|
||||
// if ( m_SelfDevicePath == NULL ) {
|
||||
// log_technical_bug("m_SelfDevicePath == NULL"); // not sure what can work without m_SelfDevicePath
|
||||
// }
|
||||
//
|
||||
//#ifdef JIEF_DEBUG
|
||||
// DBG("Self DevicePath()=%ls @%llX\n", FileDevicePathToXStringW(m_SelfDevicePath).wc_str(), (uintptr_t)m_SelfLoadedImage->DeviceHandle);
|
||||
//#endif
|
||||
//
|
||||
// Status = gBS->HandleProtocol(m_SelfLoadedImage->DeviceHandle, &gEfiSimpleFileSystemProtocolGuid, (void**)&m_SelfSimpleVolume);
|
||||
// if ( EFI_ERROR(Status) ) panic("Cannot get m_SelfSimpleVolume"); // We have to panic, nothing would work without m_CloverDir, and m_SelfSimpleVolume is needed to get it
|
||||
// Status = m_SelfSimpleVolume->OpenVolume(m_SelfSimpleVolume, &m_SelfVolumeRootDir);
|
||||
// if ( EFI_ERROR(Status) ) panic("Cannot get m_SelfVolumeRootDir"); // We have to panic, nothing would work without m_CloverDir, and m_SelfVolumeRootDir is needed to get it
|
||||
//
|
||||
//#ifdef JIEF_DEBUG
|
||||
// DBG("m_SelfVolumeRootDir = %lld\n", uintptr_t(m_SelfVolumeRootDir));
|
||||
//#endif
|
||||
//
|
||||
// // find the current directory
|
||||
// m_CloverDirFullPath = FileDevicePathToXStringW(m_SelfLoadedImage->FilePath);
|
||||
//
|
||||
// // Do this before the next check.
|
||||
// if ( !m_CloverDirFullPath.startWith('\\') ) {
|
||||
// //CHAR16* f = ConvertDevicePathToText(m_SelfLoadedImage->FilePath, TRUE, TRUE);
|
||||
// //panic("Bad format for m_CloverDirFullPath(%ls). It must start with a '\\'.\nConvertDevicePathToText=%ls", m_CloverDirFullPath.wc_str(), f);
|
||||
// //
|
||||
// // Some firmware seems to not put a '\' at the begining. Do not panic anymore, just add it.
|
||||
// m_CloverDirFullPath.insertAtPos('\\', 0);
|
||||
// }
|
||||
//
|
||||
// m_efiFileName = m_CloverDirFullPath.basename();
|
||||
//#ifdef JIEF_DEBUG
|
||||
// DBG("m_efiFileName=%ls\n", m_efiFileName.wc_str());
|
||||
//#endif
|
||||
//
|
||||
// // Code to find m_CloverDirFullPath is duplicated in BootLog.cpp in case USE_SELF_INSTANCE is not defined
|
||||
//
|
||||
// // History : if this Clover was started as BootX64.efi, redirect to /EFI/CLOVER
|
||||
// if ( m_CloverDirFullPath.isEqualIC("\\EFI\\Boot\\BootX64.efi") ) { // keep getCloverDir() in sync !
|
||||
// m_CloverDirFullPath.takeValueFrom("\\EFI\\CLOVER\\CloverX64.efi"); // keep getCloverDir() in sync !
|
||||
// }
|
||||
// if ( m_CloverDirFullPath.isEmpty() ) log_technical_bug("m_CloverDirFullPath.isEmpty()");
|
||||
// m_SelfDevicePath = FileDevicePath(m_SelfLoadedImage->DeviceHandle, m_CloverDirFullPath);
|
||||
//// m_SelfDevicePathAsXStringW = FileDevicePathToXStringW(m_SelfDevicePath);
|
||||
//
|
||||
// if ( m_CloverDirFullPath.lastChar() == U'\\' ) { // keep getCloverDir() in sync !
|
||||
// log_technical_bug("m_CloverDirFullPath.lastChar() == U'\\'"); // Just to see if that happens.
|
||||
// m_CloverDirFullPath.deleteCharsAtPos(m_CloverDirFullPath.length()-1, 1);
|
||||
// }
|
||||
//
|
||||
// size_t i = m_CloverDirFullPath.rindexOf(U'\\', SIZE_T_MAX-1); // keep getCloverDir() in sync !
|
||||
// if ( i != SIZE_T_MAX && i > 0 ) m_CloverDirFullPath.deleteCharsAtPos(i, SIZE_T_MAX); // keep getCloverDir() in sync !
|
||||
//
|
||||
//#ifdef JIEF_DEBUG
|
||||
// DBG("SelfDirPath = %ls\n", m_CloverDirFullPath.wc_str());
|
||||
//#endif
|
||||
// Status = m_SelfVolumeRootDir->Open(m_SelfVolumeRootDir, &m_CloverDir, m_CloverDirFullPath.wc_str(), EFI_FILE_MODE_READ, 0);
|
||||
// if ( EFI_ERROR(Status) ) panic("Cannot open getSelfRootDir()"); // We have to panic, nothing would work without m_CloverDir
|
||||
//#ifdef JIEF_DEBUG
|
||||
// DBG("m_CloverDir = %lld\n", uintptr_t(m_CloverDir));
|
||||
//#endif
|
||||
//
|
||||
//
|
||||
// _openDir(THEMES_DIRNAME, &m_ThemesDirExists, &m_ThemesDir); // don't need to check returned status as it's ok to not have a themes dir.
|
||||
//
|
||||
// return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
EFI_STATUS Self::initialize(EFI_HANDLE ImageHandle)
|
||||
|
@ -18,34 +18,34 @@ extern "C" {
|
||||
|
||||
class Self
|
||||
{
|
||||
// Class method, usable even without any instance of Self.
|
||||
protected:
|
||||
EFI_HANDLE m_SelfImageHandle; // this efi.
|
||||
EFI_LOADED_IMAGE* m_SelfLoadedImage; // this efi.
|
||||
EFI_DEVICE_PATH* m_SelfDevicePath; // path to device containing this efi.
|
||||
XStringW m_SelfDevicePathAsXStringW; // path to device containing this efi.
|
||||
static EFI_STATUS __initialize(EFI_HANDLE m_SelfImageHandle, EFI_LOADED_IMAGE** m_SelfLoadedImage, EFI_SIMPLE_FILE_SYSTEM_PROTOCOL** m_SelfSimpleVolumePtr, EFI_FILE** m_SelfVolumeRootDirPtr, XStringW* m_CloverDirFullPathPtr, XStringW* m_efiFileNamePtr, EFI_FILE** m_CloverDirPtr);
|
||||
public:
|
||||
static const EFI_FILE_PROTOCOL* getCloverDirAndEfiFileName(EFI_HANDLE ImageHandle, XStringW* efiFileName);
|
||||
|
||||
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL *m_SelfSimpleVolume; // Volume containing this efi.
|
||||
EFI_FILE* m_SelfVolumeRootDir; // Root dir of the volume containing this efi.
|
||||
protected:
|
||||
EFI_HANDLE m_SelfImageHandle {}; // this efi.
|
||||
EFI_LOADED_IMAGE* m_SelfLoadedImage {}; // this efi.
|
||||
EFI_DEVICE_PATH* m_SelfDevicePath {}; // path to device containing this efi.
|
||||
// XStringW m_SelfDevicePathAsXStringW; // path to device containing this efi.
|
||||
|
||||
XStringW m_efiFileName = L""_XSW;
|
||||
EFI_DEVICE_PATH* m_CloverDirFullDevicePath; // full path, including device, of the folder containing this efi.
|
||||
EFI_FILE* m_CloverDir; // opened folder containing this efi
|
||||
XStringW m_CloverDirFullPath; // full path of folder containing this efi.
|
||||
// XStringW m_CloverDirPath; // dirname containing this efi (contains just the dir, not the device path)
|
||||
EFI_SIMPLE_FILE_SYSTEM_PROTOCOL* m_SelfSimpleVolume {}; // Volume containing this efi.
|
||||
EFI_FILE* m_SelfVolumeRootDir {}; // Root dir of the volume containing this efi.
|
||||
|
||||
// bool m_OemDirExists;
|
||||
// EFI_FILE *m_OemDir;
|
||||
XStringW m_efiFileName = {};
|
||||
EFI_DEVICE_PATH* m_CloverDirFullDevicePath {}; // full path, including device, of the folder containing this efi.
|
||||
EFI_FILE* m_CloverDir {}; // opened folder containing this efi
|
||||
XStringW m_CloverDirFullPath {}; // full path of folder containing this efi.
|
||||
|
||||
bool m_ThemesDirExists;
|
||||
EFI_FILE *m_ThemesDir;
|
||||
bool m_ThemesDirExists {};
|
||||
EFI_FILE *m_ThemesDir {};
|
||||
|
||||
EFI_STATUS _openDir(const XStringW& path, bool* b, EFI_FILE** efiDir);
|
||||
EFI_STATUS _initialize();
|
||||
|
||||
public:
|
||||
Self () : m_SelfImageHandle(NULL), m_SelfLoadedImage(NULL), m_SelfDevicePath(NULL), m_SelfDevicePathAsXStringW(),
|
||||
m_SelfSimpleVolume(NULL), m_SelfVolumeRootDir(NULL),
|
||||
m_CloverDirFullDevicePath(NULL), m_CloverDir(NULL), m_CloverDirFullPath()/*, m_CloverDirPath()*/, m_ThemesDirExists(false), m_ThemesDir(0) {};
|
||||
Self () {};
|
||||
Self(const Self&) = delete;
|
||||
Self& operator = (const Self&) = delete;
|
||||
|
||||
@ -77,10 +77,6 @@ public:
|
||||
const EFI_DEVICE_PATH& getCloverDirFullDevicePath() { checkInitialized(); return *m_CloverDirFullDevicePath; }
|
||||
const EFI_FILE& getCloverDir() { checkInitialized(); return *m_CloverDir; }
|
||||
const XStringW& getCloverDirFullPath() { checkInitialized(); return m_CloverDirFullPath; }
|
||||
// const XStringW& getCloverDirPath() { checkInitialized(); return m_CloverDirPath; } // returns path containing this efi. Like \\EFI\\CLOVER
|
||||
|
||||
// bool oemDirExists() { checkInitialized(); return m_OemDirExists; }
|
||||
// const EFI_FILE& getOemDir() { checkInitialized(); return *m_OemDir; } // Oem dir name under SelfDir. Like "OEM\\MyBoard"
|
||||
|
||||
bool themesDirExists() { checkInitialized(); return m_ThemesDirExists; }
|
||||
const EFI_FILE& getThemesDir() { checkInitialized(); return *m_ThemesDir; }
|
||||
|
Loading…
Reference in New Issue
Block a user