Merge tag 'arc-4.1-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/vgupta/arc
Pull ARC updates from Vineet Gupta: - perf fixes/improvements - misc cleanups * tag 'arc-4.1-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/vgupta/arc: ARC: perf: don't add code for impossible case ARC: perf: Rename DT binding to not confuse with power mgmt ARC: perf: add user space attribution in callchains ARC: perf: Add kernel callchain support ARC: perf: support cache hit/miss ratio ARC: perf: Add some comments/debug stuff ARC: perf: make @arc_pmu static global ARC: mem init spring cleaning - No functional changes ARC: Fix RTT boot printing ARC: fold __builtin_constant_p() into test_bit() ARC: rename unhandled exception handler ARC: cosmetic: Remove unused ECR bitfield masks ARC: Fix WRITE_BCR ARC: [nsimosci] Update defconfig arc: copy_thread(): rename 'arg' argument to 'kthread_arg'
This commit is contained in:
@@ -30,6 +30,7 @@
|
||||
#define ARC_REG_D_UNCACH_BCR 0x6A
|
||||
#define ARC_REG_BPU_BCR 0xc0
|
||||
#define ARC_REG_ISA_CFG_BCR 0xc1
|
||||
#define ARC_REG_RTT_BCR 0xF2
|
||||
#define ARC_REG_SMART_BCR 0xFF
|
||||
|
||||
/* status32 Bits Positions */
|
||||
@@ -50,11 +51,7 @@
|
||||
* [15: 8] = Exception Cause Code
|
||||
* [ 7: 0] = Exception Parameters (for certain types only)
|
||||
*/
|
||||
#define ECR_VEC_MASK 0xff0000
|
||||
#define ECR_CODE_MASK 0x00ff00
|
||||
#define ECR_PARAM_MASK 0x0000ff
|
||||
|
||||
/* Exception Cause Vector Values */
|
||||
#define ECR_V_MEM_ERR 0x01
|
||||
#define ECR_V_INSN_ERR 0x02
|
||||
#define ECR_V_MACH_CHK 0x20
|
||||
#define ECR_V_ITLB_MISS 0x21
|
||||
@@ -62,7 +59,8 @@
|
||||
#define ECR_V_PROTV 0x23
|
||||
#define ECR_V_TRAP 0x25
|
||||
|
||||
/* Protection Violation Exception Cause Code Values */
|
||||
/* DTLB Miss and Protection Violation Cause Codes */
|
||||
|
||||
#define ECR_C_PROTV_INST_FETCH 0x00
|
||||
#define ECR_C_PROTV_LOAD 0x01
|
||||
#define ECR_C_PROTV_STORE 0x02
|
||||
@@ -173,11 +171,11 @@
|
||||
} \
|
||||
}
|
||||
|
||||
#define WRITE_BCR(reg, into) \
|
||||
#define WRITE_AUX(reg, into) \
|
||||
{ \
|
||||
unsigned int tmp; \
|
||||
if (sizeof(tmp) == sizeof(into)) { \
|
||||
tmp = (*(unsigned int *)(into)); \
|
||||
tmp = (*(unsigned int *)&(into)); \
|
||||
write_aux_reg(reg, tmp); \
|
||||
} else { \
|
||||
extern void bogus_undefined(void); \
|
||||
|
@@ -32,6 +32,20 @@ static inline void set_bit(unsigned long nr, volatile unsigned long *m)
|
||||
|
||||
m += nr >> 5;
|
||||
|
||||
/*
|
||||
* ARC ISA micro-optimization:
|
||||
*
|
||||
* Instructions dealing with bitpos only consider lower 5 bits (0-31)
|
||||
* e.g (x << 33) is handled like (x << 1) by ASL instruction
|
||||
* (mem pointer still needs adjustment to point to next word)
|
||||
*
|
||||
* Hence the masking to clamp @nr arg can be elided in general.
|
||||
*
|
||||
* However if @nr is a constant (above assumed it in a register),
|
||||
* and greater than 31, gcc can optimize away (x << 33) to 0,
|
||||
* as overflow, given the 32-bit ISA. Thus masking needs to be done
|
||||
* for constant @nr, but no code is generated due to const prop.
|
||||
*/
|
||||
if (__builtin_constant_p(nr))
|
||||
nr &= 0x1f;
|
||||
|
||||
@@ -374,29 +388,20 @@ __test_and_change_bit(unsigned long nr, volatile unsigned long *m)
|
||||
* This routine doesn't need to be atomic.
|
||||
*/
|
||||
static inline int
|
||||
__constant_test_bit(unsigned int nr, const volatile unsigned long *addr)
|
||||
{
|
||||
return ((1UL << (nr & 31)) &
|
||||
(((const volatile unsigned int *)addr)[nr >> 5])) != 0;
|
||||
}
|
||||
|
||||
static inline int
|
||||
__test_bit(unsigned int nr, const volatile unsigned long *addr)
|
||||
test_bit(unsigned int nr, const volatile unsigned long *addr)
|
||||
{
|
||||
unsigned long mask;
|
||||
|
||||
addr += nr >> 5;
|
||||
|
||||
/* ARC700 only considers 5 bits in bit-fiddling insn */
|
||||
if (__builtin_constant_p(nr))
|
||||
nr &= 0x1f;
|
||||
|
||||
mask = 1 << nr;
|
||||
|
||||
return ((mask & *addr) != 0);
|
||||
}
|
||||
|
||||
#define test_bit(nr, addr) (__builtin_constant_p(nr) ? \
|
||||
__constant_test_bit((nr), (addr)) : \
|
||||
__test_bit((nr), (addr)))
|
||||
|
||||
/*
|
||||
* Count the number of zeros, starting from MSB
|
||||
* Helper for fls( ) friends
|
||||
|
@@ -54,29 +54,13 @@ struct arc_reg_cc_build {
|
||||
#define PERF_COUNT_ARC_BPOK (PERF_COUNT_HW_MAX + 3)
|
||||
#define PERF_COUNT_ARC_EDTLB (PERF_COUNT_HW_MAX + 4)
|
||||
#define PERF_COUNT_ARC_EITLB (PERF_COUNT_HW_MAX + 5)
|
||||
#define PERF_COUNT_ARC_HW_MAX (PERF_COUNT_HW_MAX + 6)
|
||||
#define PERF_COUNT_ARC_LDC (PERF_COUNT_HW_MAX + 6)
|
||||
#define PERF_COUNT_ARC_STC (PERF_COUNT_HW_MAX + 7)
|
||||
|
||||
#define PERF_COUNT_ARC_HW_MAX (PERF_COUNT_HW_MAX + 8)
|
||||
|
||||
/*
|
||||
* The "generalized" performance events seem to really be a copy
|
||||
* of the available events on x86 processors; the mapping to ARC
|
||||
* events is not always possible 1-to-1. Fortunately, there doesn't
|
||||
* seem to be an exact definition for these events, so we can cheat
|
||||
* a bit where necessary.
|
||||
*
|
||||
* In particular, the following PERF events may behave a bit differently
|
||||
* compared to other architectures:
|
||||
*
|
||||
* PERF_COUNT_HW_CPU_CYCLES
|
||||
* Cycles not in halted state
|
||||
*
|
||||
* PERF_COUNT_HW_REF_CPU_CYCLES
|
||||
* Reference cycles not in halted state, same as PERF_COUNT_HW_CPU_CYCLES
|
||||
* for now as we don't do Dynamic Voltage/Frequency Scaling (yet)
|
||||
*
|
||||
* PERF_COUNT_HW_BUS_CYCLES
|
||||
* Unclear what this means, Intel uses 0x013c, which according to
|
||||
* their datasheet means "unhalted reference cycles". It sounds similar
|
||||
* to PERF_COUNT_HW_REF_CPU_CYCLES, and we use the same counter for it.
|
||||
* Some ARC pct quirks:
|
||||
*
|
||||
* PERF_COUNT_HW_STALLED_CYCLES_BACKEND
|
||||
* PERF_COUNT_HW_STALLED_CYCLES_FRONTEND
|
||||
@@ -91,21 +75,38 @@ struct arc_reg_cc_build {
|
||||
* Note that I$ cache misses aren't counted by either of the two!
|
||||
*/
|
||||
|
||||
/*
|
||||
* ARC PCT has hardware conditions with fixed "names" but variable "indexes"
|
||||
* (based on a specific RTL build)
|
||||
* Below is the static map between perf generic/arc specific event_id and
|
||||
* h/w condition names.
|
||||
* At the time of probe, we loop thru each index and find it's name to
|
||||
* complete the mapping of perf event_id to h/w index as latter is needed
|
||||
* to program the counter really
|
||||
*/
|
||||
static const char * const arc_pmu_ev_hw_map[] = {
|
||||
/* count cycles */
|
||||
[PERF_COUNT_HW_CPU_CYCLES] = "crun",
|
||||
[PERF_COUNT_HW_REF_CPU_CYCLES] = "crun",
|
||||
[PERF_COUNT_HW_BUS_CYCLES] = "crun",
|
||||
[PERF_COUNT_HW_INSTRUCTIONS] = "iall",
|
||||
[PERF_COUNT_HW_BRANCH_MISSES] = "bpfail",
|
||||
[PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = "ijmp",
|
||||
|
||||
[PERF_COUNT_HW_STALLED_CYCLES_FRONTEND] = "bflush",
|
||||
[PERF_COUNT_HW_STALLED_CYCLES_BACKEND] = "bstall",
|
||||
[PERF_COUNT_ARC_DCLM] = "dclm",
|
||||
[PERF_COUNT_ARC_DCSM] = "dcsm",
|
||||
[PERF_COUNT_ARC_ICM] = "icm",
|
||||
[PERF_COUNT_ARC_BPOK] = "bpok",
|
||||
[PERF_COUNT_ARC_EDTLB] = "edtlb",
|
||||
[PERF_COUNT_ARC_EITLB] = "eitlb",
|
||||
|
||||
/* counts condition */
|
||||
[PERF_COUNT_HW_INSTRUCTIONS] = "iall",
|
||||
[PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = "ijmp",
|
||||
[PERF_COUNT_ARC_BPOK] = "bpok", /* NP-NT, PT-T, PNT-NT */
|
||||
[PERF_COUNT_HW_BRANCH_MISSES] = "bpfail", /* NP-T, PT-NT, PNT-T */
|
||||
|
||||
[PERF_COUNT_ARC_LDC] = "imemrdc", /* Instr: mem read cached */
|
||||
[PERF_COUNT_ARC_STC] = "imemwrc", /* Instr: mem write cached */
|
||||
|
||||
[PERF_COUNT_ARC_DCLM] = "dclm", /* D-cache Load Miss */
|
||||
[PERF_COUNT_ARC_DCSM] = "dcsm", /* D-cache Store Miss */
|
||||
[PERF_COUNT_ARC_ICM] = "icm", /* I-cache Miss */
|
||||
[PERF_COUNT_ARC_EDTLB] = "edtlb", /* D-TLB Miss */
|
||||
[PERF_COUNT_ARC_EITLB] = "eitlb", /* I-TLB Miss */
|
||||
};
|
||||
|
||||
#define C(_x) PERF_COUNT_HW_CACHE_##_x
|
||||
@@ -114,11 +115,11 @@ static const char * const arc_pmu_ev_hw_map[] = {
|
||||
static const unsigned arc_pmu_cache_map[C(MAX)][C(OP_MAX)][C(RESULT_MAX)] = {
|
||||
[C(L1D)] = {
|
||||
[C(OP_READ)] = {
|
||||
[C(RESULT_ACCESS)] = CACHE_OP_UNSUPPORTED,
|
||||
[C(RESULT_ACCESS)] = PERF_COUNT_ARC_LDC,
|
||||
[C(RESULT_MISS)] = PERF_COUNT_ARC_DCLM,
|
||||
},
|
||||
[C(OP_WRITE)] = {
|
||||
[C(RESULT_ACCESS)] = CACHE_OP_UNSUPPORTED,
|
||||
[C(RESULT_ACCESS)] = PERF_COUNT_ARC_STC,
|
||||
[C(RESULT_MISS)] = PERF_COUNT_ARC_DCSM,
|
||||
},
|
||||
[C(OP_PREFETCH)] = {
|
||||
@@ -128,7 +129,7 @@ static const unsigned arc_pmu_cache_map[C(MAX)][C(OP_MAX)][C(RESULT_MAX)] = {
|
||||
},
|
||||
[C(L1I)] = {
|
||||
[C(OP_READ)] = {
|
||||
[C(RESULT_ACCESS)] = CACHE_OP_UNSUPPORTED,
|
||||
[C(RESULT_ACCESS)] = PERF_COUNT_HW_INSTRUCTIONS,
|
||||
[C(RESULT_MISS)] = PERF_COUNT_ARC_ICM,
|
||||
},
|
||||
[C(OP_WRITE)] = {
|
||||
@@ -156,9 +157,10 @@ static const unsigned arc_pmu_cache_map[C(MAX)][C(OP_MAX)][C(RESULT_MAX)] = {
|
||||
},
|
||||
[C(DTLB)] = {
|
||||
[C(OP_READ)] = {
|
||||
[C(RESULT_ACCESS)] = CACHE_OP_UNSUPPORTED,
|
||||
[C(RESULT_ACCESS)] = PERF_COUNT_ARC_LDC,
|
||||
[C(RESULT_MISS)] = PERF_COUNT_ARC_EDTLB,
|
||||
},
|
||||
/* DTLB LD/ST Miss not segregated by h/w*/
|
||||
[C(OP_WRITE)] = {
|
||||
[C(RESULT_ACCESS)] = CACHE_OP_UNSUPPORTED,
|
||||
[C(RESULT_MISS)] = CACHE_OP_UNSUPPORTED,
|
||||
|
Reference in New Issue
Block a user