[v3,14/25] Merge reginfo.c into risu.c

Message ID 20200522023440.26261-15-richard.henderson@linaro.org
State New
Headers show
Series
  • risu cleanups and improvements
Related show

Commit Message

Richard Henderson May 22, 2020, 2:34 a.m.
The distinction between the two is artificial.  Following
patches will rearrange the functions involved to make it
easier for dumping of the trace file.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>

---
 Makefile  |   2 +-
 risu.h    |  28 +---------
 reginfo.c | 151 ------------------------------------------------------
 risu.c    | 129 ++++++++++++++++++++++++++++++++++++++++++++--
 4 files changed, 126 insertions(+), 184 deletions(-)
 delete mode 100644 reginfo.c

-- 
2.20.1

Comments

Alex Bennée June 23, 2020, 8:33 a.m. | #1
Richard Henderson <richard.henderson@linaro.org> writes:

> The distinction between the two is artificial.  Following

> patches will rearrange the functions involved to make it

> easier for dumping of the trace file.

>

> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>


Reviewed-by: Alex Bennée <alex.bennee@linaro.org>


-- 
Alex Bennée

Patch

diff --git a/Makefile b/Makefile
index 6ab014a..ad7f879 100644
--- a/Makefile
+++ b/Makefile
@@ -20,7 +20,7 @@  CFLAGS ?= -g
 ALL_CFLAGS = -Wall -D_GNU_SOURCE -DARCH=$(ARCH) -U$(ARCH) $(BUILD_INC) $(CFLAGS) $(EXTRA_CFLAGS)
 
 PROG=risu
-SRCS=risu.c comms.c reginfo.c risu_$(ARCH).c risu_reginfo_$(ARCH).c
+SRCS=risu.c comms.c risu_$(ARCH).c risu_reginfo_$(ARCH).c
 HDRS=risu.h risu_reginfo_$(ARCH).h
 BINS=test_$(ARCH).bin
 
diff --git a/risu.h b/risu.h
index 77d6128..dd9fda5 100644
--- a/risu.h
+++ b/risu.h
@@ -35,7 +35,6 @@  void process_arch_opt(int opt, const char *arg);
 #include REGINFO_HEADER(ARCH)
 
 extern uintptr_t image_start_address;
-extern void *memblock;
 
 /* Ops code under test can request from risu: */
 typedef enum {
@@ -83,34 +82,9 @@  void send_response_byte(int sock, int resp);
 
 /* Functions operating on reginfo */
 
-/* Function prototypes for read/write helper functions. */
-RisuResult write_buffer(void *ptr, size_t bytes);
-RisuResult read_buffer(void *ptr, size_t bytes);
-void respond(RisuResult response);
-
-/*
- * Send the register information from the struct ucontext down the socket.
- * NB: called from a signal handler.
- */
-RisuResult send_register_info(void *uc);
-
-/*
- * Read register info from the socket and compare it with that from the
- * ucontext.
- * NB: called from a signal handler.
- */
-RisuResult recv_and_compare_register_info(void *uc);
-
-/*
- * Print a useful report on the status of the last reg comparison
- * done in recv_and_compare_register_info().
- */
-void report_mismatch_reg(void);
-
 /* Interface provided by CPU-specific code: */
 
-/* Move the PC past this faulting insn by adjusting ucontext
- */
+/* Move the PC past this faulting insn by adjusting ucontext. */
 void advance_pc(void *uc);
 
 /* Set the parameter register in a ucontext_t to the specified value.
diff --git a/reginfo.c b/reginfo.c
deleted file mode 100644
index a007f16..0000000
--- a/reginfo.c
+++ /dev/null
@@ -1,151 +0,0 @@ 
-/******************************************************************************
- * Copyright (c) 2017 Linaro Limited
- * All rights reserved. This program and the accompanying materials
- * are made available under the terms of the Eclipse Public License v1.0
- * which accompanies this distribution, and is available at
- * http://www.eclipse.org/legal/epl-v10.html
- *
- * Contributors:
- *     Peter Maydell (Linaro) - initial implementation
- *****************************************************************************/
-
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-#include "risu.h"
-
-static struct reginfo master_ri, apprentice_ri;
-static uint8_t master_memblock[MEMBLOCKLEN];
-
-RisuResult send_register_info(void *uc)
-{
-    struct reginfo ri;
-    trace_header_t header;
-    RisuResult res;
-    RisuOp op;
-
-    reginfo_init(&ri, uc);
-    op = get_risuop(&ri);
-
-    /* Write a header with PC/op to keep in sync */
-    header.pc = get_pc(&ri);
-    header.risu_op = op;
-    res = write_buffer(&header, sizeof(header));
-    if (res != RES_OK) {
-        return res;
-    }
-
-    switch (op) {
-    case OP_COMPARE:
-    case OP_TESTEND:
-    case OP_SIGILL:
-        /*
-         * Do a simple register compare on (a) explicit request
-         * (b) end of test (c) a non-risuop UNDEF
-         */
-        res = write_buffer(&ri, reginfo_size());
-        /* For OP_TEST_END, force exit. */
-        if (res == RES_OK && op == OP_TESTEND) {
-            res = RES_END;
-        }
-        break;
-    case OP_SETMEMBLOCK:
-        memblock = (void *)(uintptr_t)get_reginfo_paramreg(&ri);
-        break;
-    case OP_GETMEMBLOCK:
-        set_ucontext_paramreg(uc,
-                              get_reginfo_paramreg(&ri) + (uintptr_t)memblock);
-        break;
-    case OP_COMPAREMEM:
-        return write_buffer(memblock, MEMBLOCKLEN);
-    default:
-        abort();
-    }
-    return res;
-}
-
-/* Read register info from the socket and compare it with that from the
- * ucontext. Return 0 for match, 1 for end-of-test, 2 for mismatch.
- * NB: called from a signal handler.
- *
- * We don't have any kind of identifying info in the incoming data
- * that says whether it is register or memory data, so if the two
- * sides get out of sync then we will fail obscurely.
- */
-RisuResult recv_and_compare_register_info(void *uc)
-{
-    RisuResult res;
-    trace_header_t header;
-    RisuOp op;
-
-    reginfo_init(&apprentice_ri, uc);
-    op = get_risuop(&apprentice_ri);
-
-    res = read_buffer(&header, sizeof(header));
-    if (res != RES_OK) {
-        return res;
-    }
-
-    if (header.risu_op != op) {
-        /* We are out of sync.  Tell master to exit. */
-        respond(RES_END);
-        return RES_BAD_IO;
-    }
-
-    /* send OK for the header */
-    respond(RES_OK);
-
-    switch (op) {
-    case OP_COMPARE:
-    case OP_TESTEND:
-    case OP_SIGILL:
-        /* Do a simple register compare on (a) explicit request
-         * (b) end of test (c) a non-risuop UNDEF
-         */
-        res = read_buffer(&master_ri, reginfo_size());
-        if (res != RES_OK) {
-            /* fail */
-        } else if (!reginfo_is_eq(&master_ri, &apprentice_ri)) {
-            /* register mismatch */
-            res = RES_MISMATCH_REG;
-        } else if (op == OP_TESTEND) {
-            res = RES_END;
-        }
-        respond(res == RES_OK ? RES_OK : RES_END);
-        break;
-    case OP_SETMEMBLOCK:
-        memblock = (void *)(uintptr_t)get_reginfo_paramreg(&apprentice_ri);
-        break;
-    case OP_GETMEMBLOCK:
-        set_ucontext_paramreg(uc, get_reginfo_paramreg(&apprentice_ri) +
-                              (uintptr_t)memblock);
-        break;
-    case OP_COMPAREMEM:
-        res = read_buffer(master_memblock, MEMBLOCKLEN);
-        if (res != RES_OK) {
-            /* fail */
-        } else if (memcmp(memblock, master_memblock, MEMBLOCKLEN) != 0) {
-            /* memory mismatch */
-            res = RES_MISMATCH_MEM;
-        }
-        respond(res == RES_OK ? RES_OK : RES_END);
-        break;
-    default:
-        abort();
-    }
-
-    return res;
-}
-
-/*
- * Print a useful report on the status of the last reg comparison
- * done in recv_and_compare_register_info().
- */
-void report_mismatch_reg(void)
-{
-    fprintf(stderr, "master reginfo:\n");
-    reginfo_dump(&master_ri, stderr);
-    fprintf(stderr, "apprentice reginfo:\n");
-    reginfo_dump(&apprentice_ri, stderr);
-    reginfo_dump_mismatch(&master_ri, &apprentice_ri, stderr);
-}
diff --git a/risu.c b/risu.c
index d6c2deb..a0e20d5 100644
--- a/risu.c
+++ b/risu.c
@@ -28,7 +28,10 @@ 
 #include "config.h"
 #include "risu.h"
 
-void *memblock;
+static void *memblock;
+static struct reginfo master_ri, apprentice_ri;
+static uint8_t master_memblock[MEMBLOCKLEN];
+
 
 static int comm_fd;
 static bool trace;
@@ -48,7 +51,7 @@  static sigjmp_buf jmpbuf;
 
 /* I/O functions */
 
-RisuResult read_buffer(void *ptr, size_t bytes)
+static RisuResult read_buffer(void *ptr, size_t bytes)
 {
     size_t res;
 
@@ -69,7 +72,7 @@  RisuResult read_buffer(void *ptr, size_t bytes)
     return res == bytes ? RES_OK : RES_BAD_IO;
 }
 
-RisuResult write_buffer(void *ptr, size_t bytes)
+static RisuResult write_buffer(void *ptr, size_t bytes)
 {
     size_t res;
 
@@ -90,13 +93,60 @@  RisuResult write_buffer(void *ptr, size_t bytes)
     return res == bytes ? RES_OK : RES_BAD_IO;
 }
 
-void respond(RisuResult r)
+static void respond(RisuResult r)
 {
     if (!trace) {
         send_response_byte(comm_fd, r);
     }
 }
 
+static RisuResult send_register_info(void *uc)
+{
+    struct reginfo ri;
+    trace_header_t header;
+    RisuResult res;
+    RisuOp op;
+
+    reginfo_init(&ri, uc);
+    op = get_risuop(&ri);
+
+    /* Write a header with PC/op to keep in sync */
+    header.pc = get_pc(&ri);
+    header.risu_op = op;
+    res = write_buffer(&header, sizeof(header));
+    if (res != RES_OK) {
+        return res;
+    }
+
+    switch (op) {
+    case OP_COMPARE:
+    case OP_TESTEND:
+    case OP_SIGILL:
+        /*
+         * Do a simple register compare on (a) explicit request
+         * (b) end of test (c) a non-risuop UNDEF
+         */
+        res = write_buffer(&ri, reginfo_size());
+        /* For OP_TEST_END, force exit. */
+        if (res == RES_OK && op == OP_TESTEND) {
+            res = RES_END;
+        }
+        break;
+    case OP_SETMEMBLOCK:
+        memblock = (void *)(uintptr_t)get_reginfo_paramreg(&ri);
+        break;
+    case OP_GETMEMBLOCK:
+        set_ucontext_paramreg(uc,
+                              get_reginfo_paramreg(&ri) + (uintptr_t)memblock);
+        break;
+    case OP_COMPAREMEM:
+        return write_buffer(memblock, MEMBLOCKLEN);
+    default:
+        abort();
+    }
+    return res;
+}
+
 static void master_sigill(int sig, siginfo_t *si, void *uc)
 {
     RisuResult r;
@@ -110,6 +160,71 @@  static void master_sigill(int sig, siginfo_t *si, void *uc)
     }
 }
 
+static RisuResult recv_and_compare_register_info(void *uc)
+{
+    RisuResult res;
+    trace_header_t header;
+    RisuOp op;
+
+    reginfo_init(&apprentice_ri, uc);
+    op = get_risuop(&apprentice_ri);
+
+    res = read_buffer(&header, sizeof(header));
+    if (res != RES_OK) {
+        return res;
+    }
+
+    if (header.risu_op != op) {
+        /* We are out of sync.  Tell master to exit. */
+        respond(RES_END);
+        return RES_BAD_IO;
+    }
+
+    /* send OK for the header */
+    respond(RES_OK);
+
+    switch (op) {
+    case OP_COMPARE:
+    case OP_TESTEND:
+    case OP_SIGILL:
+        /* Do a simple register compare on (a) explicit request
+         * (b) end of test (c) a non-risuop UNDEF
+         */
+        res = read_buffer(&master_ri, reginfo_size());
+        if (res != RES_OK) {
+            /* fail */
+        } else if (!reginfo_is_eq(&master_ri, &apprentice_ri)) {
+            /* register mismatch */
+            res = RES_MISMATCH_REG;
+        } else if (op == OP_TESTEND) {
+            res = RES_END;
+        }
+        respond(res == RES_OK ? RES_OK : RES_END);
+        break;
+    case OP_SETMEMBLOCK:
+        memblock = (void *)(uintptr_t)get_reginfo_paramreg(&apprentice_ri);
+        break;
+    case OP_GETMEMBLOCK:
+        set_ucontext_paramreg(uc, get_reginfo_paramreg(&apprentice_ri) +
+                              (uintptr_t)memblock);
+        break;
+    case OP_COMPAREMEM:
+        res = read_buffer(master_memblock, MEMBLOCKLEN);
+        if (res != RES_OK) {
+            /* fail */
+        } else if (memcmp(memblock, master_memblock, MEMBLOCKLEN) != 0) {
+            /* memory mismatch */
+            res = RES_MISMATCH_MEM;
+        }
+        respond(res == RES_OK ? RES_OK : RES_END);
+        break;
+    default:
+        abort();
+    }
+
+    return res;
+}
+
 static void apprentice_sigill(int sig, siginfo_t *si, void *uc)
 {
     RisuResult r;
@@ -226,7 +341,11 @@  static int apprentice(void)
 
     case RES_MISMATCH_REG:
         fprintf(stderr, "mismatch reg after %zd checkpoints\n", signal_count);
-        report_mismatch_reg();
+        fprintf(stderr, "master reginfo:\n");
+        reginfo_dump(&master_ri, stderr);
+        fprintf(stderr, "apprentice reginfo:\n");
+        reginfo_dump(&apprentice_ri, stderr);
+        reginfo_dump_mismatch(&master_ri, &apprentice_ri, stderr);
         return EXIT_FAILURE;
 
     case RES_MISMATCH_MEM: