Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0
0002 #include <errno.h>
0003 #include <limits.h>
0004 #include <stdio.h>
0005 #include <stdlib.h>
0006 #include <unistd.h>
0007 #include <sys/epoll.h>
0008 #include <util/symbol.h>
0009 #include <linux/filter.h>
0010 #include "tests.h"
0011 #include "debug.h"
0012 #include "probe-file.h"
0013 #include "build-id.h"
0014 #include "util.h"
0015 
0016 /* To test SDT event, we need libelf support to scan elf binary */
0017 #if defined(HAVE_SDT_EVENT) && defined(HAVE_LIBELF_SUPPORT)
0018 
0019 #include <sys/sdt.h>
0020 
0021 static int target_function(void)
0022 {
0023     DTRACE_PROBE(perf, test_target);
0024     return TEST_OK;
0025 }
0026 
0027 /* Copied from builtin-buildid-cache.c */
0028 static int build_id_cache__add_file(const char *filename)
0029 {
0030     char sbuild_id[SBUILD_ID_SIZE];
0031     struct build_id bid;
0032     int err;
0033 
0034     err = filename__read_build_id(filename, &bid);
0035     if (err < 0) {
0036         pr_debug("Failed to read build id of %s\n", filename);
0037         return err;
0038     }
0039 
0040     build_id__sprintf(&bid, sbuild_id);
0041     err = build_id_cache__add_s(sbuild_id, filename, NULL, false, false);
0042     if (err < 0)
0043         pr_debug("Failed to add build id cache of %s\n", filename);
0044     return err;
0045 }
0046 
0047 static char *get_self_path(void)
0048 {
0049     char *buf = calloc(PATH_MAX, sizeof(char));
0050 
0051     if (buf && readlink("/proc/self/exe", buf, PATH_MAX - 1) < 0) {
0052         pr_debug("Failed to get correct path of perf\n");
0053         free(buf);
0054         return NULL;
0055     }
0056     return buf;
0057 }
0058 
0059 static int search_cached_probe(const char *target,
0060                    const char *group, const char *event)
0061 {
0062     struct probe_cache *cache = probe_cache__new(target, NULL);
0063     int ret = 0;
0064 
0065     if (!cache) {
0066         pr_debug("Failed to open probe cache of %s\n", target);
0067         return -EINVAL;
0068     }
0069 
0070     if (!probe_cache__find_by_name(cache, group, event)) {
0071         pr_debug("Failed to find %s:%s in the cache\n", group, event);
0072         ret = -ENOENT;
0073     }
0074     probe_cache__delete(cache);
0075 
0076     return ret;
0077 }
0078 
0079 static int test__sdt_event(struct test_suite *test __maybe_unused, int subtests __maybe_unused)
0080 {
0081     int ret = TEST_FAIL;
0082     char __tempdir[] = "./test-buildid-XXXXXX";
0083     char *tempdir = NULL, *myself = get_self_path();
0084 
0085     if (myself == NULL || mkdtemp(__tempdir) == NULL) {
0086         pr_debug("Failed to make a tempdir for build-id cache\n");
0087         goto error;
0088     }
0089     /* Note that buildid_dir must be an absolute path */
0090     tempdir = realpath(__tempdir, NULL);
0091     if (tempdir == NULL)
0092         goto error_rmdir;
0093 
0094     /* At first, scan itself */
0095     set_buildid_dir(tempdir);
0096     if (build_id_cache__add_file(myself) < 0)
0097         goto error_rmdir;
0098 
0099     /* Open a cache and make sure the SDT is stored */
0100     if (search_cached_probe(myself, "sdt_perf", "test_target") < 0)
0101         goto error_rmdir;
0102 
0103     /* TBD: probing on the SDT event and collect logs */
0104 
0105     /* Call the target and get an event */
0106     ret = target_function();
0107 
0108 error_rmdir:
0109     /* Cleanup temporary buildid dir */
0110     rm_rf(__tempdir);
0111 error:
0112     free(tempdir);
0113     free(myself);
0114     return ret;
0115 }
0116 #else
0117 static int test__sdt_event(struct test_suite *test __maybe_unused, int subtests __maybe_unused)
0118 {
0119     pr_debug("Skip SDT event test because SDT support is not compiled\n");
0120     return TEST_SKIP;
0121 }
0122 #endif
0123 
0124 DEFINE_SUITE("Probe SDT events", sdt_event);