Merge tag 'linux-kselftest-4.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel...
authorLinus Torvalds <torvalds@linux-foundation.org>
Sat, 7 Apr 2018 18:54:21 +0000 (11:54 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Sat, 7 Apr 2018 18:54:21 +0000 (11:54 -0700)
Pull kselftest update from Shuah Khan:
 "This Kselftest update for 4.17-rc1 consists of:

   - Test build error fixes

   - Fixes to prevent intel_pstate from building on non-x86 systems.

   - New test for ion with vgem driver.

   - Change to print the test name to /dev/kmsg to add context to kernel
     failures if any uncovered from running the test.

   - Kselftest framework enhancements to add KSFT_TAP_LEVEL environment
     variable to prevent nested TAP headers being printed in the
     Kselftest output.

     Nested TAP13 headers could cause problems for some parsers. This
     change suppresses the nested headers from test programs and test
     shell scripts with changes to framework and Makefiles without
     changing the tests"

* tag 'linux-kselftest-4.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest:
  selftests/intel_pstate: Fix build rule for x86
  selftests: Print the test we're running to /dev/kmsg
  selftests/seccomp: Allow get_metadata to XFAIL
  selftests/android/ion: Makefile: fix build error
  selftests: futex Makefile add top level TAP header echo to RUN_TESTS
  selftests: Makefile set KSFT_TAP_LEVEL to prevent nested TAP headers
  selftests: lib.mk set KSFT_TAP_LEVEL to prevent nested TAP headers
  selftests: kselftest framework: add handling for TAP header level
  selftests: ion: Add simple test with the vgem driver
  selftests: ion: Remove some prints

12 files changed:
tools/testing/selftests/Makefile
tools/testing/selftests/android/ion/.gitignore
tools/testing/selftests/android/ion/Makefile
tools/testing/selftests/android/ion/config
tools/testing/selftests/android/ion/ionmap_test.c [new file with mode: 0644]
tools/testing/selftests/android/ion/ionutils.c
tools/testing/selftests/futex/Makefile
tools/testing/selftests/intel_pstate/Makefile
tools/testing/selftests/kselftest.h
tools/testing/selftests/kselftest_harness.h
tools/testing/selftests/lib.mk
tools/testing/selftests/seccomp/seccomp_bpf.c

index dbda89c9d9b92544854c459364dcc1d37d8d5a32..bae6a4e9f2ee108bc7edc1749c0f2a3ebbb7b63d 100644 (file)
@@ -67,6 +67,12 @@ ifndef BUILD
   BUILD := $(shell pwd)
 endif
 
+# KSFT_TAP_LEVEL is used from KSFT framework to prevent nested TAP header
+# printing from tests. Applicable to run_tests case where run_tests adds
+# TAP header prior running tests and when a test program invokes another
+# with system() call. Export it here to cover override RUN_TESTS defines.
+export KSFT_TAP_LEVEL=`echo 1`
+
 export BUILD
 all:
        @for TARGET in $(TARGETS); do           \
@@ -126,11 +132,14 @@ ifdef INSTALL_PATH
        echo "else" >> $(ALL_SCRIPT)
        echo "  OUTPUT=/dev/stdout" >> $(ALL_SCRIPT)
        echo "fi" >> $(ALL_SCRIPT)
+       echo "export KSFT_TAP_LEVEL=`echo 1`" >> $(ALL_SCRIPT)
 
        for TARGET in $(TARGETS); do \
                BUILD_TARGET=$$BUILD/$$TARGET;  \
-               echo "echo ; echo Running tests in $$TARGET" >> $(ALL_SCRIPT); \
+               echo "echo ; echo TAP version 13" >> $(ALL_SCRIPT);     \
+               echo "echo Running tests in $$TARGET" >> $(ALL_SCRIPT); \
                echo "echo ========================================" >> $(ALL_SCRIPT); \
+               echo "[ -w /dev/kmsg ] && echo \"kselftest: Running tests in $$TARGET\" >> /dev/kmsg" >> $(ALL_SCRIPT); \
                echo "cd $$TARGET" >> $(ALL_SCRIPT); \
                make -s --no-print-directory OUTPUT=$$BUILD_TARGET -C $$TARGET emit_tests >> $(ALL_SCRIPT); \
                echo "cd \$$ROOT" >> $(ALL_SCRIPT); \
index 67e6f391b2a95c6a110b209989fa7fbfa2ed2d67..95e8f456147412f74299f11658a893925a949fe5 100644 (file)
@@ -1,2 +1,3 @@
 ionapp_export
 ionapp_import
+ionmap_test
index 96e0c448b39d31cf2846040c2df79b78998d9792..e03695287f763e809bfb78637f6ff166082efc1c 100644 (file)
@@ -1,8 +1,8 @@
 
-INCLUDEDIR := -I. -I../../../../../drivers/staging/android/uapi/
+INCLUDEDIR := -I. -I../../../../../drivers/staging/android/uapi/ -I../../../../../usr/include/
 CFLAGS := $(CFLAGS) $(INCLUDEDIR) -Wall -O2 -g
 
-TEST_GEN_FILES := ionapp_export ionapp_import
+TEST_GEN_FILES := ionapp_export ionapp_import ionmap_test
 
 all: $(TEST_GEN_FILES)
 
@@ -14,3 +14,4 @@ include ../../lib.mk
 
 $(OUTPUT)/ionapp_export: ionapp_export.c ipcsocket.c ionutils.c
 $(OUTPUT)/ionapp_import: ionapp_import.c ipcsocket.c ionutils.c
+$(OUTPUT)/ionmap_test: ionmap_test.c ionutils.c
index 19db6ca9aa2b2496f1c457a7053809dea6ec6739..b4ad748a9dd99a586af85c8d584880614a1863c7 100644 (file)
@@ -2,3 +2,4 @@ CONFIG_ANDROID=y
 CONFIG_STAGING=y
 CONFIG_ION=y
 CONFIG_ION_SYSTEM_HEAP=y
+CONFIG_DRM_VGEM=y
diff --git a/tools/testing/selftests/android/ion/ionmap_test.c b/tools/testing/selftests/android/ion/ionmap_test.c
new file mode 100644 (file)
index 0000000..dab36b0
--- /dev/null
@@ -0,0 +1,136 @@
+#include <errno.h>
+#include <fcntl.h>
+#include <stdio.h>
+#include <stdint.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <sys/ioctl.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+
+#include <linux/dma-buf.h>
+
+#include <drm/drm.h>
+
+#include "ion.h"
+#include "ionutils.h"
+
+int check_vgem(int fd)
+{
+       drm_version_t version = { 0 };
+       char name[5];
+       int ret;
+
+       version.name_len = 4;
+       version.name = name;
+
+       ret = ioctl(fd, DRM_IOCTL_VERSION, &version);
+       if (ret)
+               return 1;
+
+       return strcmp(name, "vgem");
+}
+
+int open_vgem(void)
+{
+       int i, fd;
+       const char *drmstr = "/dev/dri/card";
+
+       fd = -1;
+       for (i = 0; i < 16; i++) {
+               char name[80];
+
+               sprintf(name, "%s%u", drmstr, i);
+
+               fd = open(name, O_RDWR);
+               if (fd < 0)
+                       continue;
+
+               if (check_vgem(fd)) {
+                       close(fd);
+                       continue;
+               } else {
+                       break;
+               }
+
+       }
+       return fd;
+}
+
+int import_vgem_fd(int vgem_fd, int dma_buf_fd, uint32_t *handle)
+{
+       struct drm_prime_handle import_handle = { 0 };
+       int ret;
+
+       import_handle.fd = dma_buf_fd;
+       import_handle.flags = 0;
+       import_handle.handle = 0;
+
+       ret = ioctl(vgem_fd, DRM_IOCTL_PRIME_FD_TO_HANDLE, &import_handle);
+       if (ret == 0)
+               *handle = import_handle.handle;
+       return ret;
+}
+
+void close_handle(int vgem_fd, uint32_t handle)
+{
+       struct drm_gem_close close = { 0 };
+
+       close.handle = handle;
+       ioctl(vgem_fd, DRM_IOCTL_GEM_CLOSE, &close);
+}
+
+int main()
+{
+       int ret, vgem_fd;
+       struct ion_buffer_info info;
+       uint32_t handle = 0;
+       struct dma_buf_sync sync = { 0 };
+
+       info.heap_type = ION_HEAP_TYPE_SYSTEM;
+       info.heap_size = 4096;
+       info.flag_type = ION_FLAG_CACHED;
+
+       ret = ion_export_buffer_fd(&info);
+       if (ret < 0) {
+               printf("ion buffer alloc failed\n");
+               return -1;
+       }
+
+       vgem_fd = open_vgem();
+       if (vgem_fd < 0) {
+               ret = vgem_fd;
+               printf("Failed to open vgem\n");
+               goto out_ion;
+       }
+
+       ret = import_vgem_fd(vgem_fd, info.buffd, &handle);
+
+       if (ret < 0) {
+               printf("Failed to import buffer\n");
+               goto out_vgem;
+       }
+
+       sync.flags = DMA_BUF_SYNC_START | DMA_BUF_SYNC_RW;
+       ret = ioctl(info.buffd, DMA_BUF_IOCTL_SYNC, &sync);
+       if (ret)
+               printf("sync start failed %d\n", errno);
+
+       memset(info.buffer, 0xff, 4096);
+
+       sync.flags = DMA_BUF_SYNC_END | DMA_BUF_SYNC_RW;
+       ret = ioctl(info.buffd, DMA_BUF_IOCTL_SYNC, &sync);
+       if (ret)
+               printf("sync end failed %d\n", errno);
+
+       close_handle(vgem_fd, handle);
+       ret = 0;
+
+out_vgem:
+       close(vgem_fd);
+out_ion:
+       ion_close_buffer_fd(&info);
+       printf("done.\n");
+       return ret;
+}
index ce69c14f51fac6ab84f394656e5d3eaed1ed7ba6..7d1d37c4ef6af6ec3e306188c7e68e639fca9d5a 100644 (file)
@@ -80,11 +80,6 @@ int ion_export_buffer_fd(struct ion_buffer_info *ion_info)
        heap_id = MAX_HEAP_COUNT + 1;
        for (i = 0; i < query.cnt; i++) {
                if (heap_data[i].type == ion_info->heap_type) {
-                       printf("--------------------------------------\n");
-                       printf("heap type: %d\n", heap_data[i].type);
-                       printf("  heap id: %d\n", heap_data[i].heap_id);
-                       printf("heap name: %s\n", heap_data[i].name);
-                       printf("--------------------------------------\n");
                        heap_id = heap_data[i].heap_id;
                        break;
                }
@@ -204,7 +199,6 @@ void ion_close_buffer_fd(struct ion_buffer_info *ion_info)
                /* Finally, close the client fd */
                if (ion_info->ionfd > 0)
                        close(ion_info->ionfd);
-               printf("<%s>: buffer release successfully....\n", __func__);
        }
 }
 
index a63e8453984d2793eb38b706236f31dc49527e9b..8497a376ef9d5eaa7d8969146655d45a82281449 100644 (file)
@@ -18,6 +18,10 @@ all:
        done
 
 override define RUN_TESTS
+       @export KSFT_TAP_LEVEL=`echo 1`;
+       @echo "TAP version 13";
+       @echo "selftests: futex";
+       @echo "========================================";
        @cd $(OUTPUT); ./run.sh
 endef
 
index 5a3f7d37e91214b88d2e1af2f63f44d84e1ef11a..7340fd6a9a9f2cbd0d0f16ad7388d674b0ae0fb5 100644 (file)
@@ -2,7 +2,10 @@
 CFLAGS := $(CFLAGS) -Wall -D_GNU_SOURCE
 LDLIBS := $(LDLIBS) -lm
 
-ifeq (,$(filter $(ARCH),x86))
+uname_M := $(shell uname -m 2>/dev/null || echo not)
+ARCH ?= $(shell echo $(uname_M) | sed -e s/i.86/x86/ -e s/x86_64/x86/)
+
+ifeq (x86,$(ARCH))
 TEST_GEN_FILES := msr aperf
 endif
 
index 1a52b03962a3f9481969dd6af6c2f5d60ed590e5..1b9d8ecdebce271ad5b643aea91f639b47c94bec 100644 (file)
@@ -57,7 +57,8 @@ static inline int ksft_get_error_cnt(void) { return ksft_cnt.ksft_error; }
 
 static inline void ksft_print_header(void)
 {
-       printf("TAP version 13\n");
+       if (!(getenv("KSFT_TAP_LEVEL")))
+               printf("TAP version 13\n");
 }
 
 static inline void ksft_print_cnts(void)
index e81bd28bdd8940366eacb3bda6428bf7d47b5f24..6ae3730c4ee35b1cfc2e93ed39aac6b2bf3755ad 100644 (file)
                fprintf(TH_LOG_STREAM, "%s:%d:%s:" fmt "\n", \
                        __FILE__, __LINE__, _metadata->name, ##__VA_ARGS__)
 
+/**
+ * XFAIL(statement, fmt, ...)
+ *
+ * @statement: statement to run after reporting XFAIL
+ * @fmt: format string
+ * @...: optional arguments
+ *
+ * This forces a "pass" after reporting a failure with an XFAIL prefix,
+ * and runs "statement", which is usually "return" or "goto skip".
+ */
+#define XFAIL(statement, fmt, ...) do { \
+       if (TH_LOG_ENABLED) { \
+               fprintf(TH_LOG_STREAM, "[  XFAIL!  ] " fmt "\n", \
+                       ##__VA_ARGS__); \
+       } \
+       /* TODO: find a way to pass xfail to test runner process. */ \
+       _metadata->passed = 1; \
+       _metadata->trigger = 0; \
+       statement; \
+} while (0)
+
 /**
  * TEST(test_name) - Defines the test function and creates the registration
  * stub
 
 /**
  * FIXTURE_SETUP(fixture_name) - Prepares the setup function for the fixture.
- * *_metadata* is included so that ASSERT_* work as a convenience
+ * *_metadata* is included so that EXPECT_* and ASSERT_* work correctly.
  *
  * @fixture_name: fixture name
  *
                FIXTURE_DATA(fixture_name) __attribute__((unused)) *self)
 /**
  * FIXTURE_TEARDOWN(fixture_name)
+ * *_metadata* is included so that EXPECT_* and ASSERT_* work correctly.
  *
  * @fixture_name: fixture name
  *
  * Defines a test that depends on a fixture (e.g., is part of a test case).
  * Very similar to TEST() except that *self* is the setup instance of fixture's
  * datatype exposed for use by the implementation.
+ *
+ * Warning: use of ASSERT_* here will skip TEARDOWN.
  */
 /* TODO(wad) register fixtures on dedicated test lists. */
 #define TEST_F(fixture_name, test_name) \
index 7de482a0519dbbc9889e8d969d064bae4d29b3d5..195e9d4739a98d6aee0fb10f2c074b2a55bcf531 100644 (file)
@@ -20,6 +20,7 @@ all: $(TEST_GEN_PROGS) $(TEST_GEN_PROGS_EXTENDED) $(TEST_GEN_FILES)
 
 .ONESHELL:
 define RUN_TESTS
+       @export KSFT_TAP_LEVEL=`echo 1`;
        @test_num=`echo 0`;
        @echo "TAP version 13";
        @for TEST in $(1); do                           \
index 5df609950a666f8000307653a0b1e8d4368549a2..168c66d74fc5ca67f300cd7235182e4fd3d572aa 100644 (file)
@@ -2860,6 +2860,7 @@ TEST(get_metadata)
        int pipefd[2];
        char buf;
        struct seccomp_metadata md;
+       long ret;
 
        ASSERT_EQ(0, pipe(pipefd));
 
@@ -2893,16 +2894,26 @@ TEST(get_metadata)
        ASSERT_EQ(0, ptrace(PTRACE_ATTACH, pid));
        ASSERT_EQ(pid, waitpid(pid, NULL, 0));
 
+       /* Past here must not use ASSERT or child process is never killed. */
+
        md.filter_off = 0;
-       ASSERT_EQ(sizeof(md), ptrace(PTRACE_SECCOMP_GET_METADATA, pid, sizeof(md), &md));
+       errno = 0;
+       ret = ptrace(PTRACE_SECCOMP_GET_METADATA, pid, sizeof(md), &md);
+       EXPECT_EQ(sizeof(md), ret) {
+               if (errno == EINVAL)
+                       XFAIL(goto skip, "Kernel does not support PTRACE_SECCOMP_GET_METADATA (missing CONFIG_CHECKPOINT_RESTORE?)");
+       }
+
        EXPECT_EQ(md.flags, SECCOMP_FILTER_FLAG_LOG);
        EXPECT_EQ(md.filter_off, 0);
 
        md.filter_off = 1;
-       ASSERT_EQ(sizeof(md), ptrace(PTRACE_SECCOMP_GET_METADATA, pid, sizeof(md), &md));
+       ret = ptrace(PTRACE_SECCOMP_GET_METADATA, pid, sizeof(md), &md);
+       EXPECT_EQ(sizeof(md), ret);
        EXPECT_EQ(md.flags, 0);
        EXPECT_EQ(md.filter_off, 1);
 
+skip:
        ASSERT_EQ(0, kill(pid, SIGKILL));
 }