diff options
author | Cyril Bur <cyrilbur@gmail.com> | 2018-02-14 15:27:41 +1100 |
---|---|---|
committer | Alistair Popple <alistair@popple.id.au> | 2018-02-16 16:22:23 +1100 |
commit | 01b39f4737a7e3a5bb9d1e01d6e1f18d20a5b739 (patch) | |
tree | ed2c05503b61bf25de664c8d9fe68392633c652c | |
parent | 7407afd8b49f4ce178b6b5acd5b95044838b1482 (diff) | |
download | pdbg-01b39f4737a7e3a5bb9d1e01d6e1f18d20a5b739.tar.gz pdbg-01b39f4737a7e3a5bb9d1e01d6e1f18d20a5b739.zip |
libpdbg/htm: Add POWER8 HTM (both Core and Nest)
Signed-off-by: Cyril Bur <cyrilbur@gmail.com>
-rw-r--r-- | libpdbg/htm.c | 165 | ||||
-rw-r--r-- | p8-pib.dts.m4 | 11 |
2 files changed, 146 insertions, 30 deletions
diff --git a/libpdbg/htm.c b/libpdbg/htm.c index 692b4e0..4c1ee01 100644 --- a/libpdbg/htm.c +++ b/libpdbg/htm.c @@ -40,7 +40,9 @@ #define MIN(x,y) ((x < y) ? x : y) -#define DEBUGFS_MEMTRACE "/sys/kernel/debug/powerpc/memtrace" +#define DEBUGFS_POWERPC "/sys/kernel/debug/powerpc" +#define DEBUGFS_SCOM DEBUGFS_POWERPC"/scom" +#define DEBUGFS_MEMTRACE DEBUGFS_POWERPC"/memtrace" #define DEBUGFS_MEMTRACE_ENABLE DEBUGFS_MEMTRACE"/enable" #define HTM_COLLECTION_MODE 0 @@ -49,6 +51,7 @@ #define NHTM_MODE_CAPTURE PPC_BITMASK(4,12) #define NHTM_MODE_CAPTURE_PMISC PPC_BIT(5) #define NHTM_MODE_CRESP_PRECISE PPC_BIT(6) +#define CHTM_MODE_NO_ASSERT_LLAT_L3 PPC_BIT(6) #define HTM_MODE_WRAP PPC_BIT(13) #define HTM_MEMORY_CONF 1 #define HTM_MEM_ALLOC PPC_BIT(0) @@ -381,9 +384,35 @@ static int do_adu_magic(struct pdbg_target *target, uint32_t index, uint64_t *ar } #endif -static int do_setup(struct htm *htm) +/* + * This function doesn't do the update_mcs_regs() from the older p8 + * only tool. Not clear what this actually does. Attempting to ignore + * the problem. + * The scoms it does use are: + * SCOM ADDRESS FOR MCS4 + * #define MCS4_MCFGPQ 0x02011c00 + * #define MCS4_MCMODE 0x02011c07 + * #define MCS4_FIRMASK 0x02011c43 + * + * SCOM ADDRESS FOR MCS5 + * #define MCS5_MCFGPQ 0x02011c80 + * #define MCS5_MCMODE 0x02011c87 + * #define MCS5_FIRMASK 0x02011cc3 + * + * SCOM ADDRESS FOR MCS6 + * #define MCS6_MCFGPQ 0x02011d00 + * #define MCS6_MCMODE 0x02011d07 + * #define MCS6_FIRMASK 0x02011d43 + * + * SCOM ADDRESS FOR MCS7 + * #define MCS7_MCFGPQ 0x02011d80 + * #define MCS7_MCMODE 0x02011d87 + * #define MCS7_FIRMASK 0x02011dc3 + */ + +static int configure_debugfs_memtrace(struct htm *htm) { - uint64_t memtrace_size, val; + uint64_t memtrace_size; FILE *file; file = fopen(DEBUGFS_MEMTRACE_ENABLE, "r+"); @@ -412,6 +441,29 @@ static int do_setup(struct htm *htm) } fclose(file); + return 0; +} + +static int configure_chtm(struct htm *htm) +{ + if (HTM_ERR(configure_debugfs_memtrace(htm))) + return -1; + + if (HTM_ERR(pib_write(&htm->target, HTM_COLLECTION_MODE, + HTM_MODE_ENABLE | + CHTM_MODE_NO_ASSERT_LLAT_L3))) + return -1; + + return 0; +} + +static int configure_nhtm(struct htm *htm) +{ + uint64_t val; + + if (HTM_ERR(configure_debugfs_memtrace(htm))) + return -1; + /* * The constant is the VGTARGET field, taken from a cronus * booted system which presumably set it up correctly @@ -440,12 +492,14 @@ static int do_setup(struct htm *htm) NHTM_TTYPE_SIZE_MASK ))) /* no pattern matching */ return -1; - if (HTM_ERR(pib_read(&htm->target, NHTM_FLEX_MUX, &val))) - return -1; + if (dt_node_is_compatible(htm->target.dn, "ibm,power9-nhtm")) { + if (HTM_ERR(pib_read(&htm->target, NHTM_FLEX_MUX, &val))) + return -1; - if (GETFIELD(NHTM_FLEX_MUX_MASK, val) != NHTM_FLEX_DEFAULT) { - PR_ERROR("The HTM Flex wasn't default value\n"); - return -1; + if (GETFIELD(NHTM_FLEX_MUX_MASK, val) != NHTM_FLEX_DEFAULT) { + PR_ERROR("The HTM Flex wasn't default value\n"); + return -1; + } } return 0; @@ -581,23 +635,11 @@ static bool is_configured(struct htm *htm) return true; } - -static int do_nhtm_reset(struct htm *htm, uint64_t *r_base, uint64_t *r_size) +static int configure_memory(struct htm *htm, uint64_t *r_base, uint64_t *r_size) { - struct htm_status status; uint64_t i, size, base, val; uint16_t mem_size; - if (HTM_ERR(get_status(htm, &status))) - return -1; - - if (!is_resetable(&status) || !is_configured(htm)) { - if (HTM_ERR(do_setup(htm))) { - PR_ERROR("Couldn't setup HTM during reset\n"); - return -1; - } - } - if (HTM_ERR(get_trace_size(htm, &size))) return -1; @@ -649,6 +691,38 @@ static int do_nhtm_reset(struct htm *htm, uint64_t *r_base, uint64_t *r_size) *r_size = size; if (r_base) *r_base = base; + + return 0; +} + +static int do_htm_reset(struct htm *htm, uint64_t *r_base, uint64_t *r_size) +{ + struct htm_status status; + + if (HTM_ERR(get_status(htm, &status))) + return -1; + + if (!is_resetable(&status) || !is_configured(htm)) { + if (pdbg_target_is_class(&htm->target, "nhtm")) { + if (HTM_ERR(configure_nhtm(htm))) { + PR_ERROR("Couldn't setup Nest HTM during reset\n"); + return -1; + } + } else if (pdbg_target_is_class(&htm->target, "chtm")) { + if (HTM_ERR(configure_chtm(htm))) { + PR_ERROR("Couldn't setup Core HTM during reset\n"); + return -1; + } + } else { /* Well... */ + PR_ERROR("Unknown HTM class! %s\n", + pdbg_target_class_name(&htm->target)); + } + + } + + if (HTM_ERR(configure_memory(htm, r_base, r_size))) + return -1; + return 1; } @@ -834,36 +908,67 @@ static int do_htm_dump(struct htm *htm, uint64_t size, const char *basename) return 1; } +static bool is_debugfs_memtrace_ok(void) +{ + return access(DEBUGFS_MEMTRACE, F_OK) == 0; +} + +static bool is_debugfs_scom_ok(void) +{ + return access(DEBUGFS_SCOM, F_OK) == 0; +} + static int nhtm_probe(struct pdbg_target *target) { uint64_t val; - if (access(DEBUGFS_MEMTRACE, F_OK) != 0) { - PR_DEBUG("Couldn't open debugfs\n"); + if (!is_debugfs_memtrace_ok() || !is_debugfs_scom_ok()) return -1; - } - pib_read(target, NHTM_FLEX_MUX, &val); - if (GETFIELD(NHTM_FLEX_MUX_MASK, val) != NHTM_FLEX_DEFAULT) { - PR_DEBUG("FLEX_MUX not default\n"); - return -1; + if (dt_node_is_compatible(target->dn, "ibm,power9-nhtm")) { + pib_read(target, NHTM_FLEX_MUX, &val); + if (GETFIELD(NHTM_FLEX_MUX_MASK, val) != NHTM_FLEX_DEFAULT) { + PR_DEBUG("FLEX_MUX not default\n"); + return -1; + } } return 0; } +static int chtm_probe(struct pdbg_target *target) +{ + return is_debugfs_memtrace_ok() && is_debugfs_scom_ok() ? 0 : -1; +} + struct htm nhtm = { .target = { .name = "Nest HTM", - .compatible = "ibm,power9-nhtm", + .compatible = "ibm,power8-nhtm", "ibm,power9-nhtm", .class = "nhtm", .probe = nhtm_probe, }, .start = do_htm_start, .stop = do_htm_stop, - .reset = do_nhtm_reset, + .reset = do_htm_reset, .pause = do_htm_pause, .status = do_htm_status, .dump = do_htm_dump, }; DECLARE_HW_UNIT(nhtm); + +struct htm chtm = { + .target = { + .name = "POWER8 Core HTM", + .compatible = "ibm,power8-chtm", + .class = "chtm", + .probe = chtm_probe, + }, + .start = do_htm_start, + .stop = do_htm_stop, + .reset = do_htm_reset, + .pause = do_htm_pause, + .status = do_htm_status, + .dump = do_htm_dump, +}; +DECLARE_HW_UNIT(chtm); diff --git a/p8-pib.dts.m4 b/p8-pib.dts.m4 index de1d3bf..bdc02c5 100644 --- a/p8-pib.dts.m4 +++ b/p8-pib.dts.m4 @@ -7,6 +7,11 @@ define(`CORE', `core@CORE_BASE($1) { compatible = "ibm,power8-core"; reg = <0x0 HEX(CORE_BASE($1)) 0xfffff>; index = <0x$2>; + chtm@11000 { + compatible = "ibm,power8-chtm"; + reg = <0x0 0x11000 0xB>; + index = <0x0>; + }; THREAD(0); THREAD(1); @@ -42,4 +47,10 @@ adu@2020000 { reg = <0x0 0x2020000 0x4>; }; +nhtm@2010880 { + compatible = "ibm,power8-nhtm"; + reg = <0x0 0x2010880 0x8>; + index = <0x0>; +}; + PROC_CORES; |