selftests/resctrl: Replace file write with volatile variable
authorIlpo Järvinen <ilpo.jarvinen@linux.intel.com>
Fri, 15 Dec 2023 15:05:06 +0000 (17:05 +0200)
committerShuah Khan <skhan@linuxfoundation.org>
Tue, 13 Feb 2024 20:56:44 +0000 (13:56 -0700)
The fill_buf code prevents compiler optimizating the entire read loop
away by writing the final value of the variable into a file. While it
achieves the goal, writing into a file requires significant amount of
work within the innermost test loop and also error handling.

A simpler approach is to take advantage of volatile. Writing through
a pointer to a volatile variable is enough to prevent compiler from
optimizing the write away, and therefore compiler cannot remove the
read loop either.

Add a volatile 'value_sink' into resctrl_tests.c and make fill_buf to
write into it. As a result, the error handling in fill_buf.c can be
simplified.

Signed-off-by: Ilpo Järvinen <ilpo.jarvinen@linux.intel.com>
Reviewed-by: Reinette Chatre <reinette.chatre@intel.com>
Signed-off-by: Shuah Khan <skhan@linuxfoundation.org>
tools/testing/selftests/resctrl/fill_buf.c
tools/testing/selftests/resctrl/resctrl.h
tools/testing/selftests/resctrl/resctrl_tests.c

index 635f938b11f09614f24e42cf3c4351774f7d09a4..8fe9574db9d8b7f4ab7808149facbaa3a8439516 100644 (file)
@@ -78,10 +78,9 @@ static void fill_one_span_write(unsigned char *buf, size_t buf_size)
        }
 }
 
-static int fill_cache_read(unsigned char *buf, size_t buf_size, bool once)
+static void fill_cache_read(unsigned char *buf, size_t buf_size, bool once)
 {
        int ret = 0;
-       FILE *fp;
 
        while (1) {
                ret = fill_one_span_read(buf, buf_size);
@@ -90,26 +89,16 @@ static int fill_cache_read(unsigned char *buf, size_t buf_size, bool once)
        }
 
        /* Consume read result so that reading memory is not optimized out. */
-       fp = fopen("/dev/null", "w");
-       if (!fp) {
-               ksft_perror("Unable to write to /dev/null");
-               return -1;
-       }
-       fprintf(fp, "Sum: %d ", ret);
-       fclose(fp);
-
-       return 0;
+       *value_sink = ret;
 }
 
-static int fill_cache_write(unsigned char *buf, size_t buf_size, bool once)
+static void fill_cache_write(unsigned char *buf, size_t buf_size, bool once)
 {
        while (1) {
                fill_one_span_write(buf, buf_size);
                if (once)
                        break;
        }
-
-       return 0;
 }
 
 static unsigned char *alloc_buffer(size_t buf_size, int memflush)
@@ -143,21 +132,16 @@ static unsigned char *alloc_buffer(size_t buf_size, int memflush)
 int run_fill_buf(size_t buf_size, int memflush, int op, bool once)
 {
        unsigned char *buf;
-       int ret;
 
        buf = alloc_buffer(buf_size, memflush);
        if (!buf)
                return -1;
 
        if (op == 0)
-               ret = fill_cache_read(buf, buf_size, once);
+               fill_cache_read(buf, buf_size, once);
        else
-               ret = fill_cache_write(buf, buf_size, once);
+               fill_cache_write(buf, buf_size, once);
        free(buf);
-       if (ret) {
-               printf("\n Error in fill cache\n");
-               return -1;
-       }
 
        return 0;
 }
index f22b7897251e585d36657e5ddd6a4173667255c2..5b9bea50512015c28c5b5f0f2cc8c12a844df8a2 100644 (file)
@@ -78,6 +78,13 @@ struct perf_event_read {
 #define CMT_STR                        "cmt"
 #define CAT_STR                        "cat"
 
+/*
+ * Memory location that consumes values compiler must not optimize away.
+ * Volatile ensures writes to this location cannot be optimized away by
+ * compiler.
+ */
+extern volatile int *value_sink;
+
 extern pid_t bm_pid, ppid;
 
 extern char llc_occup_path[1024];
index 2bbe3045a018e2c09edb5785ca9e79d589c7d0f8..f0d573aa363b86453de5a22c9eac70c3c5f3c2b6 100644 (file)
  */
 #include "resctrl.h"
 
+/* Volatile memory sink to prevent compiler optimizations */
+static volatile int sink_target;
+volatile int *value_sink = &sink_target;
+
 static int detect_vendor(void)
 {
        FILE *inf = fopen("/proc/cpuinfo", "r");