Blob Blame History Raw
commit 9d6e165ea7cf9da0086b9b107d6dd2498f1af6d0
Author: Julian Seward <jseward@acm.org>
Date:   Mon Apr 24 09:24:57 2017 +0000

    Bug 369459 - valgrind on arm64 violates the ARMv8 spec (ldxr/stxr)
    
    This implements a fallback LL/SC implementation as described in bug 344524.
    
    Valgrind side changes:
    
    * Command line plumbing for --sim-hints=fallback-llsc
    
    * memcheck: handle new arm64 guest state in memcheck/mc_machine.c
    
    
    
    git-svn-id: svn://svn.valgrind.org/valgrind/trunk@16309

diff --git a/coregrind/m_main.c b/coregrind/m_main.c
index 9a4b60e..424daf7 100644
--- a/coregrind/m_main.c
+++ b/coregrind/m_main.c
@@ -187,7 +187,7 @@ static void usage_NORETURN ( Bool debug_help )
 "    --sim-hints=hint1,hint2,...  activate unusual sim behaviours [none] \n"
 "         where hint is one of:\n"
 "           lax-ioctls lax-doors fuse-compatible enable-outer\n"
-"           no-inner-prefix no-nptl-pthread-stackcache none\n"
+"           no-inner-prefix no-nptl-pthread-stackcache fallback-llsc none\n"
 "    --fair-sched=no|yes|try   schedule threads fairly on multicore systems [no]\n"
 "    --kernel-variant=variant1,variant2,...\n"
 "         handle non-standard kernel variants [none]\n"
@@ -417,7 +417,7 @@ static void early_process_cmd_line_options ( /*OUT*/Int* need_help )
       else if VG_USETX_CLO (str, "--sim-hints",
                             "lax-ioctls,lax-doors,fuse-compatible,"
                             "enable-outer,no-inner-prefix,"
-                            "no-nptl-pthread-stackcache",
+                            "no-nptl-pthread-stackcache,fallback-llsc",
                             VG_(clo_sim_hints)) {}
    }
 
diff --git a/coregrind/m_scheduler/scheduler.c b/coregrind/m_scheduler/scheduler.c
index 9ae3f21..96a24f8 100644
--- a/coregrind/m_scheduler/scheduler.c
+++ b/coregrind/m_scheduler/scheduler.c
@@ -925,6 +925,14 @@ void run_thread_for_a_while ( /*OUT*/HWord* two_words,
    tst->arch.vex.host_EvC_FAILADDR
       = (HWord)VG_(fnptr_to_fnentry)( &VG_(disp_cp_evcheck_fail) );
 
+   /* Invalidate any in-flight LL/SC transactions, in the case that we're
+      using the fallback LL/SC implementation.  See bugs 344524 and 369459. */
+#  if defined(VGP_mips32_linux) || defined(VGP_mips64_linux)
+   tst->arch.vex.guest_LLaddr = (HWord)(-1);
+#  elif defined(VGP_arm64_linux)
+   tst->arch.vex.guest_LLSC_SIZE = 0;
+#  endif
+
    if (0) {
       vki_sigset_t m;
       Int i, err = VG_(sigprocmask)(VKI_SIG_SETMASK, NULL, &m);
diff --git a/coregrind/m_translate.c b/coregrind/m_translate.c
index 2d6d3ba..c467e33 100644
--- a/coregrind/m_translate.c
+++ b/coregrind/m_translate.c
@@ -1663,30 +1663,51 @@ Bool VG_(translate) ( ThreadId tid,
    vex_abiinfo.guest_amd64_assume_fs_is_const = True;
    vex_abiinfo.guest_amd64_assume_gs_is_const = True;
 #  endif
+
 #  if defined(VGP_amd64_darwin)
    vex_abiinfo.guest_amd64_assume_gs_is_const = True;
 #  endif
+
+#  if defined(VGP_amd64_solaris)
+   vex_abiinfo.guest_amd64_assume_fs_is_const = True;
+#  endif
+
 #  if defined(VGP_ppc32_linux)
    vex_abiinfo.guest_ppc_zap_RZ_at_blr        = False;
    vex_abiinfo.guest_ppc_zap_RZ_at_bl         = NULL;
 #  endif
+
 #  if defined(VGP_ppc64be_linux)
    vex_abiinfo.guest_ppc_zap_RZ_at_blr        = True;
    vex_abiinfo.guest_ppc_zap_RZ_at_bl         = const_True;
    vex_abiinfo.host_ppc_calls_use_fndescrs    = True;
 #  endif
+
 #  if defined(VGP_ppc64le_linux)
    vex_abiinfo.guest_ppc_zap_RZ_at_blr        = True;
    vex_abiinfo.guest_ppc_zap_RZ_at_bl         = const_True;
    vex_abiinfo.host_ppc_calls_use_fndescrs    = False;
 #  endif
-#  if defined(VGP_amd64_solaris)
-   vex_abiinfo.guest_amd64_assume_fs_is_const = True;
-#  endif
+
 #  if defined(VGP_mips32_linux) || defined(VGP_mips64_linux)
    ThreadArchState* arch = &VG_(threads)[tid].arch;
    vex_abiinfo.guest_mips_fp_mode64 =
       !!(arch->vex.guest_CP0_status & MIPS_CP0_STATUS_FR);
+   /* Compute guest__use_fallback_LLSC, overiding any settings of
+      VG_(clo_fallback_llsc) that we know would cause the guest to
+      fail (loop). */
+   if (VEX_MIPS_COMP_ID(archinfo->hwcaps) == VEX_PRID_COMP_CAVIUM) {
+      /* We must use the fallback scheme. */
+      vex_abiinfo.guest__use_fallback_LLSC = True;
+   } else {
+      vex_abiinfo.guest__use_fallback_LLSC
+         = SimHintiS(SimHint_fallback_llsc, VG_(clo_sim_hints));
+   }
+#  endif
+
+#  if defined(VGP_arm64_linux)
+   vex_abiinfo.guest__use_fallback_LLSC
+      = SimHintiS(SimHint_fallback_llsc, VG_(clo_sim_hints));
 #  endif
 
    /* Set up closure args. */
diff --git a/coregrind/pub_core_options.h b/coregrind/pub_core_options.h
index ba27127..703d08a 100644
--- a/coregrind/pub_core_options.h
+++ b/coregrind/pub_core_options.h
@@ -222,14 +222,15 @@ typedef
       SimHint_fuse_compatible,
       SimHint_enable_outer,
       SimHint_no_inner_prefix,
-      SimHint_no_nptl_pthread_stackcache
+      SimHint_no_nptl_pthread_stackcache,
+      SimHint_fallback_llsc
    }
    SimHint;
 
 // Build mask to check or set SimHint a membership
 #define SimHint2S(a) (1 << (a))
 // SimHint h is member of the Set s ?
-#define SimHintiS(h,s) ((s) & SimHint2S(h))
+#define SimHintiS(h,s) (((s) & SimHint2S(h)) != 0)
 extern UInt VG_(clo_sim_hints);
 
 /* Show symbols in the form 'name+offset' ?  Default: NO */
diff --git a/memcheck/mc_machine.c b/memcheck/mc_machine.c
index f6acc0b..608a374 100644
--- a/memcheck/mc_machine.c
+++ b/memcheck/mc_machine.c
@@ -1040,6 +1040,10 @@ static Int get_otrack_shadow_offset_wrk ( Int offset, Int szB )
    if (o == GOF(CMSTART) && sz == 8) return -1; // untracked
    if (o == GOF(CMLEN)   && sz == 8) return -1; // untracked
 
+   if (o == GOF(LLSC_SIZE) && sz == 8) return -1; // untracked
+   if (o == GOF(LLSC_ADDR) && sz == 8) return o;
+   if (o == GOF(LLSC_DATA) && sz == 8) return o;
+
    VG_(printf)("MC_(get_otrack_shadow_offset)(arm64)(off=%d,sz=%d)\n",
                offset,szB);
    tl_assert(0);
diff --git a/none/tests/cmdline1.stdout.exp b/none/tests/cmdline1.stdout.exp
index 4e8bca4..a4d8175 100644
--- a/none/tests/cmdline1.stdout.exp
+++ b/none/tests/cmdline1.stdout.exp
@@ -101,7 +101,7 @@ usage: valgrind [options] prog-and-args
     --sim-hints=hint1,hint2,...  activate unusual sim behaviours [none] 
          where hint is one of:
            lax-ioctls lax-doors fuse-compatible enable-outer
-           no-inner-prefix no-nptl-pthread-stackcache none
+           no-inner-prefix no-nptl-pthread-stackcache fallback-llsc none
     --fair-sched=no|yes|try   schedule threads fairly on multicore systems [no]
     --kernel-variant=variant1,variant2,...
          handle non-standard kernel variants [none]
diff --git a/none/tests/cmdline2.stdout.exp b/none/tests/cmdline2.stdout.exp
index 644013c..461ad2d 100644
--- a/none/tests/cmdline2.stdout.exp
+++ b/none/tests/cmdline2.stdout.exp
@@ -101,7 +101,7 @@ usage: valgrind [options] prog-and-args
     --sim-hints=hint1,hint2,...  activate unusual sim behaviours [none] 
          where hint is one of:
            lax-ioctls lax-doors fuse-compatible enable-outer
-           no-inner-prefix no-nptl-pthread-stackcache none
+           no-inner-prefix no-nptl-pthread-stackcache fallback-llsc none
     --fair-sched=no|yes|try   schedule threads fairly on multicore systems [no]
     --kernel-variant=variant1,variant2,...
          handle non-standard kernel variants [none]