Commit fe25591e7b98386cce2c9ec8a8878947b50e3741

Authored by aurel32
1 parent 0b6d3ae0

SH4: Privilege check for instructions

This patch adds check for all SH4 instructions which are
executed only in privileged mode.

(Shin-ichiro KAWASAKI)

git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5224 c046a42c-6fe2-441c-8c8c-71466251a162
cpu-exec.c
@@ -209,7 +209,10 @@ static inline TranslationBlock *tb_find_fast(void) @@ -209,7 +209,10 @@ static inline TranslationBlock *tb_find_fast(void)
209 cs_base = 0; 209 cs_base = 0;
210 pc = env->pc; 210 pc = env->pc;
211 #elif defined(TARGET_SH4) 211 #elif defined(TARGET_SH4)
212 - flags = env->flags; 212 + flags = (env->flags & (DELAY_SLOT | DELAY_SLOT_CONDITIONAL
  213 + | DELAY_SLOT_TRUE | DELAY_SLOT_CLEARME)) /* Bits 0- 3 */
  214 + | (env->fpscr & (FPSCR_FR | FPSCR_SZ | FPSCR_PR)) /* Bits 19-21 */
  215 + | (env->sr & (SR_MD | SR_RB)); /* Bits 29-30 */
213 cs_base = 0; 216 cs_base = 0;
214 pc = env->pc; 217 pc = env->pc;
215 #elif defined(TARGET_ALPHA) 218 #elif defined(TARGET_ALPHA)
target-sh4/translate.c
@@ -48,6 +48,12 @@ typedef struct DisasContext { @@ -48,6 +48,12 @@ typedef struct DisasContext {
48 int singlestep_enabled; 48 int singlestep_enabled;
49 } DisasContext; 49 } DisasContext;
50 50
  51 +#if defined(CONFIG_USER_ONLY)
  52 +#define IS_USER(ctx) 1
  53 +#else
  54 +#define IS_USER(ctx) (!(ctx->sr & SR_MD))
  55 +#endif
  56 +
51 enum { 57 enum {
52 BS_NONE = 0, /* We go out of the TB without reaching a branch or an 58 BS_NONE = 0, /* We go out of the TB without reaching a branch or an
53 * exception condition 59 * exception condition
@@ -449,6 +455,13 @@ static inline void gen_store_fpr64 (TCGv t, int reg) @@ -449,6 +455,13 @@ static inline void gen_store_fpr64 (TCGv t, int reg)
449 {tcg_gen_helper_0_0(helper_raise_slot_illegal_instruction); ctx->bstate = BS_EXCP; \ 455 {tcg_gen_helper_0_0(helper_raise_slot_illegal_instruction); ctx->bstate = BS_EXCP; \
450 return;} 456 return;}
451 457
  458 +#define CHECK_PRIVILEGED \
  459 + if (IS_USER(ctx)) { \
  460 + tcg_gen_helper_0_0(helper_raise_illegal_instruction); \
  461 + ctx->bstate = BS_EXCP; \
  462 + return; \
  463 + }
  464 +
452 void _decode_opc(DisasContext * ctx) 465 void _decode_opc(DisasContext * ctx)
453 { 466 {
454 #if 0 467 #if 0
@@ -475,13 +488,11 @@ void _decode_opc(DisasContext * ctx) @@ -475,13 +488,11 @@ void _decode_opc(DisasContext * ctx)
475 gen_clr_t(); 488 gen_clr_t();
476 return; 489 return;
477 case 0x0038: /* ldtlb */ 490 case 0x0038: /* ldtlb */
478 -#if defined(CONFIG_USER_ONLY)  
479 - assert(0); /* XXXXX */  
480 -#else 491 + CHECK_PRIVILEGED
481 tcg_gen_helper_0_0(helper_ldtlb); 492 tcg_gen_helper_0_0(helper_ldtlb);
482 -#endif  
483 return; 493 return;
484 case 0x002b: /* rte */ 494 case 0x002b: /* rte */
  495 + CHECK_PRIVILEGED
485 CHECK_NOT_DELAY_SLOT 496 CHECK_NOT_DELAY_SLOT
486 tcg_gen_mov_i32(cpu_sr, cpu_ssr); 497 tcg_gen_mov_i32(cpu_sr, cpu_ssr);
487 tcg_gen_mov_i32(cpu_delayed_pc, cpu_spc); 498 tcg_gen_mov_i32(cpu_delayed_pc, cpu_spc);
@@ -505,12 +516,8 @@ void _decode_opc(DisasContext * ctx) @@ -505,12 +516,8 @@ void _decode_opc(DisasContext * ctx)
505 case 0x0009: /* nop */ 516 case 0x0009: /* nop */
506 return; 517 return;
507 case 0x001b: /* sleep */ 518 case 0x001b: /* sleep */
508 - if (ctx->memidx) {  
509 - tcg_gen_helper_0_1(helper_sleep, tcg_const_i32(ctx->pc + 2));  
510 - } else {  
511 - tcg_gen_helper_0_0(helper_raise_illegal_instruction);  
512 - ctx->bstate = BS_EXCP;  
513 - } 519 + CHECK_PRIVILEGED
  520 + tcg_gen_helper_0_1(helper_sleep, tcg_const_i32(ctx->pc + 2));
514 return; 521 return;
515 } 522 }
516 523
@@ -1351,16 +1358,20 @@ void _decode_opc(DisasContext * ctx) @@ -1351,16 +1358,20 @@ void _decode_opc(DisasContext * ctx)
1351 1358
1352 switch (ctx->opcode & 0xf08f) { 1359 switch (ctx->opcode & 0xf08f) {
1353 case 0x408e: /* ldc Rm,Rn_BANK */ 1360 case 0x408e: /* ldc Rm,Rn_BANK */
  1361 + CHECK_PRIVILEGED
1354 tcg_gen_mov_i32(ALTREG(B6_4), REG(B11_8)); 1362 tcg_gen_mov_i32(ALTREG(B6_4), REG(B11_8));
1355 return; 1363 return;
1356 case 0x4087: /* ldc.l @Rm+,Rn_BANK */ 1364 case 0x4087: /* ldc.l @Rm+,Rn_BANK */
  1365 + CHECK_PRIVILEGED
1357 tcg_gen_qemu_ld32s(ALTREG(B6_4), REG(B11_8), ctx->memidx); 1366 tcg_gen_qemu_ld32s(ALTREG(B6_4), REG(B11_8), ctx->memidx);
1358 tcg_gen_addi_i32(REG(B11_8), REG(B11_8), 4); 1367 tcg_gen_addi_i32(REG(B11_8), REG(B11_8), 4);
1359 return; 1368 return;
1360 case 0x0082: /* stc Rm_BANK,Rn */ 1369 case 0x0082: /* stc Rm_BANK,Rn */
  1370 + CHECK_PRIVILEGED
1361 tcg_gen_mov_i32(REG(B11_8), ALTREG(B6_4)); 1371 tcg_gen_mov_i32(REG(B11_8), ALTREG(B6_4));
1362 return; 1372 return;
1363 case 0x4083: /* stc.l Rm_BANK,@-Rn */ 1373 case 0x4083: /* stc.l Rm_BANK,@-Rn */
  1374 + CHECK_PRIVILEGED
1364 { 1375 {
1365 TCGv addr = tcg_temp_new(TCG_TYPE_I32); 1376 TCGv addr = tcg_temp_new(TCG_TYPE_I32);
1366 tcg_gen_subi_i32(addr, REG(B11_8), 4); 1377 tcg_gen_subi_i32(addr, REG(B11_8), 4);
@@ -1408,11 +1419,13 @@ void _decode_opc(DisasContext * ctx) @@ -1408,11 +1419,13 @@ void _decode_opc(DisasContext * ctx)
1408 ctx->flags |= DELAY_SLOT; 1419 ctx->flags |= DELAY_SLOT;
1409 ctx->delayed_pc = (uint32_t) - 1; 1420 ctx->delayed_pc = (uint32_t) - 1;
1410 return; 1421 return;
1411 - case 0x400e: /* lds Rm,SR */ 1422 + case 0x400e: /* ldc Rm,SR */
  1423 + CHECK_PRIVILEGED
1412 tcg_gen_andi_i32(cpu_sr, REG(B11_8), 0x700083f3); 1424 tcg_gen_andi_i32(cpu_sr, REG(B11_8), 0x700083f3);
1413 ctx->bstate = BS_STOP; 1425 ctx->bstate = BS_STOP;
1414 return; 1426 return;
1415 - case 0x4007: /* lds.l @Rm+,SR */ 1427 + case 0x4007: /* ldc.l @Rm+,SR */
  1428 + CHECK_PRIVILEGED
1416 { 1429 {
1417 TCGv val = tcg_temp_new(TCG_TYPE_I32); 1430 TCGv val = tcg_temp_new(TCG_TYPE_I32);
1418 tcg_gen_qemu_ld32s(val, REG(B11_8), ctx->memidx); 1431 tcg_gen_qemu_ld32s(val, REG(B11_8), ctx->memidx);
@@ -1422,10 +1435,12 @@ void _decode_opc(DisasContext * ctx) @@ -1422,10 +1435,12 @@ void _decode_opc(DisasContext * ctx)
1422 ctx->bstate = BS_STOP; 1435 ctx->bstate = BS_STOP;
1423 } 1436 }
1424 return; 1437 return;
1425 - case 0x0002: /* sts SR,Rn */ 1438 + case 0x0002: /* stc SR,Rn */
  1439 + CHECK_PRIVILEGED
1426 tcg_gen_mov_i32(REG(B11_8), cpu_sr); 1440 tcg_gen_mov_i32(REG(B11_8), cpu_sr);
1427 return; 1441 return;
1428 - case 0x4003: /* sts SR,@-Rn */ 1442 + case 0x4003: /* stc SR,@-Rn */
  1443 + CHECK_PRIVILEGED
1429 { 1444 {
1430 TCGv addr = tcg_temp_new(TCG_TYPE_I32); 1445 TCGv addr = tcg_temp_new(TCG_TYPE_I32);
1431 tcg_gen_subi_i32(addr, REG(B11_8), 4); 1446 tcg_gen_subi_i32(addr, REG(B11_8), 4);
@@ -1434,18 +1449,22 @@ void _decode_opc(DisasContext * ctx) @@ -1434,18 +1449,22 @@ void _decode_opc(DisasContext * ctx)
1434 tcg_gen_subi_i32(REG(B11_8), REG(B11_8), 4); 1449 tcg_gen_subi_i32(REG(B11_8), REG(B11_8), 4);
1435 } 1450 }
1436 return; 1451 return;
1437 -#define LDST(reg,ldnum,ldpnum,stnum,stpnum) \ 1452 +#define LDST(reg,ldnum,ldpnum,stnum,stpnum,prechk) \
1438 case ldnum: \ 1453 case ldnum: \
  1454 + prechk \
1439 tcg_gen_mov_i32 (cpu_##reg, REG(B11_8)); \ 1455 tcg_gen_mov_i32 (cpu_##reg, REG(B11_8)); \
1440 return; \ 1456 return; \
1441 case ldpnum: \ 1457 case ldpnum: \
  1458 + prechk \
1442 tcg_gen_qemu_ld32s (cpu_##reg, REG(B11_8), ctx->memidx); \ 1459 tcg_gen_qemu_ld32s (cpu_##reg, REG(B11_8), ctx->memidx); \
1443 tcg_gen_addi_i32(REG(B11_8), REG(B11_8), 4); \ 1460 tcg_gen_addi_i32(REG(B11_8), REG(B11_8), 4); \
1444 return; \ 1461 return; \
1445 case stnum: \ 1462 case stnum: \
  1463 + prechk \
1446 tcg_gen_mov_i32 (REG(B11_8), cpu_##reg); \ 1464 tcg_gen_mov_i32 (REG(B11_8), cpu_##reg); \
1447 return; \ 1465 return; \
1448 case stpnum: \ 1466 case stpnum: \
  1467 + prechk \
1449 { \ 1468 { \
1450 TCGv addr = tcg_temp_new(TCG_TYPE_I32); \ 1469 TCGv addr = tcg_temp_new(TCG_TYPE_I32); \
1451 tcg_gen_subi_i32(addr, REG(B11_8), 4); \ 1470 tcg_gen_subi_i32(addr, REG(B11_8), 4); \
@@ -1454,15 +1473,15 @@ void _decode_opc(DisasContext * ctx) @@ -1454,15 +1473,15 @@ void _decode_opc(DisasContext * ctx)
1454 tcg_gen_subi_i32(REG(B11_8), REG(B11_8), 4); \ 1473 tcg_gen_subi_i32(REG(B11_8), REG(B11_8), 4); \
1455 } \ 1474 } \
1456 return; 1475 return;
1457 - LDST(gbr, 0x401e, 0x4017, 0x0012, 0x4013)  
1458 - LDST(vbr, 0x402e, 0x4027, 0x0022, 0x4023)  
1459 - LDST(ssr, 0x403e, 0x4037, 0x0032, 0x4033)  
1460 - LDST(spc, 0x404e, 0x4047, 0x0042, 0x4043)  
1461 - LDST(dbr, 0x40fa, 0x40f6, 0x00fa, 0x40f2)  
1462 - LDST(mach, 0x400a, 0x4006, 0x000a, 0x4002)  
1463 - LDST(macl, 0x401a, 0x4016, 0x001a, 0x4012)  
1464 - LDST(pr, 0x402a, 0x4026, 0x002a, 0x4022)  
1465 - LDST(fpul, 0x405a, 0x4056, 0x005a, 0x4052) 1476 + LDST(gbr, 0x401e, 0x4017, 0x0012, 0x4013, {})
  1477 + LDST(vbr, 0x402e, 0x4027, 0x0022, 0x4023, CHECK_PRIVILEGED)
  1478 + LDST(ssr, 0x403e, 0x4037, 0x0032, 0x4033, CHECK_PRIVILEGED)
  1479 + LDST(spc, 0x404e, 0x4047, 0x0042, 0x4043, CHECK_PRIVILEGED)
  1480 + LDST(dbr, 0x40fa, 0x40f6, 0x00fa, 0x40f2, CHECK_PRIVILEGED)
  1481 + LDST(mach, 0x400a, 0x4006, 0x000a, 0x4002, {})
  1482 + LDST(macl, 0x401a, 0x4016, 0x001a, 0x4012, {})
  1483 + LDST(pr, 0x402a, 0x4026, 0x002a, 0x4022, {})
  1484 + LDST(fpul, 0x405a, 0x4056, 0x005a, 0x4052, {})
1466 case 0x406a: /* lds Rm,FPSCR */ 1485 case 0x406a: /* lds Rm,FPSCR */
1467 tcg_gen_helper_0_1(helper_ld_fpscr, REG(B11_8)); 1486 tcg_gen_helper_0_1(helper_ld_fpscr, REG(B11_8));
1468 ctx->bstate = BS_STOP; 1487 ctx->bstate = BS_STOP;