2016-09-28 93 views
2

我目前在我的Nexus 5中使用了simpleperf,這是一個用於Android的perf的移植版本。我希望做的是動態獲取本機函數的執行順序。我應該使用哪個事件來執行perf函數以獲取函數分支事件?

我想應該有一種方法來轉儲一個示例記錄一旦有分支事件。所以我要做的就是執行simpleperf record -e branch-loads:u -p [pid]

下面我列出了一些在我的設備中支持的相關事件。我爲我的目的嘗試了branch-loadsbranch-instructions。但他們都沒有返回預期的結果。我相信這是由於分支包括函數以及有條件的跳轉。

[email protected]:/data/local/tmp # ./simpleperf32 list       
List of hw-cache events: 
    ... 
    branch-loads 
    branch-load-misses 
    branch-stores 
    branch-store-misses 
    node-loads 
    node-load-misses 
    node-stores 
    node-store-misses 
    node-prefetches 
    node-prefetch-misses 

List of hardware events: 
    cpu-cycles 
    instructions 
    branch-instructions 
    branch-misses 
    bus-cycles 
    stalled-cycles-frontend 
    stalled-cycles-backend 

那麼,我怎樣才能獲得函數調用事件?或者如果我的方式不對,請給我指出正確的一條。謝謝。

+0

要獲得完整的「本機函數」執行順序「,您應該嘗試跟蹤,而不是像perf那樣進行統計分析。 – osgx

回答

2

perf list沒有列出實際的硬件事件,它只是perf預定義列表的列表,並沒有被任何CPU完全支持。某些CPU將幾個事件映射到perf的預定義的其他映射不同的事件集。

您應該檢查CPU核心(Qualcomm krait 400)的文檔以查找實際的硬件性能監視事件(計數器)並將它們用作原始數據(編碼爲perf stat -e rXXXX或在perf_attr中編碼爲特定體系結構)。您也可以嘗試使用perf stat/perf stat -d來檢查哪些事件是從某些默認列表中統計(支持)的。

您的nexus 5基於Krait 400 CPU內核。

有在金環報道了一些問題:How to get perf_event results for 2nd Nexus7 with Krait CPU 並有鏈接補丁,定義爲Krait的標準事件:

http://www.serverphorums.com/read.php?12,850329

有兩套映射從預定義的PERF的實際硬件事件。一個與支持branch-instructions事件和其他無:

/* 
+ * Krait HW events mapping 
+ */ 
+static const unsigned krait_perf_map[PERF_COUNT_HW_MAX] = { 
+ [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES, 
+ [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED, 
+ [PERF_COUNT_HW_CACHE_REFERENCES] = HW_OP_UNSUPPORTED, 
+ [PERF_COUNT_HW_CACHE_MISSES] = HW_OP_UNSUPPORTED, 
+ [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_PERFCTR_PC_WRITE, 
+ [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED, 
+ [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_CLOCK_CYCLES, 
+}; 
+ 
+static const unsigned krait_perf_map_no_branch[PERF_COUNT_HW_MAX] = { 
+ [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES, 
+ [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED, 
+ [PERF_COUNT_HW_CACHE_REFERENCES] = HW_OP_UNSUPPORTED, 
+ [PERF_COUNT_HW_CACHE_MISSES] = HW_OP_UNSUPPORTED, 
+ [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = HW_OP_UNSUPPORTED, 
+ [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED, 
+ [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_CLOCK_CYCLES, 
+}; 

根據選擇的代碼,這是更高版本的Krait CPU的功能:

+static int krait_pmu_init(struct arm_pmu *cpu_pmu) 
+{ 
+ u32 id = read_cpuid_id() & 0xffffff00; 
+ 
+ armv7pmu_init(cpu_pmu); 
+ cpu_pmu->name = "ARMv7 Krait"; 
+ /* Some early versions of Krait don't support PC write events */ 
+ if (id == 0x511f0400 || id == 0x510f0600) 
+ cpu_pmu->map_event = krait_map_event_no_branch; 
+ else 
+ cpu_pmu->map_event = krait_map_event; 
+ cpu_pmu->num_events = armv7_read_num_pmnc_events(); 
+ cpu_pmu->set_event_filter = armv7pmu_set_event_filter; 
+ return 0; 
+} 

正如我可以解碼CPUID - 金環蛇400和金環蛇600不支持分支指令PMU事件(PC寫入事件)。

更新:爲了您的Nexus 5倍,如果它使用的ARM Cortex A57核心,有「從表11-24‘的Cortex A57技術參考手冊’,」

https://sourceforge.net/p/perfmon2/libpfm4/ci/master/tree/lib/events/arm_cortex_a57_events.h

原始事件的列表,基於

所有分行仍然沒有櫃檯。有BRANCH_MISPRED & BRANCH_PRED,但我無法訪問文檔,不知道他們是否會統計所有分支。

+0

也未在libpfm4中列出:https://sourceforge.net/p/perfmon2/libpfm4/ci/master/tree/lib/events/arm_qcom_krait_events.h – osgx

+0

謝謝。由於Krait對ARM CoreSight的不良支持,我放棄了Nexus 5。相反,我嘗試了具有Coretex A57 CPU的Neuxs 5x。但同樣的問題發生了。不確定我是否以正確的方式進行測試。 – colordancer

+1

colordancer,A57沒有所有分支計數的性能事件:https://sourceforge.net/p/perfmon2/libpfm4/ci/master/tree/lib/events/arm_cortex_a57_events.h但是有BRANCH_MISPRED和BRANCH_PRED事件,你應檢查「Cortex A57技術參考手冊」中的表11-24「並嘗試將它們編碼爲perf的原始事件 – osgx

相關問題