📄 linearaddressspace.java
字号:
{
flush();
return;
}
Enumeration ee = nonGlobalPages.keys();
while (ee.hasMoreElements())
{
int index = ((Integer) ee.nextElement()).intValue();
nullIndex(readSupervisorIndex, index);
nullIndex(writeSupervisorIndex, index);
nullIndex(readUserIndex, index);
nullIndex(writeUserIndex, index);
pageFlags[index] = FOUR_K;
}
nonGlobalPages.clear();
/*
for (int i=0; i<pageFlags.length; i++)
{
if ((pageFlags[i] & IS_GLOBAL_MASK) != 0)
continue;
readSupervisorIndex[i] = null;
writeSupervisorIndex[i] = null;
readUserIndex[i] = null;
writeUserIndex[i] = null;
}
*/
}
private void nullIndex(Memory[] array, int index)
{
try {
array[index] = null;
} catch (NullPointerException e) {}
}
public void setPageDirectoryBaseAddress(int address)
{
baseAddress = address & 0xFFFFF000;
partialFlush();
}
public void invalidateTLBEntry(int offset)
{
int index = offset >>> INDEX_SHIFT;
if ((pageFlags[index] & IS_4_M_MASK) == 0)
{
nullIndex(readSupervisorIndex, index);
nullIndex(writeSupervisorIndex, index);
nullIndex(readUserIndex, index);
nullIndex(writeUserIndex, index);
nonGlobalPages.remove(new Integer(index));
}
else
{
index = ((offset & 0xFFC00000) >>> 12);
for (int i=0; i<1024; i++, index++)
{
nullIndex(readSupervisorIndex, index);
nullIndex(writeSupervisorIndex, index);
nullIndex(readUserIndex, index);
nullIndex(writeUserIndex, index);
nonGlobalPages.remove(new Integer(index));
}
}
}
public Memory validateTLBEntryRead(int offset)
{
int idx = offset >>> INDEX_SHIFT;
if (pagingDisabled)
{
setReadIndexValue(idx, target.getReadMemoryBlockAt(offset));
return readIndex[idx];
}
lastAddress = offset;
int directoryAddress = baseAddress | (0xFFC & (offset >>> 20)); // This should be (offset >>> 22) << 2.
int directoryRawBits = target.getDoubleWord(directoryAddress);
boolean directoryPresent = (0x1 & directoryRawBits) != 0;
if (!directoryPresent)
{
if (isSupervisor)
return PF_NOT_PRESENT_RS;
else
return PF_NOT_PRESENT_RU;
}
boolean directoryGlobal = globalPagesEnabled && ((0x100 & directoryRawBits) != 0);
boolean directoryReadWrite = (0x2 & directoryRawBits) != 0;
boolean directoryUser = (0x4 & directoryRawBits) != 0;
boolean directoryIs4MegPage = ((0x80 & directoryRawBits) != 0) && pageSizeExtensions;
if (directoryIs4MegPage)
{
if (!directoryUser)
{
if (!isSupervisor)
return PF_PROTECTION_VIOLATION_RU;
}
if ((directoryRawBits & 0x20) == 0)
{
directoryRawBits |= 0x20;
target.setDoubleWord(directoryAddress, directoryRawBits);
}
int fourMegPageStartAddress = 0xFFC00000 & directoryRawBits;
byte flag = FOUR_M;
if (directoryGlobal)
flag = FOUR_M_GLOBAL;
if (!pageCacheEnabled)
return target.getReadMemoryBlockAt(fourMegPageStartAddress | (offset & 0x3FFFFF));
int tableIndex = (0xFFC00000 & offset) >>> 12;
for (int i=0; i<1024; i++)
{
Memory m = target.getReadMemoryBlockAt(fourMegPageStartAddress);
fourMegPageStartAddress += BLOCK_SIZE;
pageFlags[tableIndex] = flag;
setReadIndexValue(tableIndex++, m);
if (directoryGlobal)
continue;
Integer iidx = new Integer(i);
nonGlobalPages.put(iidx, iidx);
}
return readIndex[idx];
}
else
{
int directoryBaseAddress = directoryRawBits & 0xFFFFF000;
boolean directoryPageLevelWriteThrough = (0x8 & directoryRawBits) != 0;
boolean directoryPageCacheDisable = (0x10 & directoryRawBits) != 0;
boolean directoryDirty = (0x40 & directoryRawBits) != 0;
int tableAddress = directoryBaseAddress | ((offset >>> 10) & 0xFFC);
int tableRawBits = target.getDoubleWord(tableAddress);
boolean tablePresent = (0x1 & tableRawBits) != 0;
if (!tablePresent)
{
if (isSupervisor)
return PF_NOT_PRESENT_RS;
else
return PF_NOT_PRESENT_RU;
}
boolean tableGlobal = globalPagesEnabled && ((0x100 & tableRawBits) != 0);
boolean tableReadWrite = (0x2 & tableRawBits) != 0;
boolean tableUser = (0x4 & tableRawBits) != 0;
boolean pageIsUser = tableUser && directoryUser;
boolean pageIsReadWrite = tableReadWrite || directoryReadWrite;
if (pageIsUser)
pageIsReadWrite = tableReadWrite && directoryReadWrite;
if (!pageIsUser)
{
if (!isSupervisor)
return PF_PROTECTION_VIOLATION_RU;
}
if ((tableRawBits & 0x20) == 0)
{
tableRawBits |= 0x20;
target.setDoubleWord(tableAddress, tableRawBits);
}
int fourKStartAddress = tableRawBits & 0xFFFFF000;
if (!pageCacheEnabled)
return target.getReadMemoryBlockAt(fourKStartAddress);
if (tableGlobal)
pageFlags[idx] = FOUR_K_GLOBAL;
else
{
pageFlags[idx] = FOUR_K;
Integer iidx = new Integer(idx);
nonGlobalPages.put(iidx, iidx);
}
setReadIndexValue(idx, target.getReadMemoryBlockAt(fourKStartAddress));
return readIndex[idx];
}
}
public Memory validateTLBEntryWrite(int offset)
{
int idx = offset >>> INDEX_SHIFT;
if (pagingDisabled)
{
setWriteIndexValue(idx, target.getWriteMemoryBlockAt(offset));
return writeIndex[idx];
}
lastAddress = offset;
int directoryAddress = baseAddress | (0xFFC & (offset >>> 20)); // This should be (offset >>> 22) << 2.
int directoryRawBits = target.getDoubleWord(directoryAddress);
boolean directoryPresent = (0x1 & directoryRawBits) != 0;
if (!directoryPresent)
{
if (isSupervisor)
return PF_NOT_PRESENT_WS;
else
return PF_NOT_PRESENT_WU;
}
boolean directoryGlobal = globalPagesEnabled && ((0x100 & directoryRawBits) != 0);
boolean directoryReadWrite = (0x2 & directoryRawBits) != 0;
boolean directoryUser = (0x4 & directoryRawBits) != 0;
boolean directoryIs4MegPage = ((0x80 & directoryRawBits) != 0) && pageSizeExtensions;
if (directoryIs4MegPage)
{
if (directoryUser)
{
if (!directoryReadWrite) // if readWrite then all access is OK
{
if (isSupervisor)
{
if (writeProtectUserPages)
return PF_PROTECTION_VIOLATION_WS;
}
else
return PF_PROTECTION_VIOLATION_WU;
}
}
else // A supervisor page
{
if (directoryReadWrite)
{
if (!isSupervisor)
return PF_PROTECTION_VIOLATION_WU;
}
else
{
if (isSupervisor)
return PF_PROTECTION_VIOLATION_WS;
else
return PF_PROTECTION_VIOLATION_WU;
}
}
if ((directoryRawBits & 0x60) != 0x60)
{
directoryRawBits |= 0x60;
target.setDoubleWord(directoryAddress, directoryRawBits);
}
int fourMegPageStartAddress = 0xFFC00000 & directoryRawBits;
byte flag = FOUR_M;
if (directoryGlobal)
flag = FOUR_M_GLOBAL;
if (!pageCacheEnabled)
return target.getWriteMemoryBlockAt(fourMegPageStartAddress | (offset & 0x3FFFFF));
int tableIndex = (0xFFC00000 & offset) >>> 12;
for (int i=0; i<1024; i++)
{
Memory m = target.getWriteMemoryBlockAt(fourMegPageStartAddress);
fourMegPageStartAddress += BLOCK_SIZE;
pageFlags[tableIndex] = flag;
setWriteIndexValue(tableIndex++, m);
if (directoryGlobal)
continue;
Integer iidx = new Integer(i);
nonGlobalPages.put(iidx, iidx);
}
return writeIndex[idx];
}
else
{
int directoryBaseAddress = directoryRawBits & 0xFFFFF000;
boolean directoryPageLevelWriteThrough = (0x8 & directoryRawBits) != 0;
boolean directoryPageCacheDisable = (0x10 & directoryRawBits) != 0;
boolean directoryDirty = (0x40 & directoryRawBits) != 0;
int tableAddress = directoryBaseAddress | ((offset >>> 10) & 0xFFC);
int tableRawBits = target.getDoubleWord(tableAddress);
boolean tablePresent = (0x1 & tableRawBits) != 0;
if (!tablePresent)
{
if (isSupervisor)
return PF_NOT_PRESENT_WS;
else
return PF_NOT_PRESENT_WU;
}
boolean tableGlobal = globalPagesEnabled && ((0x100 & tableRawBits) != 0);
boolean tableReadWrite = (0x2 & tableRawBits) != 0;
boolean tableUser = (0x4 & tableRawBits) != 0;
boolean pageIsUser = tableUser && directoryUser;
boolean pageIsReadWrite = tableReadWrite || directoryReadWrite;
if (pageIsUser)
pageIsReadWrite = tableReadWrite && directoryReadWrite;
if (pageIsUser)
{
if (!pageIsReadWrite) // if readWrite then all access is OK
{
if (isSupervisor)
{
if (writeProtectUserPages)
return PF_PROTECTION_VIOLATION_WS;
}
else
return PF_PROTECTION_VIOLATION_WU;
}
}
else // A supervisor page
{
if (pageIsReadWrite)
{
if (!isSupervisor)
return PF_PROTECTION_VIOLATION_WU;
}
else
{
if (isSupervisor)
return PF_PROTECTION_VIOLATION_WS;
else
return PF_PROTECTION_VIOLATION_WU;
}
}
if ((tableRawBits & 0x60) != 0x60)
{
tableRawBits |= 0x60;
target.setDoubleWord(tableAddress, tableRawBits);
}
int fourKStartAddress = tableRawBits & 0xFFFFF000;
if (!pageCacheEnabled)
return target.getWriteMemoryBlockAt(fourKStartAddress);
if (tableGlobal)
pageFlags[idx] = FOUR_K_GLOBAL;
else
{
pageFlags[idx] = FOUR_K;
Integer iidx = new Integer(idx);
nonGlobalPages.put(iidx, iidx);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -