ev5.cc revision 2190
1/* 2 * Copyright (c) 2002-2005 The Regents of The University of Michigan 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer; 9 * redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution; 12 * neither the name of the copyright holders nor the names of its 13 * contributors may be used to endorse or promote products derived from 14 * this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29#include "arch/alpha/alpha_memory.hh" 30#include "arch/alpha/isa_traits.hh" 31#include "arch/alpha/osfpal.hh" 32#include "base/kgdb.h" 33#include "base/remote_gdb.hh" 34#include "base/stats/events.hh" 35#include "config/full_system.hh" 36#include "cpu/base.hh" 37#include "cpu/cpu_exec_context.hh" 38#include "cpu/exec_context.hh" 39#include "cpu/fast/cpu.hh" 40#include "kern/kernel_stats.hh" 41#include "sim/debug.hh" 42#include "sim/sim_events.hh" 43 44#if FULL_SYSTEM 45 46using namespace EV5; 47 48//////////////////////////////////////////////////////////////////////// 49// 50// 51// 52void 53AlphaISA::swap_palshadow(RegFile *regs, bool use_shadow) 54{ 55 if (regs->pal_shadow == use_shadow) 56 panic("swap_palshadow: wrong PAL shadow state"); 57 58 regs->pal_shadow = use_shadow; 59 60 for (int i = 0; i < NumIntRegs; i++) { 61 if (reg_redir[i]) { 62 IntReg temp = regs->intRegFile[i]; 63 regs->intRegFile[i] = regs->palregs[i]; 64 regs->palregs[i] = temp; 65 } 66 } 67} 68 69//////////////////////////////////////////////////////////////////////// 70// 71// Machine dependent functions 72// 73void 74AlphaISA::initCPU(ExecContext *xc, int cpuId) 75{ 76 initIPRs(xc, cpuId); 77 // CPU comes up with PAL regs enabled 78 swap_palshadow(regs, true); 79 80 xc->setIntReg(16, cpuId); 81 xc->setIntReg(0, cpuId); 82 83 xc->setPC(xc->readMiscReg(IPR_PAL_BASE) + fault_addr(ResetFault)); 84 xc->setNextPC(xc->readPC() + sizeof(MachInst)); 85} 86 87//////////////////////////////////////////////////////////////////////// 88// 89// alpha exceptions - value equals trap address, update with MD_FAULT_TYPE 90// 91const Addr 92AlphaISA::fault_addr(Fault fault) 93{ 94 //Check for the system wide faults 95 if(fault == NoFault) return 0x0000; 96 else if(fault == MachineCheckFault) return 0x0401; 97 else if(fault == AlignmentFault) return 0x0301; 98 //Deal with the alpha specific faults 99 return ((AlphaFault*)fault)->vect; 100}; 101 102const int AlphaISA::reg_redir[AlphaISA::NumIntRegs] = { 103 /* 0 */ 0, 0, 0, 0, 0, 0, 0, 0, 104 /* 8 */ 1, 1, 1, 1, 1, 1, 1, 0, 105 /* 16 */ 0, 0, 0, 0, 0, 0, 0, 0, 106 /* 24 */ 0, 1, 0, 0, 0, 0, 0, 0 }; 107 108//////////////////////////////////////////////////////////////////////// 109// 110// 111// 112void 113AlphaISA::initIPRs(ExecContext *xc, int cpuId) 114{ 115 for (int i = 0; i < NumInternalProcRegs; ++i) { 116 xc->setMiscReg(i, 0); 117 } 118 119 xc->setMiscReg(IPR_PAL_BASE, PalBase); 120 xc->setMiscReg(IPR_MCSR, 0x6); 121 xc->setMiscReg(IPR_PALtemp16, cpuId); 122} 123 124 125template <class CPU> 126void 127AlphaISA::processInterrupts(CPU *cpu) 128{ 129 //Check if there are any outstanding interrupts 130 //Handle the interrupts 131 int ipl = 0; 132 int summary = 0; 133 134 cpu->checkInterrupts = false; 135 136 if (cpu->readMiscReg(IPR_ASTRR)) 137 panic("asynchronous traps not implemented\n"); 138 139 if (cpu->readMiscReg(IPR_SIRR)) { 140 for (int i = INTLEVEL_SOFTWARE_MIN; 141 i < INTLEVEL_SOFTWARE_MAX; i++) { 142 if (cpu->readMiscReg(IPR_SIRR) & (ULL(1) << i)) { 143 // See table 4-19 of the 21164 hardware reference 144 ipl = (i - INTLEVEL_SOFTWARE_MIN) + 1; 145 summary |= (ULL(1) << i); 146 } 147 } 148 } 149 150 uint64_t interrupts = cpu->intr_status(); 151 152 if (interrupts) { 153 for (int i = INTLEVEL_EXTERNAL_MIN; 154 i < INTLEVEL_EXTERNAL_MAX; i++) { 155 if (interrupts & (ULL(1) << i)) { 156 // See table 4-19 of the 21164 hardware reference 157 ipl = i; 158 summary |= (ULL(1) << i); 159 } 160 } 161 } 162 163 if (ipl && ipl > cpu->readMiscReg(IPR_IPLR)) { 164 cpu->setMiscReg(IPR_ISR, summary); 165 cpu->setMiscReg(IPR_INTID, ipl); 166 cpu->trap(InterruptFault); 167 DPRINTF(Flow, "Interrupt! IPLR=%d ipl=%d summary=%x\n", 168 cpu->readMiscReg(IPR_IPLR), ipl, summary); 169 } 170 171} 172 173template <class CPU> 174void 175AlphaISA::zeroRegisters(CPU *cpu) 176{ 177 // Insure ISA semantics 178 // (no longer very clean due to the change in setIntReg() in the 179 // cpu model. Consider changing later.) 180 cpu->cpuXC->setIntReg(ZeroReg, 0); 181 cpu->cpuXC->setFloatRegDouble(ZeroReg, 0.0); 182} 183 184void 185CPUExecContext::ev5_trap(Fault fault) 186{ 187 DPRINTF(Fault, "Fault %s at PC: %#x\n", fault->name, regs.pc); 188 cpu->recordEvent(csprintf("Fault %s", fault->name)); 189 190 assert(!misspeculating()); 191 cpu->kernelStats->fault(fault); 192 193 if (fault == ArithmeticFault) 194 panic("Arithmetic traps are unimplemented!"); 195 196 // exception restart address 197 if (fault != InterruptFault || !inPalMode()) 198 setMiscReg(AlphaISA::IPR_EXC_ADDR, regs.pc); 199 200 if (fault == PalFault || fault == ArithmeticFault /* || 201 fault == InterruptFault && !inPalMode() */) { 202 // traps... skip faulting instruction 203 setMiscReg(AlphaISA::IPR_EXC_ADDR, 204 readMiscReg(AlphaISA::IPR_EXC_ADDR) + 4); 205 } 206 207 if (!inPalMode()) 208 AlphaISA::swap_palshadow(®s, true); 209 210 regs.pc = readMiscReg(AlphaISA::IPR_PAL_BASE) + AlphaISA::fault_addr(fault); 211 regs.npc = regs.pc + sizeof(MachInst); 212} 213 214 215void 216AlphaISA::intr_post(RegFile *regs, Fault fault, Addr pc) 217{ 218 bool use_pc = (fault == NoFault); 219 220 if (fault == ArithmeticFault) 221 panic("arithmetic faults NYI..."); 222 223 // compute exception restart address 224 if (use_pc || fault == PalFault || fault == ArithmeticFault) { 225 // traps... skip faulting instruction 226 regs->miscRegs.setReg(IPR_EXC_ADDR, regs->pc + 4); 227 } else { 228 // fault, post fault at excepting instruction 229 regs->miscRegs.setReg(IPR_EXC_ADDR, regs->pc); 230 } 231 232 // jump to expection address (PAL PC bit set here as well...) 233 if (!use_pc) 234 regs->npc = regs->miscRegs.readReg(IPR_PAL_BASE) + 235 fault_addr(fault); 236 else 237 regs->npc = regs->miscRegs.readReg(IPR_PAL_BASE) + pc; 238 239 // that's it! (orders of magnitude less painful than x86) 240} 241 242Fault 243CPUExecContext::hwrei() 244{ 245 if (!inPalMode()) 246 return UnimplementedOpcodeFault; 247 248 setNextPC(readMiscReg(AlphaISA::IPR_EXC_ADDR)); 249 250 if (!misspeculating()) { 251 cpu->kernelStats->hwrei(); 252 253 if ((readMiscReg(AlphaISA::IPR_EXC_ADDR) & 1) == 0) 254 AlphaISA::swap_palshadow(®s, false); 255 256 cpu->checkInterrupts = true; 257 } 258 259 // FIXME: XXX check for interrupts? XXX 260 return NoFault; 261} 262 263AlphaISA::MiscReg 264AlphaISA::MiscRegFile::readIpr(int idx, Fault &fault, ExecContext *xc) 265{ 266 uint64_t retval = 0; // return value, default 0 267 268 switch (idx) { 269 case AlphaISA::IPR_PALtemp0: 270 case AlphaISA::IPR_PALtemp1: 271 case AlphaISA::IPR_PALtemp2: 272 case AlphaISA::IPR_PALtemp3: 273 case AlphaISA::IPR_PALtemp4: 274 case AlphaISA::IPR_PALtemp5: 275 case AlphaISA::IPR_PALtemp6: 276 case AlphaISA::IPR_PALtemp7: 277 case AlphaISA::IPR_PALtemp8: 278 case AlphaISA::IPR_PALtemp9: 279 case AlphaISA::IPR_PALtemp10: 280 case AlphaISA::IPR_PALtemp11: 281 case AlphaISA::IPR_PALtemp12: 282 case AlphaISA::IPR_PALtemp13: 283 case AlphaISA::IPR_PALtemp14: 284 case AlphaISA::IPR_PALtemp15: 285 case AlphaISA::IPR_PALtemp16: 286 case AlphaISA::IPR_PALtemp17: 287 case AlphaISA::IPR_PALtemp18: 288 case AlphaISA::IPR_PALtemp19: 289 case AlphaISA::IPR_PALtemp20: 290 case AlphaISA::IPR_PALtemp21: 291 case AlphaISA::IPR_PALtemp22: 292 case AlphaISA::IPR_PALtemp23: 293 case AlphaISA::IPR_PAL_BASE: 294 295 case AlphaISA::IPR_IVPTBR: 296 case AlphaISA::IPR_DC_MODE: 297 case AlphaISA::IPR_MAF_MODE: 298 case AlphaISA::IPR_ISR: 299 case AlphaISA::IPR_EXC_ADDR: 300 case AlphaISA::IPR_IC_PERR_STAT: 301 case AlphaISA::IPR_DC_PERR_STAT: 302 case AlphaISA::IPR_MCSR: 303 case AlphaISA::IPR_ASTRR: 304 case AlphaISA::IPR_ASTER: 305 case AlphaISA::IPR_SIRR: 306 case AlphaISA::IPR_ICSR: 307 case AlphaISA::IPR_ICM: 308 case AlphaISA::IPR_DTB_CM: 309 case AlphaISA::IPR_IPLR: 310 case AlphaISA::IPR_INTID: 311 case AlphaISA::IPR_PMCTR: 312 // no side-effect 313 retval = ipr[idx]; 314 break; 315 316 case AlphaISA::IPR_CC: 317 retval |= ipr[idx] & ULL(0xffffffff00000000); 318 retval |= xc->getCpuPtr()->curCycle() & ULL(0x00000000ffffffff); 319 break; 320 321 case AlphaISA::IPR_VA: 322 retval = ipr[idx]; 323 break; 324 325 case AlphaISA::IPR_VA_FORM: 326 case AlphaISA::IPR_MM_STAT: 327 case AlphaISA::IPR_IFAULT_VA_FORM: 328 case AlphaISA::IPR_EXC_MASK: 329 case AlphaISA::IPR_EXC_SUM: 330 retval = ipr[idx]; 331 break; 332 333 case AlphaISA::IPR_DTB_PTE: 334 { 335 AlphaISA::PTE &pte = xc->getDTBPtr()->index(!xc->misspeculating()); 336 337 retval |= ((u_int64_t)pte.ppn & ULL(0x7ffffff)) << 32; 338 retval |= ((u_int64_t)pte.xre & ULL(0xf)) << 8; 339 retval |= ((u_int64_t)pte.xwe & ULL(0xf)) << 12; 340 retval |= ((u_int64_t)pte.fonr & ULL(0x1)) << 1; 341 retval |= ((u_int64_t)pte.fonw & ULL(0x1))<< 2; 342 retval |= ((u_int64_t)pte.asma & ULL(0x1)) << 4; 343 retval |= ((u_int64_t)pte.asn & ULL(0x7f)) << 57; 344 } 345 break; 346 347 // write only registers 348 case AlphaISA::IPR_HWINT_CLR: 349 case AlphaISA::IPR_SL_XMIT: 350 case AlphaISA::IPR_DC_FLUSH: 351 case AlphaISA::IPR_IC_FLUSH: 352 case AlphaISA::IPR_ALT_MODE: 353 case AlphaISA::IPR_DTB_IA: 354 case AlphaISA::IPR_DTB_IAP: 355 case AlphaISA::IPR_ITB_IA: 356 case AlphaISA::IPR_ITB_IAP: 357 fault = UnimplementedOpcodeFault; 358 break; 359 360 default: 361 // invalid IPR 362 fault = UnimplementedOpcodeFault; 363 break; 364 } 365 366 return retval; 367} 368 369#ifdef DEBUG 370// Cause the simulator to break when changing to the following IPL 371int break_ipl = -1; 372#endif 373 374Fault 375AlphaISA::MiscRegFile::setIpr(int idx, uint64_t val, ExecContext *xc) 376{ 377 uint64_t old; 378 379 if (xc->misspeculating()) 380 return NoFault; 381 382 switch (idx) { 383 case AlphaISA::IPR_PALtemp0: 384 case AlphaISA::IPR_PALtemp1: 385 case AlphaISA::IPR_PALtemp2: 386 case AlphaISA::IPR_PALtemp3: 387 case AlphaISA::IPR_PALtemp4: 388 case AlphaISA::IPR_PALtemp5: 389 case AlphaISA::IPR_PALtemp6: 390 case AlphaISA::IPR_PALtemp7: 391 case AlphaISA::IPR_PALtemp8: 392 case AlphaISA::IPR_PALtemp9: 393 case AlphaISA::IPR_PALtemp10: 394 case AlphaISA::IPR_PALtemp11: 395 case AlphaISA::IPR_PALtemp12: 396 case AlphaISA::IPR_PALtemp13: 397 case AlphaISA::IPR_PALtemp14: 398 case AlphaISA::IPR_PALtemp15: 399 case AlphaISA::IPR_PALtemp16: 400 case AlphaISA::IPR_PALtemp17: 401 case AlphaISA::IPR_PALtemp18: 402 case AlphaISA::IPR_PALtemp19: 403 case AlphaISA::IPR_PALtemp20: 404 case AlphaISA::IPR_PALtemp21: 405 case AlphaISA::IPR_PALtemp22: 406 case AlphaISA::IPR_PAL_BASE: 407 case AlphaISA::IPR_IC_PERR_STAT: 408 case AlphaISA::IPR_DC_PERR_STAT: 409 case AlphaISA::IPR_PMCTR: 410 // write entire quad w/ no side-effect 411 ipr[idx] = val; 412 break; 413 414 case AlphaISA::IPR_CC_CTL: 415 // This IPR resets the cycle counter. We assume this only 416 // happens once... let's verify that. 417 assert(ipr[idx] == 0); 418 ipr[idx] = 1; 419 break; 420 421 case AlphaISA::IPR_CC: 422 // This IPR only writes the upper 64 bits. It's ok to write 423 // all 64 here since we mask out the lower 32 in rpcc (see 424 // isa_desc). 425 ipr[idx] = val; 426 break; 427 428 case AlphaISA::IPR_PALtemp23: 429 // write entire quad w/ no side-effect 430 old = ipr[idx]; 431 ipr[idx] = val; 432 xc->getCpuPtr()->kernelStats->context(old, val, xc); 433 break; 434 435 case AlphaISA::IPR_DTB_PTE: 436 // write entire quad w/ no side-effect, tag is forthcoming 437 ipr[idx] = val; 438 break; 439 440 case AlphaISA::IPR_EXC_ADDR: 441 // second least significant bit in PC is always zero 442 ipr[idx] = val & ~2; 443 break; 444 445 case AlphaISA::IPR_ASTRR: 446 case AlphaISA::IPR_ASTER: 447 // only write least significant four bits - privilege mask 448 ipr[idx] = val & 0xf; 449 break; 450 451 case AlphaISA::IPR_IPLR: 452#ifdef DEBUG 453 if (break_ipl != -1 && break_ipl == (val & 0x1f)) 454 debug_break(); 455#endif 456 457 // only write least significant five bits - interrupt level 458 ipr[idx] = val & 0x1f; 459 xc->getCpuPtr()->kernelStats->swpipl(ipr[idx]); 460 break; 461 462 case AlphaISA::IPR_DTB_CM: 463 if (val & 0x18) 464 xc->getCpuPtr()->kernelStats->mode(Kernel::user, xc); 465 else 466 xc->getCpuPtr()->kernelStats->mode(Kernel::kernel, xc); 467 468 case AlphaISA::IPR_ICM: 469 // only write two mode bits - processor mode 470 ipr[idx] = val & 0x18; 471 break; 472 473 case AlphaISA::IPR_ALT_MODE: 474 // only write two mode bits - processor mode 475 ipr[idx] = val & 0x18; 476 break; 477 478 case AlphaISA::IPR_MCSR: 479 // more here after optimization... 480 ipr[idx] = val; 481 break; 482 483 case AlphaISA::IPR_SIRR: 484 // only write software interrupt mask 485 ipr[idx] = val & 0x7fff0; 486 break; 487 488 case AlphaISA::IPR_ICSR: 489 ipr[idx] = val & ULL(0xffffff0300); 490 break; 491 492 case AlphaISA::IPR_IVPTBR: 493 case AlphaISA::IPR_MVPTBR: 494 ipr[idx] = val & ULL(0xffffffffc0000000); 495 break; 496 497 case AlphaISA::IPR_DC_TEST_CTL: 498 ipr[idx] = val & 0x1ffb; 499 break; 500 501 case AlphaISA::IPR_DC_MODE: 502 case AlphaISA::IPR_MAF_MODE: 503 ipr[idx] = val & 0x3f; 504 break; 505 506 case AlphaISA::IPR_ITB_ASN: 507 ipr[idx] = val & 0x7f0; 508 break; 509 510 case AlphaISA::IPR_DTB_ASN: 511 ipr[idx] = val & ULL(0xfe00000000000000); 512 break; 513 514 case AlphaISA::IPR_EXC_SUM: 515 case AlphaISA::IPR_EXC_MASK: 516 // any write to this register clears it 517 ipr[idx] = 0; 518 break; 519 520 case AlphaISA::IPR_INTID: 521 case AlphaISA::IPR_SL_RCV: 522 case AlphaISA::IPR_MM_STAT: 523 case AlphaISA::IPR_ITB_PTE_TEMP: 524 case AlphaISA::IPR_DTB_PTE_TEMP: 525 // read-only registers 526 return UnimplementedOpcodeFault; 527 528 case AlphaISA::IPR_HWINT_CLR: 529 case AlphaISA::IPR_SL_XMIT: 530 case AlphaISA::IPR_DC_FLUSH: 531 case AlphaISA::IPR_IC_FLUSH: 532 // the following are write only 533 ipr[idx] = val; 534 break; 535 536 case AlphaISA::IPR_DTB_IA: 537 // really a control write 538 ipr[idx] = 0; 539 540 xc->getDTBPtr()->flushAll(); 541 break; 542 543 case AlphaISA::IPR_DTB_IAP: 544 // really a control write 545 ipr[idx] = 0; 546 547 xc->getDTBPtr()->flushProcesses(); 548 break; 549 550 case AlphaISA::IPR_DTB_IS: 551 // really a control write 552 ipr[idx] = val; 553 554 xc->getDTBPtr()->flushAddr(val, 555 DTB_ASN_ASN(ipr[AlphaISA::IPR_DTB_ASN])); 556 break; 557 558 case AlphaISA::IPR_DTB_TAG: { 559 struct AlphaISA::PTE pte; 560 561 // FIXME: granularity hints NYI... 562 if (DTB_PTE_GH(ipr[AlphaISA::IPR_DTB_PTE]) != 0) 563 panic("PTE GH field != 0"); 564 565 // write entire quad 566 ipr[idx] = val; 567 568 // construct PTE for new entry 569 pte.ppn = DTB_PTE_PPN(ipr[AlphaISA::IPR_DTB_PTE]); 570 pte.xre = DTB_PTE_XRE(ipr[AlphaISA::IPR_DTB_PTE]); 571 pte.xwe = DTB_PTE_XWE(ipr[AlphaISA::IPR_DTB_PTE]); 572 pte.fonr = DTB_PTE_FONR(ipr[AlphaISA::IPR_DTB_PTE]); 573 pte.fonw = DTB_PTE_FONW(ipr[AlphaISA::IPR_DTB_PTE]); 574 pte.asma = DTB_PTE_ASMA(ipr[AlphaISA::IPR_DTB_PTE]); 575 pte.asn = DTB_ASN_ASN(ipr[AlphaISA::IPR_DTB_ASN]); 576 577 // insert new TAG/PTE value into data TLB 578 xc->getDTBPtr()->insert(val, pte); 579 } 580 break; 581 582 case AlphaISA::IPR_ITB_PTE: { 583 struct AlphaISA::PTE pte; 584 585 // FIXME: granularity hints NYI... 586 if (ITB_PTE_GH(val) != 0) 587 panic("PTE GH field != 0"); 588 589 // write entire quad 590 ipr[idx] = val; 591 592 // construct PTE for new entry 593 pte.ppn = ITB_PTE_PPN(val); 594 pte.xre = ITB_PTE_XRE(val); 595 pte.xwe = 0; 596 pte.fonr = ITB_PTE_FONR(val); 597 pte.fonw = ITB_PTE_FONW(val); 598 pte.asma = ITB_PTE_ASMA(val); 599 pte.asn = ITB_ASN_ASN(ipr[AlphaISA::IPR_ITB_ASN]); 600 601 // insert new TAG/PTE value into data TLB 602 xc->getITBPtr()->insert(ipr[AlphaISA::IPR_ITB_TAG], pte); 603 } 604 break; 605 606 case AlphaISA::IPR_ITB_IA: 607 // really a control write 608 ipr[idx] = 0; 609 610 xc->getITBPtr()->flushAll(); 611 break; 612 613 case AlphaISA::IPR_ITB_IAP: 614 // really a control write 615 ipr[idx] = 0; 616 617 xc->getITBPtr()->flushProcesses(); 618 break; 619 620 case AlphaISA::IPR_ITB_IS: 621 // really a control write 622 ipr[idx] = val; 623 624 xc->getITBPtr()->flushAddr(val, 625 ITB_ASN_ASN(ipr[AlphaISA::IPR_ITB_ASN])); 626 break; 627 628 default: 629 // invalid IPR 630 return UnimplementedOpcodeFault; 631 } 632 633 // no error... 634 return NoFault; 635} 636 637/** 638 * Check for special simulator handling of specific PAL calls. 639 * If return value is false, actual PAL call will be suppressed. 640 */ 641bool 642CPUExecContext::simPalCheck(int palFunc) 643{ 644 cpu->kernelStats->callpal(palFunc, proxy); 645 646 switch (palFunc) { 647 case PAL::halt: 648 halt(); 649 if (--System::numSystemsRunning == 0) 650 new SimExitEvent("all cpus halted"); 651 break; 652 653 case PAL::bpt: 654 case PAL::bugchk: 655 if (system->breakpoint()) 656 return false; 657 break; 658 } 659 660 return true; 661} 662 663//Forward instantiation for FastCPU object 664template 665void AlphaISA::processInterrupts(FastCPU *xc); 666 667//Forward instantiation for FastCPU object 668template 669void AlphaISA::zeroRegisters(FastCPU *xc); 670 671#endif // FULL_SYSTEM 672