1 /* 2 * QEMU RISC-V Native Debug Support 3 * 4 * Copyright (c) 2022 Wind River Systems, Inc. 5 * 6 * Author: 7 * Bin Meng <bin.meng@windriver.com> 8 * 9 * This provides the native debug support via the Trigger Module, as defined 10 * in the RISC-V Debug Specification: 11 * https://github.com/riscv/riscv-debug-spec/raw/master/riscv-debug-stable.pdf 12 * 13 * This program is free software; you can redistribute it and/or modify it 14 * under the terms and conditions of the GNU General Public License, 15 * version 2 or later, as published by the Free Software Foundation. 16 * 17 * This program is distributed in the hope it will be useful, but WITHOUT 18 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 19 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 20 * more details. 21 * 22 * You should have received a copy of the GNU General Public License along with 23 * this program. If not, see <http://www.gnu.org/licenses/>. 24 */ 25 26 #include "qemu/osdep.h" 27 #include "qemu/log.h" 28 #include "qapi/error.h" 29 #include "cpu.h" 30 #include "trace.h" 31 #include "exec/exec-all.h" 32 33 /* 34 * The following M-mode trigger CSRs are implemented: 35 * 36 * - tselect 37 * - tdata1 38 * - tdata2 39 * - tdata3 40 * 41 * We don't support writable 'type' field in the tdata1 register, so there is 42 * no need to implement the "tinfo" CSR. 43 * 44 * The following triggers are implemented: 45 * 46 * Index | Type | tdata mapping | Description 47 * ------+------+------------------------+------------ 48 * 0 | 2 | tdata1, tdata2 | Address / Data Match 49 * 1 | 2 | tdata1, tdata2 | Address / Data Match 50 */ 51 52 /* tdata availability of a trigger */ 53 typedef bool tdata_avail[TDATA_NUM]; 54 55 static tdata_avail tdata_mapping[TRIGGER_TYPE_NUM] = { 56 [TRIGGER_TYPE_NO_EXIST] = { false, false, false }, 57 [TRIGGER_TYPE_AD_MATCH] = { true, true, true }, 58 [TRIGGER_TYPE_INST_CNT] = { true, false, true }, 59 [TRIGGER_TYPE_INT] = { true, true, true }, 60 [TRIGGER_TYPE_EXCP] = { true, true, true }, 61 [TRIGGER_TYPE_AD_MATCH6] = { true, true, true }, 62 [TRIGGER_TYPE_EXT_SRC] = { true, false, false }, 63 [TRIGGER_TYPE_UNAVAIL] = { true, true, true } 64 }; 65 66 /* only breakpoint size 1/2/4/8 supported */ 67 static int access_size[SIZE_NUM] = { 68 [SIZE_ANY] = 0, 69 [SIZE_1B] = 1, 70 [SIZE_2B] = 2, 71 [SIZE_4B] = 4, 72 [SIZE_6B] = -1, 73 [SIZE_8B] = 8, 74 [6 ... 15] = -1, 75 }; 76 77 static inline target_ulong extract_trigger_type(CPURISCVState *env, 78 target_ulong tdata1) 79 { 80 switch (riscv_cpu_mxl(env)) { 81 case MXL_RV32: 82 return extract32(tdata1, 28, 4); 83 case MXL_RV64: 84 case MXL_RV128: 85 return extract64(tdata1, 60, 4); 86 default: 87 g_assert_not_reached(); 88 } 89 } 90 91 static inline target_ulong get_trigger_type(CPURISCVState *env, 92 target_ulong trigger_index) 93 { 94 target_ulong tdata1 = env->type2_trig[trigger_index].mcontrol; 95 return extract_trigger_type(env, tdata1); 96 } 97 98 static inline target_ulong trigger_type(CPURISCVState *env, 99 trigger_type_t type) 100 { 101 target_ulong tdata1; 102 103 switch (riscv_cpu_mxl(env)) { 104 case MXL_RV32: 105 tdata1 = RV32_TYPE(type); 106 break; 107 case MXL_RV64: 108 case MXL_RV128: 109 tdata1 = RV64_TYPE(type); 110 break; 111 default: 112 g_assert_not_reached(); 113 } 114 115 return tdata1; 116 } 117 118 bool tdata_available(CPURISCVState *env, int tdata_index) 119 { 120 int trigger_type = get_trigger_type(env, env->trigger_cur); 121 122 if (unlikely(tdata_index >= TDATA_NUM)) { 123 return false; 124 } 125 126 if (unlikely(env->trigger_cur >= RV_MAX_TRIGGERS)) { 127 return false; 128 } 129 130 return tdata_mapping[trigger_type][tdata_index]; 131 } 132 133 target_ulong tselect_csr_read(CPURISCVState *env) 134 { 135 return env->trigger_cur; 136 } 137 138 void tselect_csr_write(CPURISCVState *env, target_ulong val) 139 { 140 /* all target_ulong bits of tselect are implemented */ 141 env->trigger_cur = val; 142 } 143 144 static target_ulong tdata1_validate(CPURISCVState *env, target_ulong val, 145 trigger_type_t t) 146 { 147 uint32_t type, dmode; 148 target_ulong tdata1; 149 150 switch (riscv_cpu_mxl(env)) { 151 case MXL_RV32: 152 type = extract32(val, 28, 4); 153 dmode = extract32(val, 27, 1); 154 tdata1 = RV32_TYPE(t); 155 break; 156 case MXL_RV64: 157 case MXL_RV128: 158 type = extract64(val, 60, 4); 159 dmode = extract64(val, 59, 1); 160 tdata1 = RV64_TYPE(t); 161 break; 162 default: 163 g_assert_not_reached(); 164 } 165 166 if (type != t) { 167 qemu_log_mask(LOG_GUEST_ERROR, 168 "ignoring type write to tdata1 register\n"); 169 } 170 171 if (dmode != 0) { 172 qemu_log_mask(LOG_UNIMP, "debug mode is not supported\n"); 173 } 174 175 return tdata1; 176 } 177 178 static inline void warn_always_zero_bit(target_ulong val, target_ulong mask, 179 const char *msg) 180 { 181 if (val & mask) { 182 qemu_log_mask(LOG_UNIMP, "%s bit is always zero\n", msg); 183 } 184 } 185 186 static uint32_t type2_breakpoint_size(CPURISCVState *env, target_ulong ctrl) 187 { 188 uint32_t size, sizelo, sizehi = 0; 189 190 if (riscv_cpu_mxl(env) == MXL_RV64) { 191 sizehi = extract32(ctrl, 21, 2); 192 } 193 sizelo = extract32(ctrl, 16, 2); 194 size = (sizehi << 2) | sizelo; 195 196 return size; 197 } 198 199 static inline bool type2_breakpoint_enabled(target_ulong ctrl) 200 { 201 bool mode = !!(ctrl & (TYPE2_U | TYPE2_S | TYPE2_M)); 202 bool rwx = !!(ctrl & (TYPE2_LOAD | TYPE2_STORE | TYPE2_EXEC)); 203 204 return mode && rwx; 205 } 206 207 static target_ulong type2_mcontrol_validate(CPURISCVState *env, 208 target_ulong ctrl) 209 { 210 target_ulong val; 211 uint32_t size; 212 213 /* validate the generic part first */ 214 val = tdata1_validate(env, ctrl, TRIGGER_TYPE_AD_MATCH); 215 216 /* validate unimplemented (always zero) bits */ 217 warn_always_zero_bit(ctrl, TYPE2_MATCH, "match"); 218 warn_always_zero_bit(ctrl, TYPE2_CHAIN, "chain"); 219 warn_always_zero_bit(ctrl, TYPE2_ACTION, "action"); 220 warn_always_zero_bit(ctrl, TYPE2_TIMING, "timing"); 221 warn_always_zero_bit(ctrl, TYPE2_SELECT, "select"); 222 warn_always_zero_bit(ctrl, TYPE2_HIT, "hit"); 223 224 /* validate size encoding */ 225 size = type2_breakpoint_size(env, ctrl); 226 if (access_size[size] == -1) { 227 qemu_log_mask(LOG_UNIMP, "access size %d is not supported, using SIZE_ANY\n", 228 size); 229 } else { 230 val |= (ctrl & TYPE2_SIZELO); 231 if (riscv_cpu_mxl(env) == MXL_RV64) { 232 val |= (ctrl & TYPE2_SIZEHI); 233 } 234 } 235 236 /* keep the mode and attribute bits */ 237 val |= (ctrl & (TYPE2_U | TYPE2_S | TYPE2_M | 238 TYPE2_LOAD | TYPE2_STORE | TYPE2_EXEC)); 239 240 return val; 241 } 242 243 static void type2_breakpoint_insert(CPURISCVState *env, target_ulong index) 244 { 245 target_ulong ctrl = env->type2_trig[index].mcontrol; 246 target_ulong addr = env->type2_trig[index].maddress; 247 bool enabled = type2_breakpoint_enabled(ctrl); 248 CPUState *cs = env_cpu(env); 249 int flags = BP_CPU | BP_STOP_BEFORE_ACCESS; 250 uint32_t size; 251 252 if (!enabled) { 253 return; 254 } 255 256 if (ctrl & TYPE2_EXEC) { 257 cpu_breakpoint_insert(cs, addr, flags, &env->type2_trig[index].bp); 258 } 259 260 if (ctrl & TYPE2_LOAD) { 261 flags |= BP_MEM_READ; 262 } 263 if (ctrl & TYPE2_STORE) { 264 flags |= BP_MEM_WRITE; 265 } 266 267 if (flags & BP_MEM_ACCESS) { 268 size = type2_breakpoint_size(env, ctrl); 269 if (size != 0) { 270 cpu_watchpoint_insert(cs, addr, size, flags, 271 &env->type2_trig[index].wp); 272 } else { 273 cpu_watchpoint_insert(cs, addr, 8, flags, 274 &env->type2_trig[index].wp); 275 } 276 } 277 } 278 279 static void type2_breakpoint_remove(CPURISCVState *env, target_ulong index) 280 { 281 CPUState *cs = env_cpu(env); 282 283 if (env->type2_trig[index].bp) { 284 cpu_breakpoint_remove_by_ref(cs, env->type2_trig[index].bp); 285 env->type2_trig[index].bp = NULL; 286 } 287 288 if (env->type2_trig[index].wp) { 289 cpu_watchpoint_remove_by_ref(cs, env->type2_trig[index].wp); 290 env->type2_trig[index].wp = NULL; 291 } 292 } 293 294 static target_ulong type2_reg_read(CPURISCVState *env, 295 target_ulong index, int tdata_index) 296 { 297 target_ulong tdata; 298 299 switch (tdata_index) { 300 case TDATA1: 301 tdata = env->type2_trig[index].mcontrol; 302 break; 303 case TDATA2: 304 tdata = env->type2_trig[index].maddress; 305 break; 306 default: 307 g_assert_not_reached(); 308 } 309 310 return tdata; 311 } 312 313 static void type2_reg_write(CPURISCVState *env, target_ulong index, 314 int tdata_index, target_ulong val) 315 { 316 target_ulong new_val; 317 318 switch (tdata_index) { 319 case TDATA1: 320 new_val = type2_mcontrol_validate(env, val); 321 if (new_val != env->type2_trig[index].mcontrol) { 322 env->type2_trig[index].mcontrol = new_val; 323 type2_breakpoint_remove(env, index); 324 type2_breakpoint_insert(env, index); 325 } 326 break; 327 case TDATA2: 328 if (val != env->type2_trig[index].maddress) { 329 env->type2_trig[index].maddress = val; 330 type2_breakpoint_remove(env, index); 331 type2_breakpoint_insert(env, index); 332 } 333 break; 334 default: 335 g_assert_not_reached(); 336 } 337 338 return; 339 } 340 341 target_ulong tdata_csr_read(CPURISCVState *env, int tdata_index) 342 { 343 int trigger_type = get_trigger_type(env, env->trigger_cur); 344 345 switch (trigger_type) { 346 case TRIGGER_TYPE_AD_MATCH: 347 return type2_reg_read(env, env->trigger_cur, tdata_index); 348 break; 349 case TRIGGER_TYPE_INST_CNT: 350 case TRIGGER_TYPE_INT: 351 case TRIGGER_TYPE_EXCP: 352 case TRIGGER_TYPE_AD_MATCH6: 353 case TRIGGER_TYPE_EXT_SRC: 354 qemu_log_mask(LOG_UNIMP, "trigger type: %d is not supported\n", 355 trigger_type); 356 break; 357 case TRIGGER_TYPE_NO_EXIST: 358 case TRIGGER_TYPE_UNAVAIL: 359 qemu_log_mask(LOG_GUEST_ERROR, "trigger type: %d does not exit\n", 360 trigger_type); 361 break; 362 default: 363 g_assert_not_reached(); 364 } 365 366 return 0; 367 } 368 369 void tdata_csr_write(CPURISCVState *env, int tdata_index, target_ulong val) 370 { 371 int trigger_type; 372 373 if (tdata_index == TDATA1) { 374 trigger_type = extract_trigger_type(env, val); 375 } else { 376 trigger_type = get_trigger_type(env, env->trigger_cur); 377 } 378 379 switch (trigger_type) { 380 case TRIGGER_TYPE_AD_MATCH: 381 type2_reg_write(env, env->trigger_cur, tdata_index, val); 382 break; 383 case TRIGGER_TYPE_INST_CNT: 384 case TRIGGER_TYPE_INT: 385 case TRIGGER_TYPE_EXCP: 386 case TRIGGER_TYPE_AD_MATCH6: 387 case TRIGGER_TYPE_EXT_SRC: 388 qemu_log_mask(LOG_UNIMP, "trigger type: %d is not supported\n", 389 trigger_type); 390 break; 391 case TRIGGER_TYPE_NO_EXIST: 392 case TRIGGER_TYPE_UNAVAIL: 393 qemu_log_mask(LOG_GUEST_ERROR, "trigger type: %d does not exit\n", 394 trigger_type); 395 break; 396 default: 397 g_assert_not_reached(); 398 } 399 } 400 401 void riscv_cpu_debug_excp_handler(CPUState *cs) 402 { 403 RISCVCPU *cpu = RISCV_CPU(cs); 404 CPURISCVState *env = &cpu->env; 405 406 if (cs->watchpoint_hit) { 407 if (cs->watchpoint_hit->flags & BP_CPU) { 408 cs->watchpoint_hit = NULL; 409 riscv_raise_exception(env, RISCV_EXCP_BREAKPOINT, 0); 410 } 411 } else { 412 if (cpu_breakpoint_test(cs, env->pc, BP_CPU)) { 413 riscv_raise_exception(env, RISCV_EXCP_BREAKPOINT, 0); 414 } 415 } 416 } 417 418 bool riscv_cpu_debug_check_breakpoint(CPUState *cs) 419 { 420 RISCVCPU *cpu = RISCV_CPU(cs); 421 CPURISCVState *env = &cpu->env; 422 CPUBreakpoint *bp; 423 target_ulong ctrl; 424 target_ulong pc; 425 int trigger_type; 426 int i; 427 428 QTAILQ_FOREACH(bp, &cs->breakpoints, entry) { 429 for (i = 0; i < RV_MAX_TRIGGERS; i++) { 430 trigger_type = get_trigger_type(env, i); 431 432 switch (trigger_type) { 433 case TRIGGER_TYPE_AD_MATCH: 434 ctrl = env->type2_trig[i].mcontrol; 435 pc = env->type2_trig[i].maddress; 436 437 if ((ctrl & TYPE2_EXEC) && (bp->pc == pc)) { 438 /* check U/S/M bit against current privilege level */ 439 if ((ctrl >> 3) & BIT(env->priv)) { 440 return true; 441 } 442 } 443 break; 444 default: 445 /* other trigger types are not supported or irrelevant */ 446 break; 447 } 448 } 449 } 450 451 return false; 452 } 453 454 bool riscv_cpu_debug_check_watchpoint(CPUState *cs, CPUWatchpoint *wp) 455 { 456 RISCVCPU *cpu = RISCV_CPU(cs); 457 CPURISCVState *env = &cpu->env; 458 target_ulong ctrl; 459 target_ulong addr; 460 int trigger_type; 461 int flags; 462 int i; 463 464 for (i = 0; i < RV_MAX_TRIGGERS; i++) { 465 trigger_type = get_trigger_type(env, i); 466 467 switch (trigger_type) { 468 case TRIGGER_TYPE_AD_MATCH: 469 ctrl = env->type2_trig[i].mcontrol; 470 addr = env->type2_trig[i].maddress; 471 flags = 0; 472 473 if (ctrl & TYPE2_LOAD) { 474 flags |= BP_MEM_READ; 475 } 476 if (ctrl & TYPE2_STORE) { 477 flags |= BP_MEM_WRITE; 478 } 479 480 if ((wp->flags & flags) && (wp->vaddr == addr)) { 481 /* check U/S/M bit against current privilege level */ 482 if ((ctrl >> 3) & BIT(env->priv)) { 483 return true; 484 } 485 } 486 break; 487 default: 488 /* other trigger types are not supported */ 489 break; 490 } 491 } 492 493 return false; 494 } 495 496 void riscv_trigger_init(CPURISCVState *env) 497 { 498 target_ulong tdata1 = trigger_type(env, TRIGGER_TYPE_AD_MATCH); 499 int i; 500 501 /* init to type 2 triggers */ 502 for (i = 0; i < RV_MAX_TRIGGERS; i++) { 503 /* 504 * type = TRIGGER_TYPE_AD_MATCH 505 * dmode = 0 (both debug and M-mode can write tdata) 506 * maskmax = 0 (unimplemented, always 0) 507 * sizehi = 0 (match against any size, RV64 only) 508 * hit = 0 (unimplemented, always 0) 509 * select = 0 (always 0, perform match on address) 510 * timing = 0 (always 0, trigger before instruction) 511 * sizelo = 0 (match against any size) 512 * action = 0 (always 0, raise a breakpoint exception) 513 * chain = 0 (unimplemented, always 0) 514 * match = 0 (always 0, when any compare value equals tdata2) 515 */ 516 env->type2_trig[i].mcontrol = tdata1; 517 env->type2_trig[i].maddress = 0; 518 env->type2_trig[i].bp = NULL; 519 env->type2_trig[i].wp = NULL; 520 } 521 } 522