Update copies to work around alignment faults.

arch/alpha/isa_desc:
    whitespace fix.
cpu/simple_cpu/simple_cpu.cc:
    Add support to make sure we don't get alignment faults in copies. Warn if we go over an 8k page boundary.

--HG--
extra : convert_revision : 98b38da86a66215d80ea9eb6e6f1f68ee573cb57
This commit is contained in:
Erik Hallnor 2004-09-20 22:00:35 -04:00
parent bb59e2e7a3
commit 15d08a3422
2 changed files with 36 additions and 9 deletions

View file

@ -338,16 +338,29 @@ change_thread_state(int thread_number, int activate, int priority)
Fault Fault
SimpleCPU::copySrcTranslate(Addr src) SimpleCPU::copySrcTranslate(Addr src)
{ {
memReq->reset(src, (dcacheInterface) ? static bool no_warn = true;
dcacheInterface->getBlockSize() int blk_size = (dcacheInterface) ? dcacheInterface->getBlockSize() : 64;
: 64); // Only support block sizes of 64 atm.
assert(blk_size == 64);
int offset = src & (blk_size - 1);
// Make sure block doesn't span page
if (no_warn && (src & (~8191)) == ((src + blk_size) & (~8191))) {
warn("Copied block source spans pages.");
no_warn = false;
}
memReq->reset(src & ~(blk_size - 1), blk_size);
// translate to physical address // translate to physical address
Fault fault = xc->translateDataReadReq(memReq); Fault fault = xc->translateDataReadReq(memReq);
assert(fault != Alignment_Fault);
if (fault == No_Fault) { if (fault == No_Fault) {
xc->copySrcAddr = src; xc->copySrcAddr = src;
xc->copySrcPhysAddr = memReq->paddr; xc->copySrcPhysAddr = memReq->paddr + offset;
} else { } else {
xc->copySrcAddr = 0; xc->copySrcAddr = 0;
xc->copySrcPhysAddr = 0; xc->copySrcPhysAddr = 0;
@ -358,14 +371,28 @@ SimpleCPU::copySrcTranslate(Addr src)
Fault Fault
SimpleCPU::copy(Addr dest) SimpleCPU::copy(Addr dest)
{ {
static bool no_warn = true;
int blk_size = (dcacheInterface) ? dcacheInterface->getBlockSize() : 64; int blk_size = (dcacheInterface) ? dcacheInterface->getBlockSize() : 64;
// Only support block sizes of 64 atm.
assert(blk_size == 64);
uint8_t data[blk_size]; uint8_t data[blk_size];
assert(xc->copySrcAddr); //assert(xc->copySrcAddr);
memReq->reset(dest, blk_size); int offset = dest & (blk_size - 1);
// Make sure block doesn't span page
if (no_warn && (dest & (~8191)) == ((dest + blk_size) & (~8191))) {
no_warn = false;
warn("Copied block destination spans pages. ");
}
memReq->reset(dest & ~(blk_size -1), blk_size);
// translate to physical address // translate to physical address
Fault fault = xc->translateDataWriteReq(memReq); Fault fault = xc->translateDataWriteReq(memReq);
assert(fault != Alignment_Fault);
if (fault == No_Fault) { if (fault == No_Fault) {
Addr dest_addr = memReq->paddr; Addr dest_addr = memReq->paddr + offset;
// Need to read straight from memory since we have more than 8 bytes. // Need to read straight from memory since we have more than 8 bytes.
memReq->paddr = xc->copySrcPhysAddr; memReq->paddr = xc->copySrcPhysAddr;
xc->mem->read(memReq, data); xc->mem->read(memReq, data);