aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHendrik Brueckner <brueckner@linux.vnet.ibm.com>2013-12-13 06:45:01 -0500
committerMartin Schwidefsky <schwidefsky@de.ibm.com>2013-12-16 08:38:01 -0500
commitd7528862cf035994972c2c6f42c927db78f2f3a2 (patch)
tree8e5c54f2de4462a8600037f7563930acf5260bcf
parent7e75fc3ff4cffd90684816d69838f8730ac3e072 (diff)
s390/cpum_sf: Add flag to process full SDBs only
Add the PERF_CPUM_SF_FULL_BLOCKS flag to process only sample-data-blocks that have the block-full-indicator bit set. Sample-data-blocks that are partially filled are discarded. Use this flag if the sampling buffer is likely to be shared among perf events that use different sampling modes. In such environments, flushing sample-data-blocks that are not completely filled, might cause invalid-data-formats. Setting PERF_CPUM_SF_FULL_BLOCKS prevents potentially invalid sampling data to be processed but, in contrast, also discards valid samples in partially filled sample-data-blocks. Note that sample-data-blocks might not become full for small sampling frequencies or for workload that is scheduled for tiny intervals. To sample with the PERF_CPUM_SF_FULL_BLOCKS flag, set the perf->attr.config1 to 0x0004. For example: perf record -e cpum_sf/config=0xB000,config1=0x0004/ Signed-off-by: Hendrik Brueckner <brueckner@linux.vnet.ibm.com> Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
-rw-r--r--arch/s390/include/asm/perf_event.h2
-rw-r--r--arch/s390/kernel/perf_cpum_sf.c13
2 files changed, 13 insertions, 2 deletions
diff --git a/arch/s390/include/asm/perf_event.h b/arch/s390/include/asm/perf_event.h
index bd4573f1d65c..159a8ec6da9a 100644
--- a/arch/s390/include/asm/perf_event.h
+++ b/arch/s390/include/asm/perf_event.h
@@ -59,6 +59,7 @@ struct perf_sf_sde_regs {
59#define PERF_CPUM_SF_DIAG_MODE 0x0002 /* Diagnostic-sampling flag */ 59#define PERF_CPUM_SF_DIAG_MODE 0x0002 /* Diagnostic-sampling flag */
60#define PERF_CPUM_SF_MODE_MASK (PERF_CPUM_SF_BASIC_MODE| \ 60#define PERF_CPUM_SF_MODE_MASK (PERF_CPUM_SF_BASIC_MODE| \
61 PERF_CPUM_SF_DIAG_MODE) 61 PERF_CPUM_SF_DIAG_MODE)
62#define PERF_CPUM_SF_FULL_BLOCKS 0x0004 /* Process full SDBs only */
62 63
63#define REG_NONE 0 64#define REG_NONE 0
64#define REG_OVERFLOW 1 65#define REG_OVERFLOW 1
@@ -69,6 +70,7 @@ struct perf_sf_sde_regs {
69#define SAMPL_RATE(hwc) ((hwc)->event_base) 70#define SAMPL_RATE(hwc) ((hwc)->event_base)
70#define SAMPL_FLAGS(hwc) ((hwc)->config_base) 71#define SAMPL_FLAGS(hwc) ((hwc)->config_base)
71#define SAMPL_DIAG_MODE(hwc) (SAMPL_FLAGS(hwc) & PERF_CPUM_SF_DIAG_MODE) 72#define SAMPL_DIAG_MODE(hwc) (SAMPL_FLAGS(hwc) & PERF_CPUM_SF_DIAG_MODE)
73#define SDB_FULL_BLOCKS(hwc) (SAMPL_FLAGS(hwc) & PERF_CPUM_SF_FULL_BLOCKS)
72 74
73/* Structure for sampling data entries to be passed as perf raw sample data 75/* Structure for sampling data entries to be passed as perf raw sample data
74 * to user space. Note that raw sample data must be aligned and, thus, might 76 * to user space. Note that raw sample data must be aligned and, thus, might
diff --git a/arch/s390/kernel/perf_cpum_sf.c b/arch/s390/kernel/perf_cpum_sf.c
index b4ec058c4f10..3c3bc8d7b220 100644
--- a/arch/s390/kernel/perf_cpum_sf.c
+++ b/arch/s390/kernel/perf_cpum_sf.c
@@ -733,6 +733,10 @@ static int __hw_perf_event_init(struct perf_event *event)
733 SAMPL_FLAGS(hwc) |= PERF_CPUM_SF_DIAG_MODE; 733 SAMPL_FLAGS(hwc) |= PERF_CPUM_SF_DIAG_MODE;
734 } 734 }
735 735
736 /* Check and set other sampling flags */
737 if (attr->config1 & PERF_CPUM_SF_FULL_BLOCKS)
738 SAMPL_FLAGS(hwc) |= PERF_CPUM_SF_FULL_BLOCKS;
739
736 /* The sampling information (si) contains information about the 740 /* The sampling information (si) contains information about the
737 * min/max sampling intervals and the CPU speed. So calculate the 741 * min/max sampling intervals and the CPU speed. So calculate the
738 * correct sampling interval and avoid the whole period adjust 742 * correct sampling interval and avoid the whole period adjust
@@ -1203,8 +1207,10 @@ static void hw_collect_samples(struct perf_event *event, unsigned long *sdbt,
1203 * register of the specified perf event. 1207 * register of the specified perf event.
1204 * 1208 *
1205 * Only full sample-data-blocks are processed. Specify the flash_all flag 1209 * Only full sample-data-blocks are processed. Specify the flash_all flag
1206 * to also walk through partially filled sample-data-blocks. 1210 * to also walk through partially filled sample-data-blocks. It is ignored
1207 * 1211 * if PERF_CPUM_SF_FULL_BLOCKS is set. The PERF_CPUM_SF_FULL_BLOCKS flag
1212 * enforces the processing of full sample-data-blocks only (trailer entries
1213 * with the block-full-indicator bit set).
1208 */ 1214 */
1209static void hw_perf_event_update(struct perf_event *event, int flush_all) 1215static void hw_perf_event_update(struct perf_event *event, int flush_all)
1210{ 1216{
@@ -1214,6 +1220,9 @@ static void hw_perf_event_update(struct perf_event *event, int flush_all)
1214 unsigned long long event_overflow, sampl_overflow, num_sdb, te_flags; 1220 unsigned long long event_overflow, sampl_overflow, num_sdb, te_flags;
1215 int done; 1221 int done;
1216 1222
1223 if (flush_all && SDB_FULL_BLOCKS(hwc))
1224 flush_all = 0;
1225
1217 sdbt = (unsigned long *) TEAR_REG(hwc); 1226 sdbt = (unsigned long *) TEAR_REG(hwc);
1218 done = event_overflow = sampl_overflow = num_sdb = 0; 1227 done = event_overflow = sampl_overflow = num_sdb = 0;
1219 while (!done) { 1228 while (!done) {