Formatting

This commit is contained in:
Maschell 2020-06-03 18:36:02 +02:00
parent 5ac51ef3ce
commit 6c5a2edf6d
4 changed files with 249 additions and 241 deletions

View File

@ -23,23 +23,20 @@
class CThread { class CThread {
public: public:
typedef void (* Callback)(CThread *thread, void *arg); typedef void (*Callback)(CThread *thread, void *arg);
//! constructor //! constructor
CThread(int32_t iAttr, int32_t iPriority = 16, int32_t iStackSize = 0x8000, CThread::Callback callback = NULL, void *callbackArg = NULL) CThread(int32_t iAttr, int32_t iPriority = 16, int32_t iStackSize = 0x8000, CThread::Callback callback = NULL, void *callbackArg = NULL)
: pThread(NULL) : pThread(NULL), pThreadStack(NULL), pCallback(callback), pCallbackArg(callbackArg) {
, pThreadStack(NULL)
, pCallback(callback)
, pCallbackArg(callbackArg) {
//! save attribute assignment //! save attribute assignment
iAttributes = iAttr; iAttributes = iAttr;
//! allocate the thread //! allocate the thread
pThread = (OSThread*) memalign(8, 0x1000); pThread = (OSThread *) memalign(8, 0x1000);
//! allocate the stack //! allocate the stack
pThreadStack = (uint8_t *) memalign(0x20, iStackSize); pThreadStack = (uint8_t *) memalign(0x20, iStackSize);
//! create the thread //! create the thread
if(pThread && pThreadStack) { if (pThread && pThreadStack) {
OSCreateThread(pThread, (int (*)(int, const char**)) &CThread::threadCallback, 1, (char*) this, (void*) (pThreadStack+iStackSize), iStackSize, iPriority, iAttributes); OSCreateThread(pThread, (int (*)(int, const char **)) &CThread::threadCallback, 1, (char *) this, (void *) (pThreadStack + iStackSize), iStackSize, iPriority, iAttributes);
} }
} }
@ -49,42 +46,49 @@ public:
} }
static CThread *create(CThread::Callback callback, void *callbackArg, int32_t iAttr = eAttributeNone, int32_t iPriority = 16, int32_t iStackSize = 0x8000) { static CThread *create(CThread::Callback callback, void *callbackArg, int32_t iAttr = eAttributeNone, int32_t iPriority = 16, int32_t iStackSize = 0x8000) {
return ( new CThread(iAttr, iPriority, iStackSize, callback, callbackArg) ); return (new CThread(iAttr, iPriority, iStackSize, callback, callbackArg));
} }
//! Get thread ID //! Get thread ID
virtual void* getThread() const { virtual void *getThread() const {
return pThread; return pThread;
} }
//! Thread entry function //! Thread entry function
virtual void executeThread(void) { virtual void executeThread(void) {
if(pCallback) if (pCallback)
pCallback(this, pCallbackArg); pCallback(this, pCallbackArg);
} }
//! Suspend thread //! Suspend thread
virtual void suspendThread(void) { virtual void suspendThread(void) {
if(isThreadSuspended()) return; if (isThreadSuspended()) return;
if(pThread) OSSuspendThread(pThread); if (pThread) OSSuspendThread(pThread);
} }
//! Resume thread //! Resume thread
virtual void resumeThread(void) { virtual void resumeThread(void) {
if(!isThreadSuspended()) return; if (!isThreadSuspended()) return;
if(pThread) OSResumeThread(pThread); if (pThread) OSResumeThread(pThread);
} }
//! Set thread priority //! Set thread priority
virtual void setThreadPriority(int32_t prio) { virtual void setThreadPriority(int32_t prio) {
if(pThread) OSSetThreadPriority(pThread, prio); if (pThread) OSSetThreadPriority(pThread, prio);
} }
//! Check if thread is suspended //! Check if thread is suspended
virtual bool isThreadSuspended(void) const { virtual bool isThreadSuspended(void) const {
if(pThread) return OSIsThreadSuspended(pThread); if (pThread) return OSIsThreadSuspended(pThread);
return false; return false;
} }
//! Check if thread is terminated //! Check if thread is terminated
virtual bool isThreadTerminated(void) const { virtual bool isThreadTerminated(void) const {
if(pThread) return OSIsThreadTerminated(pThread); if (pThread) return OSIsThreadTerminated(pThread);
return false; return false;
} }
//! Check if thread is running //! Check if thread is running
virtual bool isThreadRunning(void) const { virtual bool isThreadRunning(void) const {
return !isThreadSuspended() && !isThreadRunning(); return !isThreadSuspended() && !isThreadRunning();
@ -92,29 +96,30 @@ public:
//! Gets the thread affinity. //! Gets the thread affinity.
virtual uint16_t getThreadAffinity(void) const { virtual uint16_t getThreadAffinity(void) const {
if(pThread) return OSGetThreadAffinity(pThread); if (pThread) return OSGetThreadAffinity(pThread);
return 0; return 0;
} }
//! Shutdown thread //! Shutdown thread
virtual void shutdownThread(void) { virtual void shutdownThread(void) {
//! wait for thread to finish //! wait for thread to finish
if(pThread && !(iAttributes & eAttributeDetach)) { if (pThread && !(iAttributes & eAttributeDetach)) {
while(isThreadSuspended()) { while (isThreadSuspended()) {
resumeThread(); resumeThread();
} }
OSJoinThread(pThread, NULL); OSJoinThread(pThread, NULL);
} }
//! free the thread stack buffer //! free the thread stack buffer
if(pThreadStack) { if (pThreadStack) {
free(pThreadStack); free(pThreadStack);
} }
if(pThread) { if (pThread) {
free(pThread); free(pThread);
} }
pThread = NULL; pThread = NULL;
pThreadStack = NULL; pThreadStack = NULL;
} }
//! Thread attributes //! Thread attributes
enum eCThreadAttributes { enum eCThreadAttributes {
eAttributeNone = 0x07, eAttributeNone = 0x07,
@ -130,6 +135,7 @@ private:
((CThread *) arg)->executeThread(); ((CThread *) arg)->executeThread();
return 0; return 0;
} }
int32_t iAttributes; int32_t iAttributes;
OSThread *pThread; OSThread *pThread;
uint8_t *pThreadStack; uint8_t *pThreadStack;

View File

@ -9,47 +9,48 @@
WUMS_MODULE_EXPORT_NAME("homebrew_memorymapping"); WUMS_MODULE_EXPORT_NAME("homebrew_memorymapping");
WUMS_INITIALIZE(){ WUMS_INITIALIZE() {
WHBLogUdpInit(); WHBLogUdpInit();
DEBUG_FUNCTION_LINE("Setting up memory mapping!"); DEBUG_FUNCTION_LINE("Setting up memory mapping!");
static uint8_t ucSetupRequired = 1; static uint8_t ucSetupRequired = 1;
if (!ucSetupRequired){ if (!ucSetupRequired) {
return; return;
} }
ucSetupRequired = 0; ucSetupRequired = 0;
MemoryMapping::setupMemoryMapping(); MemoryMapping::setupMemoryMapping();
MemoryMapping::CreateHeaps(); MemoryMapping::CreateHeaps();
DEBUG_FUNCTION_LINE("total free space %d KiB", MemoryMapping::GetFreeSpace()/1024); DEBUG_FUNCTION_LINE("total free space %d KiB", MemoryMapping::GetFreeSpace() / 1024);
} }
int main(int argc, char **argv) { int main(int argc, char **argv) {
WHBLogUdpInit(); WHBLogUdpInit();
MemoryMapping::DestroyHeaps(); MemoryMapping::DestroyHeaps();
MemoryMapping::CreateHeaps(); MemoryMapping::CreateHeaps();
DEBUG_FUNCTION_LINE("total free space %d KiB", MemoryMapping::GetFreeSpace()/1024); DEBUG_FUNCTION_LINE("total free space %d KiB", MemoryMapping::GetFreeSpace() / 1024);
return 0; return 0;
} }
void MemoryMappingFree(void* ptr){ void MemoryMappingFree(void *ptr) {
MemoryMapping::free(ptr); MemoryMapping::free(ptr);
} }
uint32_t MemoryMappingEffectiveToPhysical(uint32_t address){ uint32_t MemoryMappingEffectiveToPhysical(uint32_t address) {
return MemoryMapping::EffectiveToPhysical(address); return MemoryMapping::EffectiveToPhysical(address);
} }
uint32_t MemoryMappingPhysicalToEffective(uint32_t address){
uint32_t MemoryMappingPhysicalToEffective(uint32_t address) {
return MemoryMapping::PhysicalToEffective(address); return MemoryMapping::PhysicalToEffective(address);
} }
void* MemoryMappingAlloc(uint32_t size){ void *MemoryMappingAlloc(uint32_t size) {
void* res = MemoryMapping::alloc(size, 0x04); void *res = MemoryMapping::alloc(size, 0x04);
//DEBUG_FUNCTION_LINE("[res: %08X] alloc %d ", res, size); //DEBUG_FUNCTION_LINE("[res: %08X] alloc %d ", res, size);
return res; return res;
} }
void* MemoryMappingAllocEx(uint32_t size, uint32_t align){ void *MemoryMappingAllocEx(uint32_t size, uint32_t align) {
void * res = MemoryMapping::alloc(size, align); void *res = MemoryMapping::alloc(size, align);
//DEBUG_FUNCTION_LINE("[res %08X] allocEX %d %d ", res, size, align); //DEBUG_FUNCTION_LINE("[res %08X] allocEX %d %d ", res, size, align);
return res; return res;
} }

View File

@ -15,56 +15,56 @@
// #define DEBUG_FUNCTION_LINE(x,...) // #define DEBUG_FUNCTION_LINE(x,...)
void runOnAllCores(CThread::Callback callback, void *callbackArg, int32_t iAttr = 0, int32_t iPriority = 16, int32_t iStackSize = 0x8000) { void runOnAllCores(CThread::Callback callback, void *callbackArg, int32_t iAttr = 0, int32_t iPriority = 16, int32_t iStackSize = 0x8000) {
int32_t aff[] = {CThread::eAttributeAffCore2,CThread::eAttributeAffCore1,CThread::eAttributeAffCore0}; int32_t aff[] = {CThread::eAttributeAffCore2, CThread::eAttributeAffCore1, CThread::eAttributeAffCore0};
for(uint32_t i = 0; i <(sizeof(aff)/sizeof(aff[0])); i++) { for (uint32_t i = 0; i < (sizeof(aff) / sizeof(aff[0])); i++) {
CThread * thread = CThread::create(callback, callbackArg, iAttr | aff[i],iPriority,iStackSize); CThread *thread = CThread::create(callback, callbackArg, iAttr | aff[i], iPriority, iStackSize);
thread->resumeThread(); thread->resumeThread();
delete thread; delete thread;
} }
} }
void writeSegmentRegister(CThread *thread, void *arg) { void writeSegmentRegister(CThread *thread, void *arg) {
sr_table_t * table = (sr_table_t *) arg; sr_table_t *table = (sr_table_t *) arg;
uint16_t core = OSGetThreadAffinity(OSGetCurrentThread()); uint16_t core = OSGetThreadAffinity(OSGetCurrentThread());
DEBUG_FUNCTION_LINE("Writing segment register to core %d\n",core); DEBUG_FUNCTION_LINE("Writing segment register to core %d\n", core);
DCFlushRange(table,sizeof(sr_table_t)); DCFlushRange(table, sizeof(sr_table_t));
KernelWriteSRs(table); KernelWriteSRs(table);
} }
void readAndPrintSegmentRegister(CThread *thread, void *arg) { void readAndPrintSegmentRegister(CThread *thread, void *arg) {
uint16_t core = OSGetThreadAffinity(OSGetCurrentThread()); uint16_t core = OSGetThreadAffinity(OSGetCurrentThread());
DEBUG_FUNCTION_LINE("Reading segment register and page table from core %d",core); DEBUG_FUNCTION_LINE("Reading segment register and page table from core %d", core);
sr_table_t srTable; sr_table_t srTable;
memset(&srTable,0,sizeof(srTable)); memset(&srTable, 0, sizeof(srTable));
KernelReadSRs(&srTable); KernelReadSRs(&srTable);
DCFlushRange(&srTable,sizeof(srTable)); DCFlushRange(&srTable, sizeof(srTable));
for(int32_t i = 0; i < 16; i++) { for (int32_t i = 0; i < 16; i++) {
DEBUG_FUNCTION_LINE("[%d] SR[%d]=%08X",core,i,srTable.value[i]); DEBUG_FUNCTION_LINE("[%d] SR[%d]=%08X", core, i, srTable.value[i]);
} }
uint32_t pageTable[0x8000]; uint32_t pageTable[0x8000];
memset(pageTable,0,sizeof(pageTable)); memset(pageTable, 0, sizeof(pageTable));
DEBUG_FUNCTION_LINE("Reading pageTable now."); DEBUG_FUNCTION_LINE("Reading pageTable now.");
KernelReadPTE((uint32_t) pageTable,sizeof(pageTable)); KernelReadPTE((uint32_t) pageTable, sizeof(pageTable));
DCFlushRange(pageTable,sizeof(pageTable)); DCFlushRange(pageTable, sizeof(pageTable));
DEBUG_FUNCTION_LINE("Reading pageTable done"); DEBUG_FUNCTION_LINE("Reading pageTable done");
MemoryMapping::printPageTableTranslation(srTable,pageTable); MemoryMapping::printPageTableTranslation(srTable, pageTable);
DEBUG_FUNCTION_LINE("-----------------------------"); DEBUG_FUNCTION_LINE("-----------------------------");
} }
bool MemoryMapping::isMemoryMapped() { bool MemoryMapping::isMemoryMapped() {
sr_table_t srTable; sr_table_t srTable;
memset(&srTable,0,sizeof(srTable)); memset(&srTable, 0, sizeof(srTable));
KernelReadSRs(&srTable); KernelReadSRs(&srTable);
if((srTable.value[MEMORY_START_BASE >> 28] & 0x00FFFFFF) == SEGMENT_UNIQUE_ID) { if ((srTable.value[MEMORY_START_BASE >> 28] & 0x00FFFFFF) == SEGMENT_UNIQUE_ID) {
return true; return true;
} }
return false; return false;
@ -73,57 +73,57 @@ bool MemoryMapping::isMemoryMapped() {
void MemoryMapping::searchEmptyMemoryRegions() { void MemoryMapping::searchEmptyMemoryRegions() {
DEBUG_FUNCTION_LINE("Searching for empty memory."); DEBUG_FUNCTION_LINE("Searching for empty memory.");
for(int32_t i = 0;; i++) { for (int32_t i = 0;; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
uint32_t ea_start_address = mem_mapping[i].effective_start_address; uint32_t ea_start_address = mem_mapping[i].effective_start_address;
const memory_values_t * mem_vals = mem_mapping[i].physical_addresses; const memory_values_t *mem_vals = mem_mapping[i].physical_addresses;
uint32_t ea_size = 0; uint32_t ea_size = 0;
for(uint32_t j = 0;; j++) { for (uint32_t j = 0;; j++) {
uint32_t pa_start_address = mem_vals[j].start_address; uint32_t pa_start_address = mem_vals[j].start_address;
uint32_t pa_end_address = mem_vals[j].end_address; uint32_t pa_end_address = mem_vals[j].end_address;
if(pa_end_address == 0 && pa_start_address == 0) { if (pa_end_address == 0 && pa_start_address == 0) {
break; break;
} }
ea_size += pa_end_address - pa_start_address; ea_size += pa_end_address - pa_start_address;
} }
uint32_t* flush_start = (uint32_t*)ea_start_address; uint32_t *flush_start = (uint32_t *) ea_start_address;
uint32_t flush_size = ea_size; uint32_t flush_size = ea_size;
DEBUG_FUNCTION_LINE("Flushing %08X (%d kB) at %08X.",flush_size,flush_size/1024, flush_start); DEBUG_FUNCTION_LINE("Flushing %08X (%d kB) at %08X.", flush_size, flush_size / 1024, flush_start);
DCFlushRange(flush_start,flush_size); DCFlushRange(flush_start, flush_size);
DEBUG_FUNCTION_LINE("Searching in memory region %d. 0x%08X - 0x%08X. Size 0x%08X (%d KBytes).",i+1,ea_start_address,ea_start_address+ea_size,ea_size,ea_size/1024); DEBUG_FUNCTION_LINE("Searching in memory region %d. 0x%08X - 0x%08X. Size 0x%08X (%d KBytes).", i + 1, ea_start_address, ea_start_address + ea_size, ea_size, ea_size / 1024);
bool success = true; bool success = true;
uint32_t * memory_ptr = (uint32_t*) ea_start_address; uint32_t *memory_ptr = (uint32_t *) ea_start_address;
bool inFailRange = false; bool inFailRange = false;
uint32_t startFailing = 0; uint32_t startFailing = 0;
uint32_t startGood = ea_start_address; uint32_t startGood = ea_start_address;
for(uint32_t j=0; j < ea_size/4; j++) { for (uint32_t j = 0; j < ea_size / 4; j++) {
if(memory_ptr[j] != 0) { if (memory_ptr[j] != 0) {
success = false; success = false;
if(!success && !inFailRange) { if (!success && !inFailRange) {
if((((uint32_t)&memory_ptr[j])-(uint32_t)startGood)/1024 > 512) { if ((((uint32_t) &memory_ptr[j]) - (uint32_t) startGood) / 1024 > 512) {
uint32_t start_addr = startGood & 0xFFFE0000; uint32_t start_addr = startGood & 0xFFFE0000;
if(start_addr != startGood) { if (start_addr != startGood) {
start_addr += 0x20000; start_addr += 0x20000;
} }
uint32_t end_addr = ((uint32_t)&memory_ptr[j]) - MEMORY_START_BASE; uint32_t end_addr = ((uint32_t) &memory_ptr[j]) - MEMORY_START_BASE;
end_addr = (end_addr & 0xFFFE0000); end_addr = (end_addr & 0xFFFE0000);
DEBUG_FUNCTION_LINE("+ Free between 0x%08X and 0x%08X size: %u kB",start_addr - MEMORY_START_BASE,end_addr,(((uint32_t)end_addr)-((uint32_t)startGood - MEMORY_START_BASE))/1024); DEBUG_FUNCTION_LINE("+ Free between 0x%08X and 0x%08X size: %u kB", start_addr - MEMORY_START_BASE, end_addr, (((uint32_t) end_addr) - ((uint32_t) startGood - MEMORY_START_BASE)) / 1024);
} }
startFailing = (uint32_t)&memory_ptr[j]; startFailing = (uint32_t) &memory_ptr[j];
inFailRange = true; inFailRange = true;
startGood = 0; startGood = 0;
j = ((j & 0xFFFF8000) + 0x00008000)-1; j = ((j & 0xFFFF8000) + 0x00008000) - 1;
} }
//break; //break;
} else { } else {
if(inFailRange) { if (inFailRange) {
//DEBUG_FUNCTION_LINE("- Error between 0x%08X and 0x%08X size: %u kB",startFailing,&memory_ptr[j],(((uint32_t)&memory_ptr[j])-(uint32_t)startFailing)/1024); //DEBUG_FUNCTION_LINE("- Error between 0x%08X and 0x%08X size: %u kB",startFailing,&memory_ptr[j],(((uint32_t)&memory_ptr[j])-(uint32_t)startFailing)/1024);
startFailing = 0; startFailing = 0;
startGood = (uint32_t) &memory_ptr[j]; startGood = (uint32_t) &memory_ptr[j];
@ -131,13 +131,14 @@ void MemoryMapping::searchEmptyMemoryRegions() {
} }
} }
} }
if(startGood != 0 && (startGood != ea_start_address + ea_size)) { if (startGood != 0 && (startGood != ea_start_address + ea_size)) {
DEBUG_FUNCTION_LINE("+ Good between 0x%08X and 0x%08X size: %u kB",startGood - MEMORY_START_BASE,((uint32_t)(ea_start_address + ea_size) - (uint32_t)MEMORY_START_BASE),((uint32_t)(ea_start_address + ea_size) - (uint32_t)startGood)/1024); DEBUG_FUNCTION_LINE("+ Good between 0x%08X and 0x%08X size: %u kB", startGood - MEMORY_START_BASE, ((uint32_t) (ea_start_address + ea_size) - (uint32_t) MEMORY_START_BASE),
} else if(inFailRange) { ((uint32_t) (ea_start_address + ea_size) - (uint32_t) startGood) / 1024);
DEBUG_FUNCTION_LINE("- Used between 0x%08X and 0x%08X size: %u kB",startFailing,ea_start_address + ea_size,((uint32_t)(ea_start_address + ea_size) - (uint32_t)startFailing)/1024); } else if (inFailRange) {
DEBUG_FUNCTION_LINE("- Used between 0x%08X and 0x%08X size: %u kB", startFailing, ea_start_address + ea_size, ((uint32_t) (ea_start_address + ea_size) - (uint32_t) startFailing) / 1024);
} }
if(success) { if (success) {
DEBUG_FUNCTION_LINE("Test %d was successful!",i+1); DEBUG_FUNCTION_LINE("Test %d was successful!", i + 1);
} }
} }
@ -149,140 +150,140 @@ void MemoryMapping::writeTestValuesToMemory() {
uint32_t chunk_size = 0x1000; uint32_t chunk_size = 0x1000;
uint32_t testBuffer[chunk_size]; uint32_t testBuffer[chunk_size];
for(int32_t i = 0;; i++) { for (int32_t i = 0;; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
uint32_t cur_ea_start_address = mem_mapping[i].effective_start_address; uint32_t cur_ea_start_address = mem_mapping[i].effective_start_address;
DEBUG_FUNCTION_LINE("Preparing memory test for region %d. Region start at effective address %08X.",i+1,cur_ea_start_address); DEBUG_FUNCTION_LINE("Preparing memory test for region %d. Region start at effective address %08X.", i + 1, cur_ea_start_address);
const memory_values_t * mem_vals = mem_mapping[i].physical_addresses; const memory_values_t *mem_vals = mem_mapping[i].physical_addresses;
uint32_t counter = 0; uint32_t counter = 0;
for(uint32_t j = 0;; j++) { for (uint32_t j = 0;; j++) {
uint32_t pa_start_address = mem_vals[j].start_address; uint32_t pa_start_address = mem_vals[j].start_address;
uint32_t pa_end_address = mem_vals[j].end_address; uint32_t pa_end_address = mem_vals[j].end_address;
if(pa_end_address == 0 && pa_start_address == 0) { if (pa_end_address == 0 && pa_start_address == 0) {
break; break;
} }
uint32_t pa_size = pa_end_address - pa_start_address; uint32_t pa_size = pa_end_address - pa_start_address;
DEBUG_FUNCTION_LINE("Writing region %d of mapping %d. From %08X to %08X Size: %d KBytes...",j+1,i+1,pa_start_address,pa_end_address,pa_size/1024); DEBUG_FUNCTION_LINE("Writing region %d of mapping %d. From %08X to %08X Size: %d KBytes...", j + 1, i + 1, pa_start_address, pa_end_address, pa_size / 1024);
for(uint32_t k=0; k<=pa_size/4; k++) { for (uint32_t k = 0; k <= pa_size / 4; k++) {
if(k > 0 && (k % chunk_size) == 0) { if (k > 0 && (k % chunk_size) == 0) {
DCFlushRange(&testBuffer,sizeof(testBuffer)); DCFlushRange(&testBuffer, sizeof(testBuffer));
DCInvalidateRange(&testBuffer,sizeof(testBuffer)); DCInvalidateRange(&testBuffer, sizeof(testBuffer));
uint32_t destination = pa_start_address + ((k*4) - sizeof(testBuffer)); uint32_t destination = pa_start_address + ((k * 4) - sizeof(testBuffer));
KernelCopyData(destination,(uint32_t)OSEffectiveToPhysical((uint32_t)testBuffer),sizeof(testBuffer)); KernelCopyData(destination, (uint32_t) OSEffectiveToPhysical((uint32_t) testBuffer), sizeof(testBuffer));
//DEBUG_FUNCTION_LINE("Copy testBuffer into %08X",destination); //DEBUG_FUNCTION_LINE("Copy testBuffer into %08X",destination);
} }
if(k != pa_size/4) { if (k != pa_size / 4) {
testBuffer[k % chunk_size] = counter++; testBuffer[k % chunk_size] = counter++;
} }
//DEBUG_FUNCTION_LINE("testBuffer[%d] = %d",i % chunk_size,i); //DEBUG_FUNCTION_LINE("testBuffer[%d] = %d",i % chunk_size,i);
} }
uint32_t* flush_start = (uint32_t*)cur_ea_start_address; uint32_t *flush_start = (uint32_t *) cur_ea_start_address;
uint32_t flush_size = pa_size; uint32_t flush_size = pa_size;
cur_ea_start_address += pa_size; cur_ea_start_address += pa_size;
DEBUG_FUNCTION_LINE("Flushing %08X (%d kB) at %08X to map memory.",flush_size,flush_size/1024, flush_start); DEBUG_FUNCTION_LINE("Flushing %08X (%d kB) at %08X to map memory.", flush_size, flush_size / 1024, flush_start);
DCFlushRange(flush_start,flush_size); DCFlushRange(flush_start, flush_size);
} }
DEBUG_FUNCTION_LINE("Done writing region %d",i+1); DEBUG_FUNCTION_LINE("Done writing region %d", i + 1);
} }
} }
void MemoryMapping::readTestValuesFromMemory() { void MemoryMapping::readTestValuesFromMemory() {
DEBUG_FUNCTION_LINE("Testing reading the written values."); DEBUG_FUNCTION_LINE("Testing reading the written values.");
for(int32_t i = 0;; i++) { for (int32_t i = 0;; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
uint32_t ea_start_address = mem_mapping[i].effective_start_address; uint32_t ea_start_address = mem_mapping[i].effective_start_address;
const memory_values_t * mem_vals = mem_mapping[i].physical_addresses; const memory_values_t *mem_vals = mem_mapping[i].physical_addresses;
//uint32_t counter = 0; //uint32_t counter = 0;
uint32_t ea_size = 0; uint32_t ea_size = 0;
for(uint32_t j = 0;; j++) { for (uint32_t j = 0;; j++) {
uint32_t pa_start_address = mem_vals[j].start_address; uint32_t pa_start_address = mem_vals[j].start_address;
uint32_t pa_end_address = mem_vals[j].end_address; uint32_t pa_end_address = mem_vals[j].end_address;
if(pa_end_address == 0 && pa_start_address == 0) { if (pa_end_address == 0 && pa_start_address == 0) {
break; break;
} }
ea_size += pa_end_address - pa_start_address; ea_size += pa_end_address - pa_start_address;
} }
uint32_t* flush_start = (uint32_t*)ea_start_address; uint32_t *flush_start = (uint32_t *) ea_start_address;
uint32_t flush_size = ea_size; uint32_t flush_size = ea_size;
DEBUG_FUNCTION_LINE("Flushing %08X (%d kB) at %08X to map memory.",flush_size,flush_size/1024, flush_start); DEBUG_FUNCTION_LINE("Flushing %08X (%d kB) at %08X to map memory.", flush_size, flush_size / 1024, flush_start);
DCFlushRange(flush_start,flush_size); DCFlushRange(flush_start, flush_size);
DEBUG_FUNCTION_LINE("Testing memory region %d. 0x%08X - 0x%08X. Size 0x%08X (%d KBytes).",i+1,ea_start_address,ea_start_address+ea_size,ea_size,ea_size/1024); DEBUG_FUNCTION_LINE("Testing memory region %d. 0x%08X - 0x%08X. Size 0x%08X (%d KBytes).", i + 1, ea_start_address, ea_start_address + ea_size, ea_size, ea_size / 1024);
bool success = true; bool success = true;
uint32_t * memory_ptr = (uint32_t*) ea_start_address; uint32_t *memory_ptr = (uint32_t *) ea_start_address;
bool inFailRange = false; bool inFailRange = false;
uint32_t startFailing = 0; uint32_t startFailing = 0;
uint32_t startGood = ea_start_address; uint32_t startGood = ea_start_address;
for(uint32_t j=0; j < ea_size/4; j++) { for (uint32_t j = 0; j < ea_size / 4; j++) {
if(memory_ptr[j] != j) { if (memory_ptr[j] != j) {
success = false; success = false;
if(!success && !inFailRange) { if (!success && !inFailRange) {
DEBUG_FUNCTION_LINE("+ Good between 0x%08X and 0x%08X size: %u kB",startGood,&memory_ptr[j],(((uint32_t)&memory_ptr[j])-(uint32_t)startGood)/1024); DEBUG_FUNCTION_LINE("+ Good between 0x%08X and 0x%08X size: %u kB", startGood, &memory_ptr[j], (((uint32_t) &memory_ptr[j]) - (uint32_t) startGood) / 1024);
startFailing = (uint32_t)&memory_ptr[j]; startFailing = (uint32_t) &memory_ptr[j];
inFailRange = true; inFailRange = true;
startGood = 0; startGood = 0;
j = ((j & 0xFFFF8000) + 0x00008000)-1; j = ((j & 0xFFFF8000) + 0x00008000) - 1;
} }
//break; //break;
} else { } else {
if(inFailRange) { if (inFailRange) {
DEBUG_FUNCTION_LINE("- Error between 0x%08X and 0x%08X size: %u kB",startFailing,&memory_ptr[j],(((uint32_t)&memory_ptr[j])-(uint32_t)startFailing)/1024); DEBUG_FUNCTION_LINE("- Error between 0x%08X and 0x%08X size: %u kB", startFailing, &memory_ptr[j], (((uint32_t) &memory_ptr[j]) - (uint32_t) startFailing) / 1024);
startFailing = 0; startFailing = 0;
startGood = (uint32_t) &memory_ptr[j]; startGood = (uint32_t) &memory_ptr[j];
inFailRange = false; inFailRange = false;
} }
} }
} }
if(startGood != 0 && (startGood != ea_start_address + ea_size)) { if (startGood != 0 && (startGood != ea_start_address + ea_size)) {
DEBUG_FUNCTION_LINE("+ Good between 0x%08X and 0x%08X size: %u kB",startGood,ea_start_address + ea_size,((uint32_t)(ea_start_address + ea_size) - (uint32_t)startGood)/1024); DEBUG_FUNCTION_LINE("+ Good between 0x%08X and 0x%08X size: %u kB", startGood, ea_start_address + ea_size, ((uint32_t) (ea_start_address + ea_size) - (uint32_t) startGood) / 1024);
} else if(inFailRange) { } else if (inFailRange) {
DEBUG_FUNCTION_LINE("- Error between 0x%08X and 0x%08X size: %u kB",startFailing,ea_start_address + ea_size,((uint32_t)(ea_start_address + ea_size) - (uint32_t)startFailing)/1024); DEBUG_FUNCTION_LINE("- Error between 0x%08X and 0x%08X size: %u kB", startFailing, ea_start_address + ea_size, ((uint32_t) (ea_start_address + ea_size) - (uint32_t) startFailing) / 1024);
} }
if(success) { if (success) {
DEBUG_FUNCTION_LINE("Test %d was successful!",i+1); DEBUG_FUNCTION_LINE("Test %d was successful!", i + 1);
} }
} }
DEBUG_FUNCTION_LINE("All tests done."); DEBUG_FUNCTION_LINE("All tests done.");
} }
void MemoryMapping::memoryMappingForRegions(const memory_mapping_t * memory_mapping, sr_table_t SRTable, uint32_t * translation_table) { void MemoryMapping::memoryMappingForRegions(const memory_mapping_t *memory_mapping, sr_table_t SRTable, uint32_t *translation_table) {
for(int32_t i = 0; /* waiting for a break */; i++) { for (int32_t i = 0; /* waiting for a break */; i++) {
//DEBUG_FUNCTION_LINE("In loop %d",i); //DEBUG_FUNCTION_LINE("In loop %d",i);
if(memory_mapping[i].physical_addresses == NULL) { if (memory_mapping[i].physical_addresses == NULL) {
//DEBUG_FUNCTION_LINE("break %d",i); //DEBUG_FUNCTION_LINE("break %d",i);
break; break;
} }
uint32_t cur_ea_start_address = memory_mapping[i].effective_start_address; uint32_t cur_ea_start_address = memory_mapping[i].effective_start_address;
DEBUG_FUNCTION_LINE("Mapping area %d. effective address %08X...",i+1,cur_ea_start_address); DEBUG_FUNCTION_LINE("Mapping area %d. effective address %08X...", i + 1, cur_ea_start_address);
const memory_values_t * mem_vals = memory_mapping[i].physical_addresses; const memory_values_t *mem_vals = memory_mapping[i].physical_addresses;
for(uint32_t j = 0;; j++) { for (uint32_t j = 0;; j++) {
//DEBUG_FUNCTION_LINE("In inner loop %d",j); //DEBUG_FUNCTION_LINE("In inner loop %d",j);
uint32_t pa_start_address = mem_vals[j].start_address; uint32_t pa_start_address = mem_vals[j].start_address;
uint32_t pa_end_address = mem_vals[j].end_address; uint32_t pa_end_address = mem_vals[j].end_address;
if(pa_end_address == 0 && pa_start_address == 0) { if (pa_end_address == 0 && pa_start_address == 0) {
//DEBUG_FUNCTION_LINE("inner break %d",j); //DEBUG_FUNCTION_LINE("inner break %d",j);
// Break if entry was empty. // Break if entry was empty.
break; break;
} }
uint32_t pa_size = pa_end_address - pa_start_address; uint32_t pa_size = pa_end_address - pa_start_address;
DEBUG_FUNCTION_LINE("Adding page table entry %d for mapping area %d. %08X-%08X => %08X-%08X...",j+1,i+1,cur_ea_start_address,memory_mapping[i].effective_start_address+pa_size,pa_start_address,pa_end_address); DEBUG_FUNCTION_LINE("Adding page table entry %d for mapping area %d. %08X-%08X => %08X-%08X...", j + 1, i + 1, cur_ea_start_address, memory_mapping[i].effective_start_address + pa_size, pa_start_address, pa_end_address);
if(!mapMemory(pa_start_address,pa_end_address,cur_ea_start_address,SRTable,translation_table)) { if (!mapMemory(pa_start_address, pa_end_address, cur_ea_start_address, SRTable, translation_table)) {
//log_print("error =("); //log_print("error =(");
DEBUG_FUNCTION_LINE("Failed to map memory."); DEBUG_FUNCTION_LINE("Failed to map memory.");
//OSFatal("Failed to map memory."); //OSFatal("Failed to map memory.");
@ -307,13 +308,13 @@ void MemoryMapping::setupMemoryMapping() {
uint32_t pageTableCpy[0x8000]; uint32_t pageTableCpy[0x8000];
KernelReadSRs(&srTableCpy); KernelReadSRs(&srTableCpy);
KernelReadPTE((uint32_t) pageTableCpy,sizeof(pageTableCpy)); KernelReadPTE((uint32_t) pageTableCpy, sizeof(pageTableCpy));
DCFlushRange(&srTableCpy,sizeof(srTableCpy)); DCFlushRange(&srTableCpy, sizeof(srTableCpy));
DCFlushRange(pageTableCpy,sizeof(pageTableCpy)); DCFlushRange(pageTableCpy, sizeof(pageTableCpy));
for(int32_t i = 0; i < 16; i++) { for (int32_t i = 0; i < 16; i++) {
DEBUG_FUNCTION_LINE("SR[%d]=%08X",i,srTableCpy.value[i]); DEBUG_FUNCTION_LINE("SR[%d]=%08X", i, srTableCpy.value[i]);
} }
//printPageTableTranslation(srTableCpy,pageTableCpy); //printPageTableTranslation(srTableCpy,pageTableCpy);
@ -326,25 +327,25 @@ void MemoryMapping::setupMemoryMapping() {
uint32_t segment_index = MEMORY_START_BASE >> 28; uint32_t segment_index = MEMORY_START_BASE >> 28;
uint32_t segment_content = 0x00000000 | SEGMENT_UNIQUE_ID; uint32_t segment_content = 0x00000000 | SEGMENT_UNIQUE_ID;
DEBUG_FUNCTION_LINE("Setting SR[%d] to %08X",segment_index,segment_content); DEBUG_FUNCTION_LINE("Setting SR[%d] to %08X", segment_index, segment_content);
srTableCpy.value[segment_index] = segment_content; srTableCpy.value[segment_index] = segment_content;
DCFlushRange(&srTableCpy,sizeof(srTableCpy)); DCFlushRange(&srTableCpy, sizeof(srTableCpy));
DEBUG_FUNCTION_LINE("Writing segment registers...",segment_index,segment_content); DEBUG_FUNCTION_LINE("Writing segment registers...", segment_index, segment_content);
// Writing the segment registers to ALL cores. // Writing the segment registers to ALL cores.
// //
//writeSegmentRegister(NULL, &srTableCpy); //writeSegmentRegister(NULL, &srTableCpy);
runOnAllCores(writeSegmentRegister,&srTableCpy); runOnAllCores(writeSegmentRegister, &srTableCpy);
memoryMappingForRegions(mem_mapping,srTableCpy,pageTableCpy); memoryMappingForRegions(mem_mapping, srTableCpy, pageTableCpy);
//printPageTableTranslation(srTableCpy,pageTableCpy); //printPageTableTranslation(srTableCpy,pageTableCpy);
DEBUG_FUNCTION_LINE("Writing PageTable... "); DEBUG_FUNCTION_LINE("Writing PageTable... ");
DCFlushRange(pageTableCpy,sizeof(pageTableCpy)); DCFlushRange(pageTableCpy, sizeof(pageTableCpy));
KernelWritePTE((uint32_t) pageTableCpy,sizeof(pageTableCpy)); KernelWritePTE((uint32_t) pageTableCpy, sizeof(pageTableCpy));
DCFlushRange(pageTableCpy,sizeof(pageTableCpy)); DCFlushRange(pageTableCpy, sizeof(pageTableCpy));
DEBUG_FUNCTION_LINE("done"); DEBUG_FUNCTION_LINE("done");
//printPageTableTranslation(srTableCpy,pageTableCpy); //printPageTableTranslation(srTableCpy,pageTableCpy);
@ -359,10 +360,10 @@ void MemoryMapping::setupMemoryMapping() {
//runOnAllCores(writeSegmentRegister,&srTableCpy); //runOnAllCores(writeSegmentRegister,&srTableCpy);
} }
void* MemoryMapping::alloc(uint32_t size, uint32_t align){ void *MemoryMapping::alloc(uint32_t size, uint32_t align) {
void* res = NULL; void *res = NULL;
for(int32_t i = 0; /* waiting for a break */; i++) { for (int32_t i = 0; /* waiting for a break */; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
res = MEMAllocFromExpHeapEx((MEMHeapHandle) mem_mapping[i].effective_start_address, size, align); res = MEMAllocFromExpHeapEx((MEMHeapHandle) mem_mapping[i].effective_start_address, size, align);
@ -373,16 +374,16 @@ void* MemoryMapping::alloc(uint32_t size, uint32_t align){
return res; return res;
} }
void MemoryMapping::free(void* ptr){ void MemoryMapping::free(void *ptr) {
if(ptr == NULL){ if (ptr == NULL) {
return; return;
} }
uint32_t ptr_val = (uint32_t) ptr; uint32_t ptr_val = (uint32_t) ptr;
for(int32_t i = 0; /* waiting for a break */; i++) { for (int32_t i = 0; /* waiting for a break */; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
if(ptr_val > mem_mapping[i].effective_start_address && ptr_val < mem_mapping[i].effective_end_address){ if (ptr_val > mem_mapping[i].effective_start_address && ptr_val < mem_mapping[i].effective_end_address) {
MEMFreeToExpHeap((MEMHeapHandle) mem_mapping[i].effective_start_address, ptr); MEMFreeToExpHeap((MEMHeapHandle) mem_mapping[i].effective_start_address, ptr);
break; break;
} }
@ -391,13 +392,13 @@ void MemoryMapping::free(void* ptr){
uint32_t MemoryMapping::GetFreeSpace() { uint32_t MemoryMapping::GetFreeSpace() {
uint32_t res = 0; uint32_t res = 0;
for(int32_t i = 0; /* waiting for a break */; i++) { for (int32_t i = 0; /* waiting for a break */; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
uint32_t curRes = MEMGetTotalFreeSizeForExpHeap((MEMHeapHandle) mem_mapping[i].effective_start_address); uint32_t curRes = MEMGetTotalFreeSizeForExpHeap((MEMHeapHandle) mem_mapping[i].effective_start_address);
DEBUG_FUNCTION_LINE("heap at %08X MEMGetTotalFreeSizeForExpHeap: %d KiB",mem_mapping[i].effective_start_address, curRes/1024 ); DEBUG_FUNCTION_LINE("heap at %08X MEMGetTotalFreeSizeForExpHeap: %d KiB", mem_mapping[i].effective_start_address, curRes / 1024);
res+=curRes; res += curRes;
} }
return res; return res;
} }
@ -432,12 +433,12 @@ uint32_t MemoryMapping::getAreaSizeFromPageTable(uint32_t start, uint32_t maxSiz
uint32_t pageTable[0x8000]; uint32_t pageTable[0x8000];
KernelReadSRs(&srTable); KernelReadSRs(&srTable);
KernelReadPTE((uint32_t) pageTable,sizeof(pageTable)); KernelReadPTE((uint32_t) pageTable, sizeof(pageTable));
uint32_t sr_start = start >> 28; uint32_t sr_start = start >> 28;
uint32_t sr_end = (start + maxSize) >> 28; uint32_t sr_end = (start + maxSize) >> 28;
if(sr_end < sr_start) { if (sr_end < sr_start) {
return 0; return 0;
} }
@ -446,35 +447,35 @@ uint32_t MemoryMapping::getAreaSizeFromPageTable(uint32_t start, uint32_t maxSiz
uint32_t memSize = 0; uint32_t memSize = 0;
for(uint32_t segment = sr_start; segment <= sr_end ; segment++) { for (uint32_t segment = sr_start; segment <= sr_end; segment++) {
uint32_t sr = srTable.value[segment]; uint32_t sr = srTable.value[segment];
if(sr >> 31) { if (sr >> 31) {
DEBUG_FUNCTION_LINE("Direct access not supported"); DEBUG_FUNCTION_LINE("Direct access not supported");
} else { } else {
uint32_t vsid = sr & 0xFFFFFF; uint32_t vsid = sr & 0xFFFFFF;
uint32_t pageSize = 1 << PAGE_INDEX_SHIFT; uint32_t pageSize = 1 << PAGE_INDEX_SHIFT;
uint32_t cur_end_addr = 0; uint32_t cur_end_addr = 0;
if(segment == sr_end) { if (segment == sr_end) {
cur_end_addr = end_address; cur_end_addr = end_address;
} else { } else {
cur_end_addr = (segment + 1) * 0x10000000; cur_end_addr = (segment + 1) * 0x10000000;
} }
if(segment != sr_start) { if (segment != sr_start) {
cur_address = (segment) * 0x10000000; cur_address = (segment) * 0x10000000;
} }
bool success = true; bool success = true;
for(uint32_t addr = cur_address; addr < cur_end_addr; addr += pageSize) { for (uint32_t addr = cur_address; addr < cur_end_addr; addr += pageSize) {
uint32_t PTEH = 0; uint32_t PTEH = 0;
uint32_t PTEL = 0; uint32_t PTEL = 0;
if(getPageEntryForAddress(srTable.sdr1, addr, vsid, pageTable, &PTEH, &PTEL, false)) { if (getPageEntryForAddress(srTable.sdr1, addr, vsid, pageTable, &PTEH, &PTEL, false)) {
memSize += pageSize; memSize += pageSize;
} else { } else {
success = false; success = false;
break; break;
} }
} }
if(!success) { if (!success) {
break; break;
} }
} }
@ -482,17 +483,17 @@ uint32_t MemoryMapping::getAreaSizeFromPageTable(uint32_t start, uint32_t maxSiz
return memSize; return memSize;
} }
bool MemoryMapping::getPageEntryForAddress(uint32_t SDR1,uint32_t addr, uint32_t vsid, uint32_t * translation_table,uint32_t* oPTEH, uint32_t* oPTEL, bool checkSecondHash) { bool MemoryMapping::getPageEntryForAddress(uint32_t SDR1, uint32_t addr, uint32_t vsid, uint32_t *translation_table, uint32_t *oPTEH, uint32_t *oPTEL, bool checkSecondHash) {
uint32_t pageMask = SDR1 & 0x1FF; uint32_t pageMask = SDR1 & 0x1FF;
uint32_t pageIndex = (addr >> PAGE_INDEX_SHIFT) & PAGE_INDEX_MASK; uint32_t pageIndex = (addr >> PAGE_INDEX_SHIFT) & PAGE_INDEX_MASK;
uint32_t primaryHash = (vsid & 0x7FFFF) ^ pageIndex; uint32_t primaryHash = (vsid & 0x7FFFF) ^pageIndex;
if(getPageEntryForAddressEx(SDR1, addr, vsid, primaryHash, translation_table, oPTEH, oPTEL, 0)) { if (getPageEntryForAddressEx(SDR1, addr, vsid, primaryHash, translation_table, oPTEH, oPTEL, 0)) {
return true; return true;
} }
if(checkSecondHash) { if (checkSecondHash) {
if(getPageEntryForAddressEx(pageMask, addr, vsid, ~primaryHash, translation_table, oPTEH, oPTEL, 1)) { if (getPageEntryForAddressEx(pageMask, addr, vsid, ~primaryHash, translation_table, oPTEH, oPTEL, 1)) {
return true; return true;
} }
} }
@ -500,7 +501,7 @@ bool MemoryMapping::getPageEntryForAddress(uint32_t SDR1,uint32_t addr, uint32_t
return false; return false;
} }
bool MemoryMapping::getPageEntryForAddressEx(uint32_t pageMask, uint32_t addr, uint32_t vsid, uint32_t primaryHash, uint32_t * translation_table,uint32_t* oPTEH, uint32_t* oPTEL,uint32_t H) { bool MemoryMapping::getPageEntryForAddressEx(uint32_t pageMask, uint32_t addr, uint32_t vsid, uint32_t primaryHash, uint32_t *translation_table, uint32_t *oPTEH, uint32_t *oPTEL, uint32_t H) {
uint32_t maskedHash = primaryHash & ((pageMask << 10) | 0x3FF); uint32_t maskedHash = primaryHash & ((pageMask << 10) | 0x3FF);
uint32_t api = (addr >> 22) & 0x3F; uint32_t api = (addr >> 22) & 0x3F;
@ -549,17 +550,17 @@ bool MemoryMapping::getPageEntryForAddressEx(uint32_t pageMask, uint32_t addr, u
return false; return false;
} }
void MemoryMapping::printPageTableTranslation(sr_table_t srTable, uint32_t * translation_table) { void MemoryMapping::printPageTableTranslation(sr_table_t srTable, uint32_t *translation_table) {
uint32_t SDR1 = srTable.sdr1; uint32_t SDR1 = srTable.sdr1;
pageInformation current; pageInformation current;
memset(&current,0,sizeof(current)); memset(&current, 0, sizeof(current));
std::vector<pageInformation> pageInfos; std::vector<pageInformation> pageInfos;
for(uint32_t segment = 0; segment < 16 ; segment++) { for (uint32_t segment = 0; segment < 16; segment++) {
uint32_t sr = srTable.value[segment]; uint32_t sr = srTable.value[segment];
if(sr >> 31) { if (sr >> 31) {
DEBUG_FUNCTION_LINE("Direct access not supported"); DEBUG_FUNCTION_LINE("Direct access not supported");
} else { } else {
uint32_t ks = (sr >> 30) & 1; uint32_t ks = (sr >> 30) & 1;
@ -567,18 +568,18 @@ void MemoryMapping::printPageTableTranslation(sr_table_t srTable, uint32_t * tra
uint32_t nx = (sr >> 28) & 1; uint32_t nx = (sr >> 28) & 1;
uint32_t vsid = sr & 0xFFFFFF; uint32_t vsid = sr & 0xFFFFFF;
DEBUG_FUNCTION_LINE("ks %08X kp %08X nx %08X vsid %08X",ks,kp,nx,vsid); DEBUG_FUNCTION_LINE("ks %08X kp %08X nx %08X vsid %08X", ks, kp, nx, vsid);
uint32_t pageSize = 1 << PAGE_INDEX_SHIFT; uint32_t pageSize = 1 << PAGE_INDEX_SHIFT;
for(uint32_t addr = segment * 0x10000000; addr < (segment + 1) * 0x10000000; addr += pageSize) { for (uint32_t addr = segment * 0x10000000; addr < (segment + 1) * 0x10000000; addr += pageSize) {
uint32_t PTEH = 0; uint32_t PTEH = 0;
uint32_t PTEL = 0; uint32_t PTEL = 0;
if(getPageEntryForAddress(SDR1, addr, vsid, translation_table, &PTEH, &PTEL, false)) { if (getPageEntryForAddress(SDR1, addr, vsid, translation_table, &PTEH, &PTEL, false)) {
uint32_t pp = PTEL & 3; uint32_t pp = PTEL & 3;
uint32_t phys = PTEL & 0xFFFFF000; uint32_t phys = PTEL & 0xFFFFF000;
//DEBUG_FUNCTION_LINE("current.phys == phys - current.size ( %08X %08X)",current.phys, phys - current.size); //DEBUG_FUNCTION_LINE("current.phys == phys - current.size ( %08X %08X)",current.phys, phys - current.size);
if( current.ks == ks && if (current.ks == ks &&
current.kp == kp && current.kp == kp &&
current.nx == nx && current.nx == nx &&
current.pp == pp && current.pp == pp &&
@ -587,14 +588,14 @@ void MemoryMapping::printPageTableTranslation(sr_table_t srTable, uint32_t * tra
current.size += pageSize; current.size += pageSize;
//DEBUG_FUNCTION_LINE("New size of %08X is %08X",current.addr,current.size); //DEBUG_FUNCTION_LINE("New size of %08X is %08X",current.addr,current.size);
} else { } else {
if(current.addr != 0 && current.size != 0) { if (current.addr != 0 && current.size != 0) {
/*DEBUG_FUNCTION_LINE("Saving old block from %08X",current.addr); /*DEBUG_FUNCTION_LINE("Saving old block from %08X",current.addr);
DEBUG_FUNCTION_LINE("ks %08X new %08X",current.ks,ks); DEBUG_FUNCTION_LINE("ks %08X new %08X",current.ks,ks);
DEBUG_FUNCTION_LINE("kp %08X new %08X",current.kp,kp); DEBUG_FUNCTION_LINE("kp %08X new %08X",current.kp,kp);
DEBUG_FUNCTION_LINE("nx %08X new %08X",current.nx,nx); DEBUG_FUNCTION_LINE("nx %08X new %08X",current.nx,nx);
DEBUG_FUNCTION_LINE("pp %08X new %08X",current.pp,pp);*/ DEBUG_FUNCTION_LINE("pp %08X new %08X",current.pp,pp);*/
pageInfos.push_back(current); pageInfos.push_back(current);
memset(&current,0,sizeof(current)); memset(&current, 0, sizeof(current));
} }
//DEBUG_FUNCTION_LINE("Found new block at %08X",addr); //DEBUG_FUNCTION_LINE("Found new block at %08X",addr);
current.addr = addr; current.addr = addr;
@ -606,9 +607,9 @@ void MemoryMapping::printPageTableTranslation(sr_table_t srTable, uint32_t * tra
current.phys = phys; current.phys = phys;
} }
} else { } else {
if(current.addr != 0 && current.size != 0) { if (current.addr != 0 && current.size != 0) {
pageInfos.push_back(current); pageInfos.push_back(current);
memset(&current,0,sizeof(current)); memset(&current, 0, sizeof(current));
} }
} }
} }
@ -618,15 +619,15 @@ void MemoryMapping::printPageTableTranslation(sr_table_t srTable, uint32_t * tra
const char *access1[] = {"read/write", "read/write", "read/write", "read only"}; const char *access1[] = {"read/write", "read/write", "read/write", "read only"};
const char *access2[] = {"no access", "read only", "read/write", "read only"}; const char *access2[] = {"no access", "read only", "read/write", "read only"};
for(std::vector<pageInformation>::iterator it = pageInfos.begin(); it != pageInfos.end(); ++it) { for (std::vector<pageInformation>::iterator it = pageInfos.begin(); it != pageInfos.end(); ++it) {
pageInformation cur = *it; pageInformation cur = *it;
DEBUG_FUNCTION_LINE("%08X %08X -> %08X %08X. user access %s. supervisor access %s. %s",cur.addr,cur.addr+cur.size,cur.phys,cur.phys+cur.size,cur.kp ? access2[cur.pp] : access1[cur.pp], DEBUG_FUNCTION_LINE("%08X %08X -> %08X %08X. user access %s. supervisor access %s. %s", cur.addr, cur.addr + cur.size, cur.phys, cur.phys + cur.size, cur.kp ? access2[cur.pp] : access1[cur.pp],
cur.ks ? access2[cur.pp] : access1[cur.pp],cur.nx? "not executable" : "executable"); cur.ks ? access2[cur.pp] : access1[cur.pp], cur.nx ? "not executable" : "executable");
} }
} }
bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,uint32_t ea_start_address, sr_table_t SRTable, uint32_t * translation_table) { bool MemoryMapping::mapMemory(uint32_t pa_start_address, uint32_t pa_end_address, uint32_t ea_start_address, sr_table_t SRTable, uint32_t *translation_table) {
// Based on code from dimok. Thanks! // Based on code from dimok. Thanks!
//uint32_t byteOffsetMask = (1 << PAGE_INDEX_SHIFT) - 1; //uint32_t byteOffsetMask = (1 << PAGE_INDEX_SHIFT) - 1;
@ -639,8 +640,8 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
// Iterate to all possible pages. Each page is 1<<(PAGE_INDEX_SHIFT) big. // Iterate to all possible pages. Each page is 1<<(PAGE_INDEX_SHIFT) big.
uint32_t pageSize = 1<<(PAGE_INDEX_SHIFT); uint32_t pageSize = 1 << (PAGE_INDEX_SHIFT);
for(uint32_t i = 0; i < pa_end_address - pa_start_address; i += pageSize) { for (uint32_t i = 0; i < pa_end_address - pa_start_address; i += pageSize) {
// Calculate the current effective address. // Calculate the current effective address.
uint32_t ea_addr = ea_start_address + i; uint32_t ea_addr = ea_start_address + i;
// Calculate the segement. // Calculate the segement.
@ -672,7 +673,7 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
uint32_t primary_hash = (VSID & 0x7FFFF); uint32_t primary_hash = (VSID & 0x7FFFF);
uint32_t hashvalue1 = primary_hash ^ page_index; uint32_t hashvalue1 = primary_hash ^page_index;
// hashvalue 2 is the complement of the first hash. // hashvalue 2 is the complement of the first hash.
uint32_t hashvalue2 = ~hashvalue1; uint32_t hashvalue2 = ~hashvalue1;
@ -690,10 +691,10 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
uint32_t PTEGoffset = PTEGaddr1 - (HTABORG << 16); uint32_t PTEGoffset = PTEGaddr1 - (HTABORG << 16);
bool setSuccessfully = false; bool setSuccessfully = false;
PTEGoffset += 7*8; PTEGoffset += 7 * 8;
// Lets iterate through the PTE group where out PTE should be saved. // Lets iterate through the PTE group where out PTE should be saved.
for(int32_t j = 7; j>0; PTEGoffset -= 8) { for (int32_t j = 7; j > 0; PTEGoffset -= 8) {
int32_t index = (PTEGoffset/4); int32_t index = (PTEGoffset / 4);
uint32_t pteh = translation_table[index]; uint32_t pteh = translation_table[index];
// Check if it's already taken. The first bit indicates if the PTE-slot inside // Check if it's already taken. The first bit indicates if the PTE-slot inside
@ -702,7 +703,7 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
// If we found a free slot, set the PTEH and PTEL value. // If we found a free slot, set the PTEH and PTEL value.
//DEBUG_FUNCTION_LINE("Used slot %d. PTEGaddr1 %08X addr %08X",j+1,PTEGaddr1 - (HTABORG << 16),PTEGoffset); //DEBUG_FUNCTION_LINE("Used slot %d. PTEGaddr1 %08X addr %08X",j+1,PTEGaddr1 - (HTABORG << 16),PTEGoffset);
translation_table[index] = PTEH; translation_table[index] = PTEH;
translation_table[index+1] = PTEL; translation_table[index + 1] = PTEL;
setSuccessfully = true; setSuccessfully = true;
break; break;
} else { } else {
@ -711,7 +712,7 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
j--; j--;
} }
// Check if we already found a slot. // Check if we already found a slot.
if(!setSuccessfully) { if (!setSuccessfully) {
//DEBUG_FUNCTION_LINE("-------------- Using second slot -----------------------"); //DEBUG_FUNCTION_LINE("-------------- Using second slot -----------------------");
// We still have a chance to find a slot in the PTEGaddr2 using the complement of the hash. // We still have a chance to find a slot in the PTEGaddr2 using the complement of the hash.
// We need to set the H flag in PTEH and use PTEGaddr2. // We need to set the H flag in PTEH and use PTEGaddr2.
@ -719,15 +720,15 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
H = 1; H = 1;
PTEH = (V << 31) | (VSID << 7) | (H << 6) | API; PTEH = (V << 31) | (VSID << 7) | (H << 6) | API;
PTEGoffset = PTEGaddr2 - (HTABORG << 16); PTEGoffset = PTEGaddr2 - (HTABORG << 16);
PTEGoffset += 7*8; PTEGoffset += 7 * 8;
// Same as before. // Same as before.
for(int32_t j = 7; j>0; PTEGoffset -= 8) { for (int32_t j = 7; j > 0; PTEGoffset -= 8) {
int32_t index = (PTEGoffset/4); int32_t index = (PTEGoffset / 4);
uint32_t pteh = translation_table[index]; uint32_t pteh = translation_table[index];
//Check if it's already taken. //Check if it's already taken.
if ((pteh == 0)) { if ((pteh == 0)) {
translation_table[index] = PTEH; translation_table[index] = PTEH;
translation_table[index+1] = PTEL; translation_table[index + 1] = PTEL;
setSuccessfully = true; setSuccessfully = true;
break; break;
} else { } else {
@ -736,7 +737,7 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
j--; j--;
} }
if(!setSuccessfully) { if (!setSuccessfully) {
// Fail if we couldn't find a free slot. // Fail if we couldn't find a free slot.
DEBUG_FUNCTION_LINE("-------------- No more free PTE -----------------------"); DEBUG_FUNCTION_LINE("-------------- No more free PTE -----------------------");
return false; return false;
@ -747,27 +748,27 @@ bool MemoryMapping::mapMemory(uint32_t pa_start_address,uint32_t pa_end_address,
} }
uint32_t MemoryMapping::PhysicalToEffective(uint32_t phyiscalAddress) { uint32_t MemoryMapping::PhysicalToEffective(uint32_t phyiscalAddress) {
if(phyiscalAddress >= 0x30800000 && phyiscalAddress < 0x31000000) { if (phyiscalAddress >= 0x30800000 && phyiscalAddress < 0x31000000) {
return phyiscalAddress - (0x30800000 - 0x00800000); return phyiscalAddress - (0x30800000 - 0x00800000);
} }
uint32_t result = 0; uint32_t result = 0;
const memory_values_t * curMemValues = NULL; const memory_values_t *curMemValues = NULL;
int32_t curOffset = 0; int32_t curOffset = 0;
//iterate through all own mapped memory regions //iterate through all own mapped memory regions
for(int32_t i = 0; true; i++) { for (int32_t i = 0; true; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
curMemValues = mem_mapping[i].physical_addresses; curMemValues = mem_mapping[i].physical_addresses;
uint32_t curOffsetInEA = 0; uint32_t curOffsetInEA = 0;
// iterate through all memory values of this region // iterate through all memory values of this region
for(int32_t j= 0; true; j++) { for (int32_t j = 0; true; j++) {
if(curMemValues[j].end_address == 0) { if (curMemValues[j].end_address == 0) {
break; break;
} }
if(phyiscalAddress >= curMemValues[j].start_address && phyiscalAddress < curMemValues[j].end_address) { if (phyiscalAddress >= curMemValues[j].start_address && phyiscalAddress < curMemValues[j].end_address) {
// calculate the EA // calculate the EA
result = (phyiscalAddress - curMemValues[j].start_address) + (mem_mapping[i].effective_start_address + curOffsetInEA); result = (phyiscalAddress - curMemValues[j].start_address) + (mem_mapping[i].effective_start_address + curOffsetInEA);
return result; return result;
@ -780,36 +781,36 @@ uint32_t MemoryMapping::PhysicalToEffective(uint32_t phyiscalAddress) {
} }
uint32_t MemoryMapping::EffectiveToPhysical(uint32_t effectiveAddress) { uint32_t MemoryMapping::EffectiveToPhysical(uint32_t effectiveAddress) {
if(effectiveAddress >= 0x00800000 && effectiveAddress < 0x01000000) { if (effectiveAddress >= 0x00800000 && effectiveAddress < 0x01000000) {
return effectiveAddress + (0x30800000 - 0x00800000); return effectiveAddress + (0x30800000 - 0x00800000);
} }
uint32_t result = 0; uint32_t result = 0;
// CAUTION: The data may be fragmented between multiple areas in PA. // CAUTION: The data may be fragmented between multiple areas in PA.
const memory_values_t * curMemValues = NULL; const memory_values_t *curMemValues = NULL;
uint32_t curOffset = 0; uint32_t curOffset = 0;
for(int32_t i = 0; true; i++) { for (int32_t i = 0; true; i++) {
if(mem_mapping[i].physical_addresses == NULL) { if (mem_mapping[i].physical_addresses == NULL) {
break; break;
} }
if(effectiveAddress >= mem_mapping[i].effective_start_address && effectiveAddress < mem_mapping[i].effective_end_address) { if (effectiveAddress >= mem_mapping[i].effective_start_address && effectiveAddress < mem_mapping[i].effective_end_address) {
curMemValues = mem_mapping[i].physical_addresses; curMemValues = mem_mapping[i].physical_addresses;
curOffset = mem_mapping[i].effective_start_address; curOffset = mem_mapping[i].effective_start_address;
break; break;
} }
} }
if(curMemValues == NULL) { if (curMemValues == NULL) {
return result; return result;
} }
for(int32_t i= 0; true; i++) { for (int32_t i = 0; true; i++) {
if(curMemValues[i].end_address == 0) { if (curMemValues[i].end_address == 0) {
break; break;
} }
uint32_t curChunkSize = curMemValues[i].end_address - curMemValues[i].start_address; uint32_t curChunkSize = curMemValues[i].end_address - curMemValues[i].start_address;
if(effectiveAddress < (curOffset + curChunkSize)) { if (effectiveAddress < (curOffset + curChunkSize)) {
result = (effectiveAddress - curOffset) + curMemValues[i].start_address; result = (effectiveAddress - curOffset) + curMemValues[i].start_address;
break; break;
} }

View File

@ -179,9 +179,9 @@ public:
static void searchEmptyMemoryRegions(); static void searchEmptyMemoryRegions();
static void * alloc(uint32_t size, uint32_t align); static void *alloc(uint32_t size, uint32_t align);
static void free(void * ptr); static void free(void *ptr);
static uint32_t getAreaSizeFromPageTable(uint32_t start, uint32_t maxSize); static uint32_t getAreaSizeFromPageTable(uint32_t start, uint32_t maxSize);