Commit 497ad68cd499bf2b6cc3bfde49fdb5aa05934ec4
1 parent
185f0762
Fix TB chaining for exceptions.
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@3721 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
1 changed file
with
17 additions
and
35 deletions
cpu-exec.c
| ... | ... | @@ -232,6 +232,11 @@ static inline TranslationBlock *tb_find_fast(void) |
| 232 | 232 | return tb; |
| 233 | 233 | } |
| 234 | 234 | |
| 235 | +#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 236 | +#define BREAK_CHAIN tmp_T0 = 0 | |
| 237 | +#else | |
| 238 | +#define BREAK_CHAIN T0 = 0 | |
| 239 | +#endif | |
| 235 | 240 | |
| 236 | 241 | /* main execution loop */ |
| 237 | 242 | |
| ... | ... | @@ -405,11 +410,7 @@ int cpu_exec(CPUState *env1) |
| 405 | 410 | svm_check_intercept(SVM_EXIT_SMI); |
| 406 | 411 | env->interrupt_request &= ~CPU_INTERRUPT_SMI; |
| 407 | 412 | do_smm_enter(); |
| 408 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 409 | - tmp_T0 = 0; | |
| 410 | -#else | |
| 411 | - T0 = 0; | |
| 412 | -#endif | |
| 413 | + BREAK_CHAIN; | |
| 413 | 414 | } else if ((interrupt_request & CPU_INTERRUPT_HARD) && |
| 414 | 415 | (env->eflags & IF_MASK || env->hflags & HF_HIF_MASK) && |
| 415 | 416 | !(env->hflags & HF_INHIBIT_IRQ_MASK)) { |
| ... | ... | @@ -423,11 +424,7 @@ int cpu_exec(CPUState *env1) |
| 423 | 424 | do_interrupt(intno, 0, 0, 0, 1); |
| 424 | 425 | /* ensure that no TB jump will be modified as |
| 425 | 426 | the program flow was changed */ |
| 426 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 427 | - tmp_T0 = 0; | |
| 428 | -#else | |
| 429 | - T0 = 0; | |
| 430 | -#endif | |
| 427 | + BREAK_CHAIN; | |
| 431 | 428 | #if !defined(CONFIG_USER_ONLY) |
| 432 | 429 | } else if ((interrupt_request & CPU_INTERRUPT_VIRQ) && |
| 433 | 430 | (env->eflags & IF_MASK) && !(env->hflags & HF_INHIBIT_IRQ_MASK)) { |
| ... | ... | @@ -441,11 +438,7 @@ int cpu_exec(CPUState *env1) |
| 441 | 438 | do_interrupt(intno, 0, 0, -1, 1); |
| 442 | 439 | stl_phys(env->vm_vmcb + offsetof(struct vmcb, control.int_ctl), |
| 443 | 440 | ldl_phys(env->vm_vmcb + offsetof(struct vmcb, control.int_ctl)) & ~V_IRQ_MASK); |
| 444 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 445 | - tmp_T0 = 0; | |
| 446 | -#else | |
| 447 | - T0 = 0; | |
| 448 | -#endif | |
| 441 | + BREAK_CHAIN; | |
| 449 | 442 | #endif |
| 450 | 443 | } |
| 451 | 444 | #elif defined(TARGET_PPC) |
| ... | ... | @@ -458,11 +451,7 @@ int cpu_exec(CPUState *env1) |
| 458 | 451 | ppc_hw_interrupt(env); |
| 459 | 452 | if (env->pending_interrupts == 0) |
| 460 | 453 | env->interrupt_request &= ~CPU_INTERRUPT_HARD; |
| 461 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 462 | - tmp_T0 = 0; | |
| 463 | -#else | |
| 464 | - T0 = 0; | |
| 465 | -#endif | |
| 454 | + BREAK_CHAIN; | |
| 466 | 455 | } |
| 467 | 456 | #elif defined(TARGET_MIPS) |
| 468 | 457 | if ((interrupt_request & CPU_INTERRUPT_HARD) && |
| ... | ... | @@ -475,11 +464,7 @@ int cpu_exec(CPUState *env1) |
| 475 | 464 | env->exception_index = EXCP_EXT_INTERRUPT; |
| 476 | 465 | env->error_code = 0; |
| 477 | 466 | do_interrupt(env); |
| 478 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 479 | - tmp_T0 = 0; | |
| 480 | -#else | |
| 481 | - T0 = 0; | |
| 482 | -#endif | |
| 467 | + BREAK_CHAIN; | |
| 483 | 468 | } |
| 484 | 469 | #elif defined(TARGET_SPARC) |
| 485 | 470 | if ((interrupt_request & CPU_INTERRUPT_HARD) && |
| ... | ... | @@ -496,11 +481,7 @@ int cpu_exec(CPUState *env1) |
| 496 | 481 | #if !defined(TARGET_SPARC64) && !defined(CONFIG_USER_ONLY) |
| 497 | 482 | cpu_check_irqs(env); |
| 498 | 483 | #endif |
| 499 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 500 | - tmp_T0 = 0; | |
| 501 | -#else | |
| 502 | - T0 = 0; | |
| 503 | -#endif | |
| 484 | + BREAK_CHAIN; | |
| 504 | 485 | } |
| 505 | 486 | } else if (interrupt_request & CPU_INTERRUPT_TIMER) { |
| 506 | 487 | //do_interrupt(0, 0, 0, 0, 0); |
| ... | ... | @@ -511,6 +492,7 @@ int cpu_exec(CPUState *env1) |
| 511 | 492 | && !(env->uncached_cpsr & CPSR_F)) { |
| 512 | 493 | env->exception_index = EXCP_FIQ; |
| 513 | 494 | do_interrupt(env); |
| 495 | + BREAK_CHAIN; | |
| 514 | 496 | } |
| 515 | 497 | /* ARMv7-M interrupt return works by loading a magic value |
| 516 | 498 | into the PC. On real hardware the load causes the |
| ... | ... | @@ -526,17 +508,20 @@ int cpu_exec(CPUState *env1) |
| 526 | 508 | || !(env->uncached_cpsr & CPSR_I))) { |
| 527 | 509 | env->exception_index = EXCP_IRQ; |
| 528 | 510 | do_interrupt(env); |
| 511 | + BREAK_CHAIN; | |
| 529 | 512 | } |
| 530 | 513 | #elif defined(TARGET_SH4) |
| 531 | 514 | /* XXXXX */ |
| 532 | 515 | #elif defined(TARGET_ALPHA) |
| 533 | 516 | if (interrupt_request & CPU_INTERRUPT_HARD) { |
| 534 | 517 | do_interrupt(env); |
| 518 | + BREAK_CHAIN; | |
| 535 | 519 | } |
| 536 | 520 | #elif defined(TARGET_CRIS) |
| 537 | 521 | if (interrupt_request & CPU_INTERRUPT_HARD) { |
| 538 | 522 | do_interrupt(env); |
| 539 | 523 | env->interrupt_request &= ~CPU_INTERRUPT_HARD; |
| 524 | + BREAK_CHAIN; | |
| 540 | 525 | } |
| 541 | 526 | #elif defined(TARGET_M68K) |
| 542 | 527 | if (interrupt_request & CPU_INTERRUPT_HARD |
| ... | ... | @@ -549,6 +534,7 @@ int cpu_exec(CPUState *env1) |
| 549 | 534 | first signalled. */ |
| 550 | 535 | env->exception_index = env->pending_vector; |
| 551 | 536 | do_interrupt(1); |
| 537 | + BREAK_CHAIN; | |
| 552 | 538 | } |
| 553 | 539 | #endif |
| 554 | 540 | /* Don't use the cached interupt_request value, |
| ... | ... | @@ -557,11 +543,7 @@ int cpu_exec(CPUState *env1) |
| 557 | 543 | env->interrupt_request &= ~CPU_INTERRUPT_EXITTB; |
| 558 | 544 | /* ensure that no TB jump will be modified as |
| 559 | 545 | the program flow was changed */ |
| 560 | -#if defined(__sparc__) && !defined(HOST_SOLARIS) | |
| 561 | - tmp_T0 = 0; | |
| 562 | -#else | |
| 563 | - T0 = 0; | |
| 564 | -#endif | |
| 546 | + BREAK_CHAIN; | |
| 565 | 547 | } |
| 566 | 548 | if (interrupt_request & CPU_INTERRUPT_EXIT) { |
| 567 | 549 | env->interrupt_request &= ~CPU_INTERRUPT_EXIT; | ... | ... |