diff --git a/sys/amd64/amd64/db_trace.c b/sys/amd64/amd64/db_trace.c index bd737dd28baa..880be61a5839 100644 --- a/sys/amd64/amd64/db_trace.c +++ b/sys/amd64/amd64/db_trace.c @@ -562,7 +562,7 @@ amd64_set_watch(watchnum, watchaddr, size, access, d) } /* - * we can watch a 1, 2, or 4 byte sized location + * we can watch a 1, 2, 4, or 8 byte sized location */ switch (size) { case 1: @@ -574,6 +574,9 @@ amd64_set_watch(watchnum, watchaddr, size, access, d) case 4: len = DBREG_DR7_LEN_4; break; + case 8: + len = DBREG_DR7_LEN_8; + break; default: return (-1); } @@ -624,12 +627,14 @@ db_md_set_watchpoint(addr, size) avail++; } - if (avail * 4 < size) + if (avail * 8 < size) return (-1); for (i = 0; i < 4 && (size > 0); i++) { if (!DBREG_DR7_ENABLED(d.dr[7], i)) { - if (size > 2) + if (size >= 8 || (avail == 1 && size > 4)) + wsize = 8; + else if (size > 2) wsize = 4; else wsize = size; @@ -637,6 +642,7 @@ db_md_set_watchpoint(addr, size) DBREG_DR7_WRONLY, &d); addr += wsize; size -= wsize; + avail--; } } @@ -699,8 +705,12 @@ db_md_list_watchpoints() if (DBREG_DR7_ENABLED(d.dr[7], i)) { type = DBREG_DR7_ACCESS(d.dr[7], i); len = DBREG_DR7_LEN(d.dr[7], i); + if (len == DBREG_DR7_LEN_8) + len = 8; + else + len++; db_printf(" %-5d %-8s %10s %3d ", - i, "enabled", watchtype_str(type), len + 1); + i, "enabled", watchtype_str(type), len); db_printsym((db_addr_t)DBREG_DRX((&d), i), DB_STGY_ANY); db_printf("\n"); } else { diff --git a/sys/amd64/amd64/machdep.c b/sys/amd64/amd64/machdep.c index 6c9801029894..67469e0b282d 100644 --- a/sys/amd64/amd64/machdep.c +++ b/sys/amd64/amd64/machdep.c @@ -1711,7 +1711,8 @@ set_dbregs(struct thread *td, struct dbreg *dbregs) for (i = 0; i < 4; i++) { if (DBREG_DR7_ACCESS(dbregs->dr[7], i) == 0x02) return (EINVAL); - if (DBREG_DR7_LEN(dbregs->dr[7], i) == 0x02) + if (td->td_frame->tf_cs == _ucode32sel && + DBREG_DR7_LEN(dbregs->dr[7], i) == DBREG_DR7_LEN_8) return (EINVAL); } if ((dbregs->dr[6] & 0xffffffff00000000ul) != 0 || diff --git a/sys/amd64/include/reg.h b/sys/amd64/include/reg.h index 9358f056b69d..9ca092fea104 100644 --- a/sys/amd64/include/reg.h +++ b/sys/amd64/include/reg.h @@ -97,6 +97,7 @@ struct dbreg { #define DBREG_DR7_LEN_1 0x00 /* 1 byte length */ #define DBREG_DR7_LEN_2 0x01 #define DBREG_DR7_LEN_4 0x03 +#define DBREG_DR7_LEN_8 0x02 #define DBREG_DR7_EXEC 0x00 /* break on execute */ #define DBREG_DR7_WRONLY 0x01 /* break on write */ #define DBREG_DR7_RDWR 0x03 /* break on read or write */