Merge branch 'perf-core-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git...
[platform/adaptation/renesas_rcar/renesas_kernel.git] / tools / perf / util / parse-events-test.c
index 34b97bb..28c18d1 100644 (file)
@@ -13,16 +13,17 @@ do { \
        } \
 } while (0)
 
+#define PERF_TP_SAMPLE_TYPE (PERF_SAMPLE_RAW | PERF_SAMPLE_TIME | \
+                            PERF_SAMPLE_CPU | PERF_SAMPLE_PERIOD)
+
 static int test__checkevent_tracepoint(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_TRACEPOINT == evsel->attr.type);
        TEST_ASSERT_VAL("wrong sample_type",
-               (PERF_SAMPLE_RAW | PERF_SAMPLE_TIME | PERF_SAMPLE_CPU) ==
-               evsel->attr.sample_type);
+               PERF_TP_SAMPLE_TYPE == evsel->attr.sample_type);
        TEST_ASSERT_VAL("wrong sample_period", 1 == evsel->attr.sample_period);
        return 0;
 }
@@ -37,8 +38,7 @@ static int test__checkevent_tracepoint_multi(struct perf_evlist *evlist)
                TEST_ASSERT_VAL("wrong type",
                        PERF_TYPE_TRACEPOINT == evsel->attr.type);
                TEST_ASSERT_VAL("wrong sample_type",
-                       (PERF_SAMPLE_RAW | PERF_SAMPLE_TIME | PERF_SAMPLE_CPU)
-                       == evsel->attr.sample_type);
+                       PERF_TP_SAMPLE_TYPE == evsel->attr.sample_type);
                TEST_ASSERT_VAL("wrong sample_period",
                        1 == evsel->attr.sample_period);
        }
@@ -47,8 +47,7 @@ static int test__checkevent_tracepoint_multi(struct perf_evlist *evlist)
 
 static int test__checkevent_raw(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_RAW == evsel->attr.type);
@@ -58,8 +57,7 @@ static int test__checkevent_raw(struct perf_evlist *evlist)
 
 static int test__checkevent_numeric(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", 1 == evsel->attr.type);
@@ -69,8 +67,7 @@ static int test__checkevent_numeric(struct perf_evlist *evlist)
 
 static int test__checkevent_symbolic_name(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
@@ -81,8 +78,7 @@ static int test__checkevent_symbolic_name(struct perf_evlist *evlist)
 
 static int test__checkevent_symbolic_name_config(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
@@ -99,8 +95,7 @@ static int test__checkevent_symbolic_name_config(struct perf_evlist *evlist)
 
 static int test__checkevent_symbolic_alias(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_SOFTWARE == evsel->attr.type);
@@ -111,8 +106,7 @@ static int test__checkevent_symbolic_alias(struct perf_evlist *evlist)
 
 static int test__checkevent_genhw(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_HW_CACHE == evsel->attr.type);
@@ -122,8 +116,7 @@ static int test__checkevent_genhw(struct perf_evlist *evlist)
 
 static int test__checkevent_breakpoint(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_BREAKPOINT == evsel->attr.type);
@@ -137,8 +130,7 @@ static int test__checkevent_breakpoint(struct perf_evlist *evlist)
 
 static int test__checkevent_breakpoint_x(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_BREAKPOINT == evsel->attr.type);
@@ -151,8 +143,7 @@ static int test__checkevent_breakpoint_x(struct perf_evlist *evlist)
 
 static int test__checkevent_breakpoint_r(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type",
@@ -167,8 +158,7 @@ static int test__checkevent_breakpoint_r(struct perf_evlist *evlist)
 
 static int test__checkevent_breakpoint_w(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type",
@@ -183,8 +173,7 @@ static int test__checkevent_breakpoint_w(struct perf_evlist *evlist)
 
 static int test__checkevent_breakpoint_rw(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type",
@@ -199,8 +188,7 @@ static int test__checkevent_breakpoint_rw(struct perf_evlist *evlist)
 
 static int test__checkevent_tracepoint_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
@@ -231,8 +219,7 @@ test__checkevent_tracepoint_multi_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_raw_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
@@ -244,8 +231,7 @@ static int test__checkevent_raw_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_numeric_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
@@ -257,8 +243,7 @@ static int test__checkevent_numeric_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_symbolic_name_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
@@ -270,8 +255,7 @@ static int test__checkevent_symbolic_name_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_exclude_host_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
        TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
@@ -281,8 +265,7 @@ static int test__checkevent_exclude_host_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_exclude_guest_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude guest", evsel->attr.exclude_guest);
        TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
@@ -292,8 +275,7 @@ static int test__checkevent_exclude_guest_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_symbolic_alias_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
@@ -305,8 +287,7 @@ static int test__checkevent_symbolic_alias_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_genhw_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
@@ -318,75 +299,71 @@ static int test__checkevent_genhw_modifier(struct perf_evlist *evlist)
 
 static int test__checkevent_breakpoint_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
+
 
        TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
        TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
        TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
        TEST_ASSERT_VAL("wrong name",
-                       !strcmp(perf_evsel__name(evsel), "mem:0x0:rw:u"));
+                       !strcmp(perf_evsel__name(evsel), "mem:0:u"));
 
        return test__checkevent_breakpoint(evlist);
 }
 
 static int test__checkevent_breakpoint_x_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
        TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
        TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
        TEST_ASSERT_VAL("wrong name",
-                       !strcmp(perf_evsel__name(evsel), "mem:0x0:x:k"));
+                       !strcmp(perf_evsel__name(evsel), "mem:0:x:k"));
 
        return test__checkevent_breakpoint_x(evlist);
 }
 
 static int test__checkevent_breakpoint_r_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
        TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
        TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip);
        TEST_ASSERT_VAL("wrong name",
-                       !strcmp(perf_evsel__name(evsel), "mem:0x0:r:hp"));
+                       !strcmp(perf_evsel__name(evsel), "mem:0:r:hp"));
 
        return test__checkevent_breakpoint_r(evlist);
 }
 
 static int test__checkevent_breakpoint_w_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
        TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
        TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip);
        TEST_ASSERT_VAL("wrong name",
-                       !strcmp(perf_evsel__name(evsel), "mem:0x0:w:up"));
+                       !strcmp(perf_evsel__name(evsel), "mem:0:w:up"));
 
        return test__checkevent_breakpoint_w(evlist);
 }
 
 static int test__checkevent_breakpoint_rw_modifier(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
        TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
        TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip);
        TEST_ASSERT_VAL("wrong name",
-                       !strcmp(perf_evsel__name(evsel), "mem:0x0:rw:kp"));
+                       !strcmp(perf_evsel__name(evsel), "mem:0:rw:kp"));
 
        return test__checkevent_breakpoint_rw(evlist);
 }
@@ -394,8 +371,7 @@ static int test__checkevent_breakpoint_rw_modifier(struct perf_evlist *evlist)
 static int test__checkevent_pmu(struct perf_evlist *evlist)
 {
 
-       struct perf_evsel *evsel = list_entry(evlist->entries.next,
-                                             struct perf_evsel, node);
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 1 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_RAW == evsel->attr.type);
@@ -409,12 +385,11 @@ static int test__checkevent_pmu(struct perf_evlist *evlist)
 
 static int test__checkevent_list(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel;
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        TEST_ASSERT_VAL("wrong number of entries", 3 == evlist->nr_entries);
 
        /* r1 */
-       evsel = list_entry(evlist->entries.next, struct perf_evsel, node);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_RAW == evsel->attr.type);
        TEST_ASSERT_VAL("wrong config", 1 == evsel->attr.config);
        TEST_ASSERT_VAL("wrong config1", 0 == evsel->attr.config1);
@@ -425,11 +400,10 @@ static int test__checkevent_list(struct perf_evlist *evlist)
        TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
 
        /* syscalls:sys_enter_open:k */
-       evsel = list_entry(evsel->node.next, struct perf_evsel, node);
+       evsel = perf_evsel__next(evsel);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_TRACEPOINT == evsel->attr.type);
        TEST_ASSERT_VAL("wrong sample_type",
-               (PERF_SAMPLE_RAW | PERF_SAMPLE_TIME | PERF_SAMPLE_CPU) ==
-               evsel->attr.sample_type);
+               PERF_TP_SAMPLE_TYPE == evsel->attr.sample_type);
        TEST_ASSERT_VAL("wrong sample_period", 1 == evsel->attr.sample_period);
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
        TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
@@ -437,7 +411,7 @@ static int test__checkevent_list(struct perf_evlist *evlist)
        TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
 
        /* 1:1:hp */
-       evsel = list_entry(evsel->node.next, struct perf_evsel, node);
+       evsel = perf_evsel__next(evsel);
        TEST_ASSERT_VAL("wrong type", 1 == evsel->attr.type);
        TEST_ASSERT_VAL("wrong config", 1 == evsel->attr.config);
        TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
@@ -450,22 +424,21 @@ static int test__checkevent_list(struct perf_evlist *evlist)
 
 static int test__checkevent_pmu_name(struct perf_evlist *evlist)
 {
-       struct perf_evsel *evsel;
+       struct perf_evsel *evsel = perf_evlist__first(evlist);
 
        /* cpu/config=1,name=krava/u */
-       evsel = list_entry(evlist->entries.next, struct perf_evsel, node);
        TEST_ASSERT_VAL("wrong number of entries", 2 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_RAW == evsel->attr.type);
        TEST_ASSERT_VAL("wrong config",  1 == evsel->attr.config);
        TEST_ASSERT_VAL("wrong name", !strcmp(perf_evsel__name(evsel), "krava"));
 
        /* cpu/config=2/u" */
-       evsel = list_entry(evsel->node.next, struct perf_evsel, node);
+       evsel = perf_evsel__next(evsel);
        TEST_ASSERT_VAL("wrong number of entries", 2 == evlist->nr_entries);
        TEST_ASSERT_VAL("wrong type", PERF_TYPE_RAW == evsel->attr.type);
        TEST_ASSERT_VAL("wrong config",  2 == evsel->attr.config);
        TEST_ASSERT_VAL("wrong name",
-                       !strcmp(perf_evsel__name(evsel), "raw 0x2:u"));
+                       !strcmp(perf_evsel__name(evsel), "cpu/config=2/u"));
 
        return 0;
 }
@@ -513,6 +486,280 @@ static int test__checkterms_simple(struct list_head *terms)
        return 0;
 }
 
+static int test__group1(struct perf_evlist *evlist)
+{
+       struct perf_evsel *evsel, *leader;
+
+       TEST_ASSERT_VAL("wrong number of entries", 2 == evlist->nr_entries);
+
+       /* instructions:k */
+       evsel = leader = perf_evlist__first(evlist);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_INSTRUCTIONS == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       /* cycles:upp */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip == 2);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+
+       return 0;
+}
+
+static int test__group2(struct perf_evlist *evlist)
+{
+       struct perf_evsel *evsel, *leader;
+
+       TEST_ASSERT_VAL("wrong number of entries", 3 == evlist->nr_entries);
+
+       /* faults + :ku modifier */
+       evsel = leader = perf_evlist__first(evlist);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_SOFTWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_SW_PAGE_FAULTS == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       /* cache-references + :u modifier */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CACHE_REFERENCES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+
+       /* cycles:k */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       return 0;
+}
+
+static int test__group3(struct perf_evlist *evlist __maybe_unused)
+{
+       struct perf_evsel *evsel, *leader;
+
+       TEST_ASSERT_VAL("wrong number of entries", 5 == evlist->nr_entries);
+
+       /* group1 syscalls:sys_enter_open:H */
+       evsel = leader = perf_evlist__first(evlist);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_TRACEPOINT == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong sample_type",
+               PERF_TP_SAMPLE_TYPE == evsel->attr.sample_type);
+       TEST_ASSERT_VAL("wrong sample_period", 1 == evsel->attr.sample_period);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+       TEST_ASSERT_VAL("wrong group name",
+               !strcmp(leader->group_name, "group1"));
+
+       /* group1 cycles:kppp */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip == 3);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+       TEST_ASSERT_VAL("wrong group name", !evsel->group_name);
+
+       /* group2 cycles + G modifier */
+       evsel = leader = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+       TEST_ASSERT_VAL("wrong group name",
+               !strcmp(leader->group_name, "group2"));
+
+       /* group2 1:3 + G modifier */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", 1 == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config", 3 == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+
+       /* instructions:u */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_INSTRUCTIONS == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       return 0;
+}
+
+static int test__group4(struct perf_evlist *evlist __maybe_unused)
+{
+       struct perf_evsel *evsel, *leader;
+
+       TEST_ASSERT_VAL("wrong number of entries", 2 == evlist->nr_entries);
+
+       /* cycles:u + p */
+       evsel = leader = perf_evlist__first(evlist);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip == 1);
+       TEST_ASSERT_VAL("wrong group name", !evsel->group_name);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       /* instructions:kp + p */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_INSTRUCTIONS == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", evsel->attr.precise_ip == 2);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+
+       return 0;
+}
+
+static int test__group5(struct perf_evlist *evlist __maybe_unused)
+{
+       struct perf_evsel *evsel, *leader;
+
+       TEST_ASSERT_VAL("wrong number of entries", 5 == evlist->nr_entries);
+
+       /* cycles + G */
+       evsel = leader = perf_evlist__first(evlist);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong group name", !evsel->group_name);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       /* instructions + G */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_INSTRUCTIONS == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+
+       /* cycles:G */
+       evsel = leader = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong group name", !evsel->group_name);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       /* instructions:G */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_INSTRUCTIONS == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", !evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == leader);
+
+       /* cycles */
+       evsel = perf_evsel__next(evsel);
+       TEST_ASSERT_VAL("wrong type", PERF_TYPE_HARDWARE == evsel->attr.type);
+       TEST_ASSERT_VAL("wrong config",
+                       PERF_COUNT_HW_CPU_CYCLES == evsel->attr.config);
+       TEST_ASSERT_VAL("wrong exclude_user", !evsel->attr.exclude_user);
+       TEST_ASSERT_VAL("wrong exclude_kernel", !evsel->attr.exclude_kernel);
+       TEST_ASSERT_VAL("wrong exclude_hv", !evsel->attr.exclude_hv);
+       TEST_ASSERT_VAL("wrong exclude guest", evsel->attr.exclude_guest);
+       TEST_ASSERT_VAL("wrong exclude host", !evsel->attr.exclude_host);
+       TEST_ASSERT_VAL("wrong precise_ip", !evsel->attr.precise_ip);
+       TEST_ASSERT_VAL("wrong leader", evsel->leader == NULL);
+
+       return 0;
+}
+
 struct test__event_st {
        const char *name;
        __u32 type;
@@ -632,6 +879,26 @@ static struct test__event_st test__events[] = {
                .name  = "mem:0:rw:kp",
                .check = test__checkevent_breakpoint_rw_modifier,
        },
+       [28] = {
+               .name  = "{instructions:k,cycles:upp}",
+               .check = test__group1,
+       },
+       [29] = {
+               .name  = "{faults:k,cache-references}:u,cycles:k",
+               .check = test__group2,
+       },
+       [30] = {
+               .name  = "group1{syscalls:sys_enter_open:H,cycles:kppp},group2{cycles,1:3}:G,instructions:u",
+               .check = test__group3,
+       },
+       [31] = {
+               .name  = "{cycles:u,instructions:kp}:p",
+               .check = test__group4,
+       },
+       [32] = {
+               .name  = "{cycles,instructions}:G,{cycles:G,instructions:G},cycles",
+               .check = test__group5,
+       },
 };
 
 static struct test__event_st test__events_pmu[] = {
@@ -658,9 +925,6 @@ static struct test__term test__terms[] = {
        },
 };
 
-#define TEST__TERMS_CNT (sizeof(test__terms) / \
-                        sizeof(struct test__term))
-
 static int test_event(struct test__event_st *e)
 {
        struct perf_evlist *evlist;
@@ -685,19 +949,19 @@ static int test_event(struct test__event_st *e)
 
 static int test_events(struct test__event_st *events, unsigned cnt)
 {
-       int ret = 0;
+       int ret1, ret2 = 0;
        unsigned i;
 
        for (i = 0; i < cnt; i++) {
                struct test__event_st *e = &events[i];
 
                pr_debug("running test %d '%s'\n", i, e->name);
-               ret = test_event(e);
-               if (ret)
-                       break;
+               ret1 = test_event(e);
+               if (ret1)
+                       ret2 = ret1;
        }
 
-       return ret;
+       return ret2;
 }
 
 static int test_term(struct test__term *t)
@@ -758,13 +1022,13 @@ static int test_pmu(void)
 
 int parse_events__test(void)
 {
-       int ret;
+       int ret1, ret2 = 0;
 
 #define TEST_EVENTS(tests)                             \
 do {                                                   \
-       ret = test_events(tests, ARRAY_SIZE(tests));    \
-       if (ret)                                        \
-               return ret;                             \
+       ret1 = test_events(tests, ARRAY_SIZE(tests));   \
+       if (!ret2)                                      \
+               ret2 = ret1;                            \
 } while (0)
 
        TEST_EVENTS(test__events);
@@ -772,5 +1036,9 @@ do {                                                       \
        if (test_pmu())
                TEST_EVENTS(test__events_pmu);
 
-       return test_terms(test__terms, ARRAY_SIZE(test__terms));
+       ret1 = test_terms(test__terms, ARRAY_SIZE(test__terms));
+       if (!ret2)
+               ret2 = ret1;
+
+       return ret2;
 }