An HVX register operand was a bare offset from env.  That works only
while the register file was part of CPUHexagonState.  When it moves to an
HVX context shared between hardware threads, its address is not a
translation-time constant.

While here, fold the repeated helper-argument pointer setup in
hex_common.py into Hvx.decl_tcg_ptr().

Signed-off-by: Brian Cain <[email protected]>
---
 target/hexagon/gen_tcg_hvx.h  | 608 +++++++++++++++++++---------------
 target/hexagon/genptr.h       |   8 +
 target/hexagon/mmvec/macros.h |  14 +-
 target/hexagon/translate.h    |   5 +-
 target/hexagon/genptr.c       | 102 +++---
 target/hexagon/translate.c    |  58 ++--
 target/hexagon/hex_common.py  | 181 +++++-----
 7 files changed, 563 insertions(+), 413 deletions(-)

diff --git a/target/hexagon/gen_tcg_hvx.h b/target/hexagon/gen_tcg_hvx.h
index 2a342cdee69..f399291dc66 100644
--- a/target/hexagon/gen_tcg_hvx.h
+++ b/target/hexagon/gen_tcg_hvx.h
@@ -49,8 +49,8 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         if (ctx->pre_commit) { \
             intptr_t dstoff = offsetof(CPUHexagonState, qtmp); \
-            tcg_gen_gvec_mov(MO_64, dstoff, QvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, QvV_base, QvV_off, \
+                                 sizeof(MMVector), sizeof(MMVector)); \
         } else { \
             assert_vhist_tmp(ctx); \
             gen_helper_vhistq(tcg_env); \
@@ -65,8 +65,8 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         if (ctx->pre_commit) { \
             intptr_t dstoff = offsetof(CPUHexagonState, qtmp); \
-            tcg_gen_gvec_mov(MO_64, dstoff, QvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, QvV_base, QvV_off, \
+                                 sizeof(MMVector), sizeof(MMVector)); \
         } else { \
             assert_vhist_tmp(ctx); \
             gen_helper_vwhist256q(tcg_env); \
@@ -81,8 +81,8 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         if (ctx->pre_commit) { \
             intptr_t dstoff = offsetof(CPUHexagonState, qtmp); \
-            tcg_gen_gvec_mov(MO_64, dstoff, QvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, QvV_base, QvV_off, \
+                                 sizeof(MMVector), sizeof(MMVector)); \
         } else { \
             assert_vhist_tmp(ctx); \
             gen_helper_vwhist256q_sat(tcg_env); \
@@ -97,8 +97,8 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         if (ctx->pre_commit) { \
             intptr_t dstoff = offsetof(CPUHexagonState, qtmp); \
-            tcg_gen_gvec_mov(MO_64, dstoff, QvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, QvV_base, QvV_off, \
+                                 sizeof(MMVector), sizeof(MMVector)); \
         } else { \
             assert_vhist_tmp(ctx); \
             gen_helper_vwhist128q(tcg_env); \
@@ -114,8 +114,8 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         if (ctx->pre_commit) { \
             intptr_t dstoff = offsetof(CPUHexagonState, qtmp); \
-            tcg_gen_gvec_mov(MO_64, dstoff, QvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, QvV_base, QvV_off, \
+                                 sizeof(MMVector), sizeof(MMVector)); \
         } else { \
             TCGv tcgv_uiV = tcg_constant_tl(uiV); \
             assert_vhist_tmp(ctx); \
@@ -125,19 +125,20 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 
 
 #define fGEN_TCG_V6_vassign(SHORTCODE) \
-    tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_mov_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vassign_tmp(SHORTCODE) \
-    tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_mov_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vcombine_tmp(SHORTCODE) \
     do { \
-        tcg_gen_gvec_mov(MO_64, VddV_off, VvV_off, \
-                         sizeof(MMVector), sizeof(MMVector)); \
-        tcg_gen_gvec_mov(MO_64, VddV_off + sizeof(MMVector), VuV_off, \
-                         sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_mov_var(MO_64, VddV_base, VddV_off, VvV_base, VvV_off, \
+                             sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_mov_var(MO_64, VddV_base, VddV_off + sizeof(MMVector), \
+                             VuV_base, VuV_off, sizeof(MMVector), \
+                             sizeof(MMVector)); \
     } while (0)
 
 /*
@@ -148,18 +149,20 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_V6_vcombine(SHORTCODE) \
     do { \
         if (VddV_off != VuV_off) { \
-            tcg_gen_gvec_mov(MO_64, VddV_off, VvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
-            tcg_gen_gvec_mov(MO_64, VddV_off + sizeof(MMVector), VuV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, VddV_base, VddV_off, VvV_base, \
+                                 VvV_off, sizeof(MMVector), sizeof(MMVector)); 
\
+            tcg_gen_gvec_mov_var(MO_64, VddV_base, \
+                                 VddV_off + sizeof(MMVector), VuV_base, \
+                                 VuV_off, sizeof(MMVector), sizeof(MMVector)); 
\
         } else { \
             intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
-            tcg_gen_gvec_mov(MO_64, tmpoff, VuV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
-            tcg_gen_gvec_mov(MO_64, VddV_off, VvV_off, \
-                             sizeof(MMVector), sizeof(MMVector)); \
-            tcg_gen_gvec_mov(MO_64, VddV_off + sizeof(MMVector), tmpoff, \
-                             sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, tcg_env, tmpoff, VuV_base, VuV_off, \
+                                 sizeof(MMVector), sizeof(MMVector)); \
+            tcg_gen_gvec_mov_var(MO_64, VddV_base, VddV_off, VvV_base, \
+                                 VvV_off, sizeof(MMVector), sizeof(MMVector)); 
\
+            tcg_gen_gvec_mov_var(MO_64, VddV_base, \
+                                 VddV_off + sizeof(MMVector), tcg_env, tmpoff, 
\
+                                 sizeof(MMVector), sizeof(MMVector)); \
         } \
     } while (0)
 
@@ -170,8 +173,8 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
         TCGLabel *false_label = gen_new_label(); \
         tcg_gen_andi_tl(lsb, PsV, 1); \
         tcg_gen_brcondi_tl(TCG_COND_NE, lsb, PRED, false_label); \
-        tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
-                         sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_mov_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                             sizeof(MMVector), sizeof(MMVector)); \
         gen_set_label(false_label); \
     } while (0)
 
@@ -186,231 +189,276 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 
 /* Vector add - various forms */
 #define fGEN_TCG_V6_vaddb(SHORTCODE) \
-    tcg_gen_gvec_add(MO_8, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_add_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, VvV_base, 
\
+                         VvV_off, sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vaddh(SHORTCYDE) \
-    tcg_gen_gvec_add(MO_16, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_add_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         VvV_base, VvV_off, sizeof(MMVector), \
+                         sizeof(MMVector))
 
 #define fGEN_TCG_V6_vaddw(SHORTCODE) \
-    tcg_gen_gvec_add(MO_32, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_add_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         VvV_base, VvV_off, sizeof(MMVector), \
+                         sizeof(MMVector))
 
 #define fGEN_TCG_V6_vaddb_dv(SHORTCODE) \
-    tcg_gen_gvec_add(MO_8, VddV_off, VuuV_off, VvvV_off, \
-                     sizeof(MMVector) * 2, sizeof(MMVector) * 2)
+    tcg_gen_gvec_add_var(MO_8, VddV_base, VddV_off, VuuV_base, VuuV_off, \
+                         VvvV_base, VvvV_off, sizeof(MMVector) * 2, \
+                         sizeof(MMVector) * 2)
 
 #define fGEN_TCG_V6_vaddh_dv(SHORTCYDE) \
-    tcg_gen_gvec_add(MO_16, VddV_off, VuuV_off, VvvV_off, \
-                     sizeof(MMVector) * 2, sizeof(MMVector) * 2)
+    tcg_gen_gvec_add_var(MO_16, VddV_base, VddV_off, VuuV_base, VuuV_off, \
+                         VvvV_base, VvvV_off, sizeof(MMVector) * 2, \
+                         sizeof(MMVector) * 2)
 
 #define fGEN_TCG_V6_vaddw_dv(SHORTCODE) \
-    tcg_gen_gvec_add(MO_32, VddV_off, VuuV_off, VvvV_off, \
-                     sizeof(MMVector) * 2, sizeof(MMVector) * 2)
+    tcg_gen_gvec_add_var(MO_32, VddV_base, VddV_off, VuuV_base, VuuV_off, \
+                         VvvV_base, VvvV_off, sizeof(MMVector) * 2, \
+                         sizeof(MMVector) * 2)
 
 /* Vector sub - various forms */
 #define fGEN_TCG_V6_vsubb(SHORTCODE) \
-    tcg_gen_gvec_sub(MO_8, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_sub_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, VvV_base, 
\
+                         VvV_off, sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vsubh(SHORTCODE) \
-    tcg_gen_gvec_sub(MO_16, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_sub_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         VvV_base, VvV_off, sizeof(MMVector), \
+                         sizeof(MMVector))
 
 #define fGEN_TCG_V6_vsubw(SHORTCODE) \
-    tcg_gen_gvec_sub(MO_32, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_sub_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         VvV_base, VvV_off, sizeof(MMVector), \
+                         sizeof(MMVector))
 
 #define fGEN_TCG_V6_vsubb_dv(SHORTCODE) \
-    tcg_gen_gvec_sub(MO_8, VddV_off, VuuV_off, VvvV_off, \
-                     sizeof(MMVector) * 2, sizeof(MMVector) * 2)
+    tcg_gen_gvec_sub_var(MO_8, VddV_base, VddV_off, VuuV_base, VuuV_off, \
+                         VvvV_base, VvvV_off, sizeof(MMVector) * 2, \
+                         sizeof(MMVector) * 2)
 
 #define fGEN_TCG_V6_vsubh_dv(SHORTCODE) \
-    tcg_gen_gvec_sub(MO_16, VddV_off, VuuV_off, VvvV_off, \
-                     sizeof(MMVector) * 2, sizeof(MMVector) * 2)
+    tcg_gen_gvec_sub_var(MO_16, VddV_base, VddV_off, VuuV_base, VuuV_off, \
+                         VvvV_base, VvvV_off, sizeof(MMVector) * 2, \
+                         sizeof(MMVector) * 2)
 
 #define fGEN_TCG_V6_vsubw_dv(SHORTCODE) \
-    tcg_gen_gvec_sub(MO_32, VddV_off, VuuV_off, VvvV_off, \
-                     sizeof(MMVector) * 2, sizeof(MMVector) * 2)
+    tcg_gen_gvec_sub_var(MO_32, VddV_base, VddV_off, VuuV_base, VuuV_off, \
+                         VvvV_base, VvvV_off, sizeof(MMVector) * 2, \
+                         sizeof(MMVector) * 2)
 
 #define fGEN_TCG_V6_vaddbsat(SHORTCODE) \
-    tcg_gen_gvec_ssadd(MO_8, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_ssadd_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vaddhsat(SHORTCODE) \
-    tcg_gen_gvec_ssadd(MO_16, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_ssadd_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vaddwsat(SHORTCODE) \
-    tcg_gen_gvec_ssadd(MO_32, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_ssadd_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vaddubsat(SHORTCODE) \
-    tcg_gen_gvec_usadd(MO_8, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_usadd_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vadduhsat(SHORTCODE) \
-    tcg_gen_gvec_usadd(MO_16, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_usadd_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vadduwsat(SHORTCODE) \
-    tcg_gen_gvec_usadd(MO_32, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_usadd_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
-#define fGEN_TCG_PAIR_ADDSUB(OP, VECE, DST, SRC_A, SRC_B) \
-    tcg_gen_gvec_##OP(VECE, DST, SRC_A, SRC_B, \
-                     2 * VECTOR_SIZE_BYTE, 2 * VECTOR_SIZE_BYTE)
+#define fGEN_TCG_PAIR_ADDSUB(OP, VECE, DBASE, DST, ABASE, SRC_A, BBASE, SRC_B) 
\
+    tcg_gen_gvec_##OP##_var(VECE, DBASE, DST, ABASE, SRC_A, BBASE, SRC_B, \
+                           2 * VECTOR_SIZE_BYTE, 2 * VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vaddbsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(ssadd, MO_8, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(ssadd, MO_8, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vaddhsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(ssadd, MO_16, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(ssadd, MO_16, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vaddwsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(ssadd, MO_32, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(ssadd, MO_32, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vaddubsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(usadd, MO_8, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(usadd, MO_8, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vadduhsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(usadd, MO_16, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(usadd, MO_16, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vadduwsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(usadd, MO_32, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(usadd, MO_32, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vsubbsat(SHORTCODE) \
-    tcg_gen_gvec_sssub(MO_8, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_sssub_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vsubhsat(SHORTCODE) \
-    tcg_gen_gvec_sssub(MO_16, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_sssub_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vsubwsat(SHORTCODE) \
-    tcg_gen_gvec_sssub(MO_32, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_sssub_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vsububsat(SHORTCODE) \
-    tcg_gen_gvec_ussub(MO_8, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_ussub_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vsubuhsat(SHORTCODE) \
-    tcg_gen_gvec_ussub(MO_16, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_ussub_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vsubuwsat(SHORTCODE) \
-    tcg_gen_gvec_ussub(MO_32, VdV_off, VuV_off, VvV_off, \
-                       VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_ussub_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, \
+                          VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vsubbsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(sssub, MO_8, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(sssub, MO_8, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vsubhsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(sssub, MO_16, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(sssub, MO_16, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vsubwsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(sssub, MO_32, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(sssub, MO_32, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vsububsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(ussub, MO_8, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(ussub, MO_8, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vsubuhsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(ussub, MO_16, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(ussub, MO_16, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vsubuwsat_dv(SHORTCODE) \
-    fGEN_TCG_PAIR_ADDSUB(ussub, MO_32, VddV_off, VuuV_off, VvvV_off)
+    fGEN_TCG_PAIR_ADDSUB(ussub, MO_32, VddV_base, VddV_off, \
+                         VuuV_base, VuuV_off, VvvV_base, VvvV_off)
 
 #define fGEN_TCG_V6_vmpyih(SHORTCODE) \
-    tcg_gen_gvec_mul(MO_16, VdV_off, VuV_off, VvV_off, \
-                     VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    tcg_gen_gvec_mul_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                        VvV_base, VvV_off, \
+                        VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vabsdiffub(SHORTCODE) \
-    gen_gvec_uabsdiff(MO_8, VdV_off, VuV_off, VvV_off, \
-                     VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    gen_gvec_uabsdiff_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                        VvV_base, VvV_off, \
+                        VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vabsdiffuh(SHORTCODE) \
-    gen_gvec_uabsdiff(MO_16, VdV_off, VuV_off, VvV_off, \
-                     VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    gen_gvec_uabsdiff_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                        VvV_base, VvV_off, \
+                        VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vabsdiffh(SHORTCODE) \
-    gen_gvec_sabsdiff(MO_16, VdV_off, VuV_off, VvV_off, \
-                     VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    gen_gvec_sabsdiff_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                        VvV_base, VvV_off, \
+                        VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_V6_vabsdiffw(SHORTCODE) \
-    gen_gvec_sabsdiff(MO_32, VdV_off, VuV_off, VvV_off, \
-                     VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
+    gen_gvec_sabsdiff_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                        VvV_base, VvV_off, \
+                        VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE)
 
 #define fGEN_TCG_VEC_AVG(VECE, SHIFT_FN) \
     do { \
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
-        tcg_gen_gvec_and(MO_64, tmpoff, VuV_off, VvV_off, \
-                         VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
-        tcg_gen_gvec_xor(MO_64, VdV_off, VuV_off, VvV_off, \
-                         VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
-        SHIFT_FN(VECE, VdV_off, VdV_off, 1, \
+        tcg_gen_gvec_and_var(MO_64, tcg_env, tmpoff, VuV_base, VuV_off, \
+                            VvV_base, VvV_off, \
+                            VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
+        tcg_gen_gvec_xor_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                             VvV_base, VvV_off, \
+                             VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
+        SHIFT_FN(VECE, VdV_base, VdV_off, VdV_base, VdV_off, 1, \
                  VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
-        tcg_gen_gvec_add(VECE, VdV_off, tmpoff, VdV_off, \
-                         VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
+        tcg_gen_gvec_add_var(VECE, VdV_base, VdV_off, tcg_env, tmpoff, \
+                             VdV_base, VdV_off, \
+                             VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
     } while (0)
 
 #define fGEN_TCG_V6_vavgub(SHORTCODE) \
-    fGEN_TCG_VEC_AVG(MO_8, tcg_gen_gvec_shri)
+    fGEN_TCG_VEC_AVG(MO_8, tcg_gen_gvec_shri_var)
 
 #define fGEN_TCG_V6_vavguh(SHORTCODE) \
-    fGEN_TCG_VEC_AVG(MO_16, tcg_gen_gvec_shri)
+    fGEN_TCG_VEC_AVG(MO_16, tcg_gen_gvec_shri_var)
 
 #define fGEN_TCG_V6_vavguw(SHORTCODE) \
-    fGEN_TCG_VEC_AVG(MO_32, tcg_gen_gvec_shri)
+    fGEN_TCG_VEC_AVG(MO_32, tcg_gen_gvec_shri_var)
 
 #define fGEN_TCG_V6_vavgb(SHORTCODE) \
-    fGEN_TCG_VEC_AVG(MO_8, tcg_gen_gvec_sari)
+    fGEN_TCG_VEC_AVG(MO_8, tcg_gen_gvec_sari_var)
 
 #define fGEN_TCG_V6_vavgh(SHORTCODE) \
-    fGEN_TCG_VEC_AVG(MO_16, tcg_gen_gvec_sari)
+    fGEN_TCG_VEC_AVG(MO_16, tcg_gen_gvec_sari_var)
 
 #define fGEN_TCG_V6_vavgw(SHORTCODE) \
-    fGEN_TCG_VEC_AVG(MO_32, tcg_gen_gvec_sari)
+    fGEN_TCG_VEC_AVG(MO_32, tcg_gen_gvec_sari_var)
 
 #define fGEN_TCG_VEC_AVGRND(VECE, SHIFT_FN) \
     do { \
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
-        tcg_gen_gvec_or(MO_64, tmpoff, VuV_off, VvV_off, \
-                        VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
-        tcg_gen_gvec_xor(MO_64, VdV_off, VuV_off, VvV_off, \
-                         VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
-        SHIFT_FN(VECE, VdV_off, VdV_off, 1, \
+        tcg_gen_gvec_or_var(MO_64, tcg_env, tmpoff, VuV_base, VuV_off, \
+                           VvV_base, VvV_off, \
+                           VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
+        tcg_gen_gvec_xor_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                             VvV_base, VvV_off, \
+                             VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
+        SHIFT_FN(VECE, VdV_base, VdV_off, VdV_base, VdV_off, 1, \
                  VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
-        tcg_gen_gvec_sub(VECE, VdV_off, tmpoff, VdV_off, \
-                         VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
+        tcg_gen_gvec_sub_var(VECE, VdV_base, VdV_off, tcg_env, tmpoff, \
+                             VdV_base, VdV_off, \
+                             VECTOR_SIZE_BYTE, VECTOR_SIZE_BYTE); \
     } while (0)
 
 #define fGEN_TCG_V6_vavgubrnd(SHORTCODE) \
-    fGEN_TCG_VEC_AVGRND(MO_8, tcg_gen_gvec_shri)
+    fGEN_TCG_VEC_AVGRND(MO_8, tcg_gen_gvec_shri_var)
 
 #define fGEN_TCG_V6_vavguhrnd(SHORTCODE) \
-    fGEN_TCG_VEC_AVGRND(MO_16, tcg_gen_gvec_shri)
+    fGEN_TCG_VEC_AVGRND(MO_16, tcg_gen_gvec_shri_var)
 
 #define fGEN_TCG_V6_vavguwrnd(SHORTCODE) \
-    fGEN_TCG_VEC_AVGRND(MO_32, tcg_gen_gvec_shri)
+    fGEN_TCG_VEC_AVGRND(MO_32, tcg_gen_gvec_shri_var)
 
 #define fGEN_TCG_V6_vavgbrnd(SHORTCODE) \
-    fGEN_TCG_VEC_AVGRND(MO_8, tcg_gen_gvec_sari)
+    fGEN_TCG_VEC_AVGRND(MO_8, tcg_gen_gvec_sari_var)
 
 #define fGEN_TCG_V6_vavghrnd(SHORTCODE) \
-    fGEN_TCG_VEC_AVGRND(MO_16, tcg_gen_gvec_sari)
+    fGEN_TCG_VEC_AVGRND(MO_16, tcg_gen_gvec_sari_var)
 
 #define fGEN_TCG_V6_vavgwrnd(SHORTCODE) \
-    fGEN_TCG_VEC_AVGRND(MO_32, tcg_gen_gvec_sari)
+    fGEN_TCG_VEC_AVGRND(MO_32, tcg_gen_gvec_sari_var)
 
 /* Vector shift right - various forms */
 #define fGEN_TCG_V6_vasrh(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 15); \
-        tcg_gen_gvec_sars(MO_16, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_sars_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vasrh_acc(SHORTCODE) \
@@ -418,18 +466,19 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 15); \
-        tcg_gen_gvec_sars(MO_16, tmpoff, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
-        tcg_gen_gvec_add(MO_16, VxV_off, VxV_off, tmpoff, \
-                         sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_sars_var(MO_16, tcg_env, tmpoff, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_add_var(MO_16, VxV_base, VxV_off, VxV_base, VxV_off, \
+                             tcg_env, tmpoff, sizeof(MMVector), \
+                             sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vasrw(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 31); \
-        tcg_gen_gvec_sars(MO_32, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_sars_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vasrw_acc(SHORTCODE) \
@@ -437,34 +486,35 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 31); \
-        tcg_gen_gvec_sars(MO_32, tmpoff, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
-        tcg_gen_gvec_add(MO_32, VxV_off, VxV_off, tmpoff, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_sars_var(MO_32, tcg_env, tmpoff, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_add_var(MO_32, VxV_base, VxV_off, VxV_base, VxV_off, \
+                             tcg_env, tmpoff, sizeof(MMVector), \
+                             sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vlsrb(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 7); \
-        tcg_gen_gvec_shrs(MO_8, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shrs_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vlsrh(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 15); \
-        tcg_gen_gvec_shrs(MO_16, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shrs_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vlsrw(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 31); \
-        tcg_gen_gvec_shrs(MO_32, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shrs_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 /* Vector shift left - various forms */
@@ -472,16 +522,16 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 7); \
-        tcg_gen_gvec_shls(MO_8, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shls_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vaslh(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 15); \
-        tcg_gen_gvec_shls(MO_16, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shls_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vaslh_acc(SHORTCODE) \
@@ -489,18 +539,19 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 15); \
-        tcg_gen_gvec_shls(MO_16, tmpoff, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
-        tcg_gen_gvec_add(MO_16, VxV_off, VxV_off, tmpoff, \
-                         sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shls_var(MO_16, tcg_env, tmpoff, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_add_var(MO_16, VxV_base, VxV_off, VxV_base, VxV_off, \
+                             tcg_env, tmpoff, sizeof(MMVector), \
+                             sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vaslw(SHORTCODE) \
     do { \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 31); \
-        tcg_gen_gvec_shls(MO_32, VdV_off, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shls_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
     } while (0)
 
 #define fGEN_TCG_V6_vaslw_acc(SHORTCODE) \
@@ -508,95 +559,109 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
         TCGv shift = tcg_temp_new(); \
         tcg_gen_andi_tl(shift, RtV, 31); \
-        tcg_gen_gvec_shls(MO_32, tmpoff, VuV_off, shift, \
-                          sizeof(MMVector), sizeof(MMVector)); \
-        tcg_gen_gvec_add(MO_32, VxV_off, VxV_off, tmpoff, \
-                         sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_shls_var(MO_32, tcg_env, tmpoff, VuV_base, VuV_off, \
+                              shift, sizeof(MMVector), sizeof(MMVector)); \
+        tcg_gen_gvec_add_var(MO_32, VxV_base, VxV_off, VxV_base, VxV_off, \
+                             tcg_env, tmpoff, sizeof(MMVector), \
+                             sizeof(MMVector)); \
     } while (0)
 
 /* Vector max - various forms */
 #define fGEN_TCG_V6_vmaxw(SHORTCODE) \
-    tcg_gen_gvec_smax(MO_32, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_smax_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vmaxh(SHORTCODE) \
-    tcg_gen_gvec_smax(MO_16, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_smax_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vmaxuh(SHORTCODE) \
-    tcg_gen_gvec_umax(MO_16, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_umax_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vmaxb(SHORTCODE) \
-    tcg_gen_gvec_smax(MO_8, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_smax_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vmaxub(SHORTCODE) \
-    tcg_gen_gvec_umax(MO_8, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_umax_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 
 /* Vector min - various forms */
 #define fGEN_TCG_V6_vminw(SHORTCODE) \
-    tcg_gen_gvec_smin(MO_32, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_smin_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vminh(SHORTCODE) \
-    tcg_gen_gvec_smin(MO_16, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_smin_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vminuh(SHORTCODE) \
-    tcg_gen_gvec_umin(MO_16, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_umin_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vminb(SHORTCODE) \
-    tcg_gen_gvec_smin(MO_8, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_smin_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 #define fGEN_TCG_V6_vminub(SHORTCODE) \
-    tcg_gen_gvec_umin(MO_8, VdV_off, VuV_off, VvV_off, \
-                      sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_umin_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                          VvV_base, VvV_off, sizeof(MMVector), \
+                          sizeof(MMVector))
 
 /* Vector logical ops */
 #define fGEN_TCG_V6_vxor(SHORTCODE) \
-    tcg_gen_gvec_xor(MO_64, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_xor_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         VvV_base, VvV_off, sizeof(MMVector), \
+                         sizeof(MMVector))
 
 #define fGEN_TCG_V6_vand(SHORTCODE) \
-    tcg_gen_gvec_and(MO_64, VdV_off, VuV_off, VvV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_and_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         VvV_base, VvV_off, sizeof(MMVector), \
+                         sizeof(MMVector))
 
 #define fGEN_TCG_V6_vor(SHORTCODE) \
-    tcg_gen_gvec_or(MO_64, VdV_off, VuV_off, VvV_off, \
-                    sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_or_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, VvV_base, 
\
+                        VvV_off, sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vnot(SHORTCODE) \
-    tcg_gen_gvec_not(MO_64, VdV_off, VuV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_not_var(MO_64, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         sizeof(MMVector), sizeof(MMVector))
 
 /* Q register logical ops */
 #define fGEN_TCG_V6_pred_or(SHORTCODE) \
-    tcg_gen_gvec_or(MO_64, QdV_off, QsV_off, QtV_off, \
-                    sizeof(MMQReg), sizeof(MMQReg))
+    tcg_gen_gvec_or_var(MO_64, QdV_base, QdV_off, QsV_base, QsV_off, QtV_base, 
\
+                        QtV_off, sizeof(MMQReg), sizeof(MMQReg))
 
 #define fGEN_TCG_V6_pred_and(SHORTCODE) \
-    tcg_gen_gvec_and(MO_64, QdV_off, QsV_off, QtV_off, \
-                     sizeof(MMQReg), sizeof(MMQReg))
+    tcg_gen_gvec_and_var(MO_64, QdV_base, QdV_off, QsV_base, QsV_off, \
+                         QtV_base, QtV_off, sizeof(MMQReg), sizeof(MMQReg))
 
 #define fGEN_TCG_V6_pred_xor(SHORTCODE) \
-    tcg_gen_gvec_xor(MO_64, QdV_off, QsV_off, QtV_off, \
-                     sizeof(MMQReg), sizeof(MMQReg))
+    tcg_gen_gvec_xor_var(MO_64, QdV_base, QdV_off, QsV_base, QsV_off, \
+                         QtV_base, QtV_off, sizeof(MMQReg), sizeof(MMQReg))
 
 #define fGEN_TCG_V6_pred_or_n(SHORTCODE) \
-    tcg_gen_gvec_orc(MO_64, QdV_off, QsV_off, QtV_off, \
-                     sizeof(MMQReg), sizeof(MMQReg))
+    tcg_gen_gvec_orc_var(MO_64, QdV_base, QdV_off, QsV_base, QsV_off, \
+                         QtV_base, QtV_off, sizeof(MMQReg), sizeof(MMQReg))
 
 #define fGEN_TCG_V6_pred_and_n(SHORTCODE) \
-    tcg_gen_gvec_andc(MO_64, QdV_off, QsV_off, QtV_off, \
-                      sizeof(MMQReg), sizeof(MMQReg))
+    tcg_gen_gvec_andc_var(MO_64, QdV_base, QdV_off, QsV_base, QsV_off, \
+                          QtV_base, QtV_off, sizeof(MMQReg), sizeof(MMQReg))
 
 #define fGEN_TCG_V6_pred_not(SHORTCODE) \
-    tcg_gen_gvec_not(MO_64, QdV_off, QsV_off, \
-                     sizeof(MMQReg), sizeof(MMQReg))
+    tcg_gen_gvec_not_var(MO_64, QdV_base, QdV_off, QsV_base, QsV_off, \
+                         sizeof(MMQReg), sizeof(MMQReg))
 
 /* Vector compares */
 #define fGEN_TCG_VEC_CMP(COND, TYPE, SIZE) \
     do { \
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
-        tcg_gen_gvec_cmp(COND, TYPE, tmpoff, VuV_off, VvV_off, \
-                         sizeof(MMVector), sizeof(MMVector)); \
-        vec_to_qvec(SIZE, QdV_off, tmpoff); \
+        tcg_gen_gvec_cmp_var(COND, TYPE, tcg_env, tmpoff, VuV_base, VuV_off, \
+                             VvV_base, VvV_off, sizeof(MMVector), \
+                             sizeof(MMVector)); \
+        vec_to_qvec(SIZE, QdV_base, QdV_off, tcg_env, tmpoff); \
     } while (0)
 
 #define fGEN_TCG_V6_vgtw(SHORTCODE) \
@@ -624,100 +689,102 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     do { \
         intptr_t tmpoff = offsetof(CPUHexagonState, vtmp); \
         intptr_t qoff = offsetof(CPUHexagonState, qtmp); \
-        tcg_gen_gvec_cmp(COND, TYPE, tmpoff, VuV_off, VvV_off, \
-                         sizeof(MMVector), sizeof(MMVector)); \
-        vec_to_qvec(SIZE, qoff, tmpoff); \
-        OP(MO_64, QxV_off, QxV_off, qoff, sizeof(MMQReg), sizeof(MMQReg)); \
+        tcg_gen_gvec_cmp_var(COND, TYPE, tcg_env, tmpoff, VuV_base, VuV_off, \
+                             VvV_base, VvV_off, sizeof(MMVector), \
+                             sizeof(MMVector)); \
+        vec_to_qvec(SIZE, tcg_env, qoff, tcg_env, tmpoff); \
+        OP(MO_64, QxV_base, QxV_off, QxV_base, QxV_off, tcg_env, qoff, \
+           sizeof(MMQReg), sizeof(MMQReg)); \
     } while (0)
 
 #define fGEN_TCG_V6_vgtw_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_32, 4, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_32, 4, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_vgtw_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_32, 4, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_32, 4, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_vgtw_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_32, 4, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_32, 4, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_vgtuw_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_32, 4, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_32, 4, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_vgtuw_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_32, 4, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_32, 4, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_vgtuw_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_32, 4, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_32, 4, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_vgth_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_16, 2, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_16, 2, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_vgth_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_16, 2, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_16, 2, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_vgth_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_16, 2, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_16, 2, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_vgtuh_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_16, 2, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_16, 2, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_vgtuh_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_16, 2, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_16, 2, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_vgtuh_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_16, 2, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_16, 2, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_vgtb_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_8, 1, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_8, 1, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_vgtb_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_8, 1, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_8, 1, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_vgtb_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_8, 1, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GT, MO_8, 1, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_vgtub_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_8, 1, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_8, 1, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_vgtub_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_8, 1, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_8, 1, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_vgtub_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_8, 1, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_GTU, MO_8, 1, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_veqw_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_32, 4, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_32, 4, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_veqw_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_32, 4, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_32, 4, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_veqw_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_32, 4, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_32, 4, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_veqh_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_16, 2, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_16, 2, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_veqh_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_16, 2, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_16, 2, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_veqh_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_16, 2, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_16, 2, tcg_gen_gvec_xor_var)
 
 #define fGEN_TCG_V6_veqb_and(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_8, 1, tcg_gen_gvec_and)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_8, 1, tcg_gen_gvec_and_var)
 #define fGEN_TCG_V6_veqb_or(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_8, 1, tcg_gen_gvec_or)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_8, 1, tcg_gen_gvec_or_var)
 #define fGEN_TCG_V6_veqb_xor(SHORTCODE) \
-    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_8, 1, tcg_gen_gvec_xor)
+    fGEN_TCG_VEC_CMP_OP(TCG_COND_EQ, MO_8, 1, tcg_gen_gvec_xor_var)
 
 /* Vector splat - various forms */
 #define fGEN_TCG_V6_lvsplatw(SHORTCODE) \
-    tcg_gen_gvec_dup_i32(MO_32, VdV_off, \
-                         sizeof(MMVector), sizeof(MMVector), RtV)
+    tcg_gen_gvec_dup_i32_var(MO_32, VdV_base, VdV_off, sizeof(MMVector), \
+                             sizeof(MMVector), RtV)
 
 #define fGEN_TCG_V6_lvsplath(SHORTCODE) \
-    tcg_gen_gvec_dup_i32(MO_16, VdV_off, \
-                         sizeof(MMVector), sizeof(MMVector), RtV)
+    tcg_gen_gvec_dup_i32_var(MO_16, VdV_base, VdV_off, sizeof(MMVector), \
+                             sizeof(MMVector), RtV)
 
 #define fGEN_TCG_V6_lvsplatb(SHORTCODE) \
-    tcg_gen_gvec_dup_i32(MO_8, VdV_off, \
-                         sizeof(MMVector), sizeof(MMVector), RtV)
+    tcg_gen_gvec_dup_i32_var(MO_8, VdV_base, VdV_off, sizeof(MMVector), \
+                             sizeof(MMVector), RtV)
 
 /* Vector absolute value - various forms */
 #define fGEN_TCG_V6_vabsb(SHORTCODE) \
-    tcg_gen_gvec_abs(MO_8, VdV_off, VuV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_abs_var(MO_8, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vabsh(SHORTCODE) \
-    tcg_gen_gvec_abs(MO_16, VdV_off, VuV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_abs_var(MO_16, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         sizeof(MMVector), sizeof(MMVector))
 
 #define fGEN_TCG_V6_vabsw(SHORTCODE) \
-    tcg_gen_gvec_abs(MO_32, VdV_off, VuV_off, \
-                     sizeof(MMVector), sizeof(MMVector))
+    tcg_gen_gvec_abs_var(MO_32, VdV_base, VdV_off, VuV_base, VuV_off, \
+                         sizeof(MMVector), sizeof(MMVector))
 
 /* Vector loads */
 #define fGEN_TCG_V6_vL32b_pi(SHORTCODE)                    SHORTCODE
@@ -743,14 +810,14 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_V6_vL32b_nt_tmp_ppu(SHORTCODE)            SHORTCODE
 
 /* Predicated vector loads */
-#define fGEN_TCG_PRED_VEC_LOAD(GET_EA, PRED, DSTOFF, INC) \
+#define fGEN_TCG_PRED_VEC_LOAD(GET_EA, PRED, DST, INC) \
     do { \
         TCGv LSB = tcg_temp_new(); \
         TCGLabel *false_label = gen_new_label(); \
         GET_EA; \
         PRED; \
         tcg_gen_brcondi_tl(TCG_COND_EQ, LSB, 0, false_label); \
-        gen_vreg_load(ctx, DSTOFF, EA, true); \
+        gen_vreg_load(ctx, DST##_base, DST##_off, EA, true); \
         INC; \
         gen_set_label(false_label); \
     } while (0)
@@ -758,12 +825,12 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_PRED_VEC_LOAD_pred_pi \
     fGEN_TCG_PRED_VEC_LOAD(fLSBOLD(PvV), \
                            fEA_REG(RxV), \
-                           VdV_off, \
+                           VdV, \
                            fPM_I(RxV, siV * sizeof(MMVector)))
 #define fGEN_TCG_PRED_VEC_LOAD_npred_pi \
     fGEN_TCG_PRED_VEC_LOAD(fLSBOLDNOT(PvV), \
                            fEA_REG(RxV), \
-                           VdV_off, \
+                           VdV, \
                            fPM_I(RxV, siV * sizeof(MMVector)))
 
 #define fGEN_TCG_V6_vL32b_pred_pi(SHORTCODE) \
@@ -794,12 +861,12 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_PRED_VEC_LOAD_pred_ai \
     fGEN_TCG_PRED_VEC_LOAD(fLSBOLD(PvV), \
                            fEA_RI(RtV, siV * sizeof(MMVector)), \
-                           VdV_off, \
+                           VdV, \
                            do {} while (0))
 #define fGEN_TCG_PRED_VEC_LOAD_npred_ai \
     fGEN_TCG_PRED_VEC_LOAD(fLSBOLDNOT(PvV), \
                            fEA_RI(RtV, siV * sizeof(MMVector)), \
-                           VdV_off, \
+                           VdV, \
                            do {} while (0))
 
 #define fGEN_TCG_V6_vL32b_pred_ai(SHORTCODE) \
@@ -830,12 +897,12 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_PRED_VEC_LOAD_pred_ppu \
     fGEN_TCG_PRED_VEC_LOAD(fLSBOLD(PvV), \
                            fEA_REG(RxV), \
-                           VdV_off, \
+                           VdV, \
                            fPM_M(RxV, MuV))
 #define fGEN_TCG_PRED_VEC_LOAD_npred_ppu \
     fGEN_TCG_PRED_VEC_LOAD(fLSBOLDNOT(PvV), \
                            fEA_REG(RxV), \
-                           VdV_off, \
+                           VdV, \
                            fPM_M(RxV, MuV))
 
 #define fGEN_TCG_V6_vL32b_pred_ppu(SHORTCODE) \
@@ -878,7 +945,7 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_NEWVAL_VEC_STORE(GET_EA, INC) \
     do { \
         GET_EA; \
-        gen_vreg_store(ctx, EA, OsN_off, insn->slot, true); \
+        gen_vreg_store(ctx, EA, OsN_base, OsN_off, insn->slot, true); \
         INC; \
     } while (0)
 
@@ -908,14 +975,15 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
     fGEN_TCG_NEWVAL_VEC_STORE_ppu
 
 /* Predicated vector stores */
-#define fGEN_TCG_PRED_VEC_STORE(GET_EA, PRED, SRCOFF, ALIGN, INC) \
+#define fGEN_TCG_PRED_VEC_STORE(GET_EA, PRED, SRC, ALIGN, INC) \
     do { \
         TCGv LSB = tcg_temp_new(); \
         TCGLabel *false_label = gen_new_label(); \
         GET_EA; \
         PRED; \
         tcg_gen_brcondi_tl(TCG_COND_EQ, LSB, 0, false_label); \
-        gen_vreg_store(ctx, EA, SRCOFF, insn->slot, ALIGN); \
+        gen_vreg_store(ctx, EA, SRC##_base, SRC##_off, insn->slot, \
+                       ALIGN); \
         INC; \
         gen_set_label(false_label); \
     } while (0)
@@ -923,22 +991,22 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_PRED_VEC_STORE_pred_pi(ALIGN) \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLD(PvV), \
                             fEA_REG(RxV), \
-                            VsV_off, ALIGN, \
+                            VsV, ALIGN, \
                             fPM_I(RxV, siV * sizeof(MMVector)))
 #define fGEN_TCG_PRED_VEC_STORE_npred_pi(ALIGN) \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLDNOT(PvV), \
                             fEA_REG(RxV), \
-                            VsV_off, ALIGN, \
+                            VsV, ALIGN, \
                             fPM_I(RxV, siV * sizeof(MMVector)))
 #define fGEN_TCG_PRED_VEC_STORE_new_pred_pi \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLD(PvV), \
                             fEA_REG(RxV), \
-                            OsN_off, true, \
+                            OsN, true, \
                             fPM_I(RxV, siV * sizeof(MMVector)))
 #define fGEN_TCG_PRED_VEC_STORE_new_npred_pi \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLDNOT(PvV), \
                             fEA_REG(RxV), \
-                            OsN_off, true, \
+                            OsN, true, \
                             fPM_I(RxV, siV * sizeof(MMVector)))
 
 #define fGEN_TCG_V6_vS32b_pred_pi(SHORTCODE) \
@@ -965,22 +1033,22 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_PRED_VEC_STORE_pred_ai(ALIGN) \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLD(PvV), \
                             fEA_RI(RtV, siV * sizeof(MMVector)), \
-                            VsV_off, ALIGN, \
+                            VsV, ALIGN, \
                             do { } while (0))
 #define fGEN_TCG_PRED_VEC_STORE_npred_ai(ALIGN) \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLDNOT(PvV), \
                             fEA_RI(RtV, siV * sizeof(MMVector)), \
-                            VsV_off, ALIGN, \
+                            VsV, ALIGN, \
                             do { } while (0))
 #define fGEN_TCG_PRED_VEC_STORE_new_pred_ai \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLD(PvV), \
                             fEA_RI(RtV, siV * sizeof(MMVector)), \
-                            OsN_off, true, \
+                            OsN, true, \
                             do { } while (0))
 #define fGEN_TCG_PRED_VEC_STORE_new_npred_ai \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLDNOT(PvV), \
                             fEA_RI(RtV, siV * sizeof(MMVector)), \
-                            OsN_off, true, \
+                            OsN, true, \
                             do { } while (0))
 
 #define fGEN_TCG_V6_vS32b_pred_ai(SHORTCODE) \
@@ -1007,22 +1075,22 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 #define fGEN_TCG_PRED_VEC_STORE_pred_ppu(ALIGN) \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLD(PvV), \
                             fEA_REG(RxV), \
-                            VsV_off, ALIGN, \
+                            VsV, ALIGN, \
                             fPM_M(RxV, MuV))
 #define fGEN_TCG_PRED_VEC_STORE_npred_ppu(ALIGN) \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLDNOT(PvV), \
                             fEA_REG(RxV), \
-                            VsV_off, ALIGN, \
+                            VsV, ALIGN, \
                             fPM_M(RxV, MuV))
 #define fGEN_TCG_PRED_VEC_STORE_new_pred_ppu \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLD(PvV), \
                             fEA_REG(RxV), \
-                            OsN_off, true, \
+                            OsN, true, \
                             fPM_M(RxV, MuV))
 #define fGEN_TCG_PRED_VEC_STORE_new_npred_ppu \
     fGEN_TCG_PRED_VEC_STORE(fLSBOLDNOT(PvV), \
                             fEA_REG(RxV), \
-                            OsN_off, true, \
+                            OsN, true, \
                             fPM_M(RxV, MuV))
 
 #define fGEN_TCG_V6_vS32b_pred_ppu(SHORTCODE) \
diff --git a/target/hexagon/genptr.h b/target/hexagon/genptr.h
index f498398367c..238ee089cba 100644
--- a/target/hexagon/genptr.h
+++ b/target/hexagon/genptr.h
@@ -59,6 +59,14 @@ TCGv gen_get_half(TCGv result, int N, TCGv src, bool sign);
 void gen_set_half(int N, TCGv result, TCGv src);
 void gen_set_half_i64(int N, TCGv_i64 result, TCGv src);
 void probe_noshuf_load(TCGv va, int s, int mi);
+void gen_gvec_sabsdiff_var(unsigned vece, TCGv_ptr dbase, uint32_t dofs,
+                           TCGv_ptr abase, uint32_t aofs,
+                           TCGv_ptr bbase, uint32_t bofs,
+                           uint32_t oprsz, uint32_t maxsz);
+void gen_gvec_uabsdiff_var(unsigned vece, TCGv_ptr dbase, uint32_t dofs,
+                           TCGv_ptr abase, uint32_t aofs,
+                           TCGv_ptr bbase, uint32_t bofs,
+                           uint32_t oprsz, uint32_t maxsz);
 void gen_gvec_sabsdiff(unsigned vece, uint32_t dofs, uint32_t aofs,
                        uint32_t bofs, uint32_t oprsz, uint32_t maxsz);
 void gen_gvec_uabsdiff(unsigned vece, uint32_t dofs, uint32_t aofs,
diff --git a/target/hexagon/mmvec/macros.h b/target/hexagon/mmvec/macros.h
index b36f833b1de..df695d0731c 100644
--- a/target/hexagon/mmvec/macros.h
+++ b/target/hexagon/mmvec/macros.h
@@ -286,26 +286,28 @@
         fV_AL_CHECK(EA, fVECSIZE() - 1); \
     } while (0)
 #ifdef QEMU_GENERATE
-#define fLOADMMV(EA, DST) gen_vreg_load(ctx, DST##_off, EA, true)
+#define fLOADMMV(EA, DST) gen_vreg_load(ctx, DST##_base, DST##_off, EA, true)
 #endif
 #ifdef QEMU_GENERATE
-#define fLOADMMVU(EA, DST) gen_vreg_load(ctx, DST##_off, EA, false)
+#define fLOADMMVU(EA, DST) gen_vreg_load(ctx, DST##_base, DST##_off, EA, false)
 #endif
 #ifdef QEMU_GENERATE
 #define fSTOREMMV(EA, SRC) \
-    gen_vreg_store(ctx, EA, SRC##_off, insn->slot, true)
+    gen_vreg_store(ctx, EA, SRC##_base, SRC##_off, insn->slot, true)
 #endif
 #ifdef QEMU_GENERATE
 #define fSTOREMMVQ(EA, SRC, MASK) \
-    gen_vreg_masked_store(ctx, EA, SRC##_off, MASK##_off, insn->slot, false)
+    gen_vreg_masked_store(ctx, EA, SRC##_base, SRC##_off, \
+                          MASK##_base, MASK##_off, insn->slot, false)
 #endif
 #ifdef QEMU_GENERATE
 #define fSTOREMMVNQ(EA, SRC, MASK) \
-    gen_vreg_masked_store(ctx, EA, SRC##_off, MASK##_off, insn->slot, true)
+    gen_vreg_masked_store(ctx, EA, SRC##_base, SRC##_off, \
+                          MASK##_base, MASK##_off, insn->slot, true)
 #endif
 #ifdef QEMU_GENERATE
 #define fSTOREMMVU(EA, SRC) \
-    gen_vreg_store(ctx, EA, SRC##_off, insn->slot, false)
+    gen_vreg_store(ctx, EA, SRC##_base, SRC##_off, insn->slot, false)
 #endif
 #define fVFOREACH(WIDTH, VAR) for (VAR = 0; VAR < fVELEM(WIDTH); VAR++)
 #define fVARRAY_ELEMENT_ACCESS(ARRAY, TYPE, INDEX) \
diff --git a/target/hexagon/translate.h b/target/hexagon/translate.h
index b87a2b20e2f..a65be7b2e04 100644
--- a/target/hexagon/translate.h
+++ b/target/hexagon/translate.h
@@ -91,6 +91,7 @@ typedef struct DisasContext {
     bool pcycle_enabled;
     bool hvx_coproc_enabled;
     bool hvx_check_emitted;
+    TCGv_ptr hvx_base;
     uint32_t num_cycles;
 } DisasContext;
 
@@ -192,9 +193,9 @@ static inline void ctx_log_reg_read_pair(DisasContext *ctx, 
int rnum)
 }
 
 intptr_t ctx_future_vreg_off(DisasContext *ctx, int regnum,
-                             int num, bool alloc_ok);
+                             int num, bool alloc_ok, TCGv_ptr *base);
 intptr_t ctx_tmp_vreg_off(DisasContext *ctx, int regnum,
-                          int num, bool alloc_ok);
+                          int num, bool alloc_ok, TCGv_ptr *base);
 
 static inline void ctx_start_hvx_insn(DisasContext *ctx)
 {
diff --git a/target/hexagon/genptr.c b/target/hexagon/genptr.c
index 257836be227..dd8ae8c5541 100644
--- a/target/hexagon/genptr.c
+++ b/target/hexagon/genptr.c
@@ -56,8 +56,10 @@ static void gen_sabsdiff_vec(unsigned vece, TCGv_vec d, 
TCGv_vec a, TCGv_vec b)
     tcg_gen_sub_vec(vece, d, d, t);
 }
 
-void gen_gvec_sabsdiff(unsigned vece, uint32_t dofs, uint32_t aofs,
-                       uint32_t bofs, uint32_t oprsz, uint32_t maxsz)
+void gen_gvec_sabsdiff_var(unsigned vece, TCGv_ptr dbase, uint32_t dofs,
+                           TCGv_ptr abase, uint32_t aofs,
+                           TCGv_ptr bbase, uint32_t bofs,
+                           uint32_t oprsz, uint32_t maxsz)
 {
     static const TCGOpcode vecop_list[] = {
         INDEX_op_sub_vec, INDEX_op_smin_vec, INDEX_op_smax_vec, 0
@@ -75,7 +77,15 @@ void gen_gvec_sabsdiff(unsigned vece, uint32_t dofs, 
uint32_t aofs,
     };
 
     tcg_debug_assert(vece == MO_16 || vece == MO_32);
-    tcg_gen_gvec_3(dofs, aofs, bofs, oprsz, maxsz, &ops[vece]);
+    tcg_gen_gvec_3_var(dbase, dofs, abase, aofs, bbase, bofs,
+                       oprsz, maxsz, &ops[vece]);
+}
+
+void gen_gvec_sabsdiff(unsigned vece, uint32_t dofs, uint32_t aofs,
+                       uint32_t bofs, uint32_t oprsz, uint32_t maxsz)
+{
+    gen_gvec_sabsdiff_var(vece, tcg_env, dofs, tcg_env, aofs, tcg_env, bofs,
+                         oprsz, maxsz);
 }
 
 static void gen_uabsdiff_vec(unsigned vece, TCGv_vec d, TCGv_vec a, TCGv_vec b)
@@ -87,8 +97,10 @@ static void gen_uabsdiff_vec(unsigned vece, TCGv_vec d, 
TCGv_vec a, TCGv_vec b)
     tcg_gen_sub_vec(vece, d, d, t);
 }
 
-void gen_gvec_uabsdiff(unsigned vece, uint32_t dofs, uint32_t aofs,
-                       uint32_t bofs, uint32_t oprsz, uint32_t maxsz)
+void gen_gvec_uabsdiff_var(unsigned vece, TCGv_ptr dbase, uint32_t dofs,
+                           TCGv_ptr abase, uint32_t aofs,
+                           TCGv_ptr bbase, uint32_t bofs,
+                           uint32_t oprsz, uint32_t maxsz)
 {
     static const TCGOpcode vecop_list[] = {
         INDEX_op_sub_vec, INDEX_op_umin_vec, INDEX_op_umax_vec, 0
@@ -105,7 +117,15 @@ void gen_gvec_uabsdiff(unsigned vece, uint32_t dofs, 
uint32_t aofs,
     };
 
     tcg_debug_assert(vece == MO_8 || vece == MO_16);
-    tcg_gen_gvec_3(dofs, aofs, bofs, oprsz, maxsz, &ops[vece]);
+    tcg_gen_gvec_3_var(dbase, dofs, abase, aofs, bbase, bofs,
+                       oprsz, maxsz, &ops[vece]);
+}
+
+void gen_gvec_uabsdiff(unsigned vece, uint32_t dofs, uint32_t aofs,
+                       uint32_t bofs, uint32_t oprsz, uint32_t maxsz)
+{
+    gen_gvec_uabsdiff_var(vece, tcg_env, dofs, tcg_env, aofs, tcg_env, bofs,
+                         oprsz, maxsz);
 }
 
 TCGv gen_read_reg(TCGv result, int num)
@@ -1431,54 +1451,56 @@ static void gen_asr_r_svw_trun(DisasContext *ctx, TCGv 
RdV,
     gen_set_label(done);
 }
 
-static intptr_t vreg_src_off(DisasContext *ctx, int num)
+static intptr_t vreg_src_off(DisasContext *ctx, int num, TCGv_ptr *base)
 {
-    intptr_t offset = offsetof(CPUHexagonState, hvx_ctx.VRegs[num]);
+    intptr_t offset = offsetof(HexagonHVXContext, VRegs[num]);
 
+    *base = ctx->hvx_base;
     if (test_bit(num, ctx->vregs_select)) {
-        offset = ctx_future_vreg_off(ctx, num, 1, false);
+        offset = ctx_future_vreg_off(ctx, num, 1, false, base);
     }
     if (test_bit(num, ctx->vregs_updated_tmp)) {
-        offset = ctx_tmp_vreg_off(ctx, num, 1, false);
+        offset = ctx_tmp_vreg_off(ctx, num, 1, false, base);
     }
     return offset;
 }
 
-static void gen_vreg_write(DisasContext *ctx, intptr_t srcoff, int num,
-                               VRegWriteType type)
+static void gen_vreg_write(DisasContext *ctx, TCGv_ptr srcbase,
+                           intptr_t srcoff, int num, VRegWriteType type)
 {
+    TCGv_ptr dstbase;
     intptr_t dstoff;
 
     if (type != EXT_TMP) {
-        dstoff = ctx_future_vreg_off(ctx, num, 1, true);
-        tcg_gen_gvec_mov(MO_64, dstoff, srcoff,
-                         sizeof(MMVector), sizeof(MMVector));
+        dstoff = ctx_future_vreg_off(ctx, num, 1, true, &dstbase);
     } else {
-        dstoff = ctx_tmp_vreg_off(ctx, num, 1, false);
-        tcg_gen_gvec_mov(MO_64, dstoff, srcoff,
-                         sizeof(MMVector), sizeof(MMVector));
+        dstoff = ctx_tmp_vreg_off(ctx, num, 1, false, &dstbase);
     }
+    tcg_gen_gvec_mov_var(MO_64, dstbase, dstoff, srcbase, srcoff,
+                         sizeof(MMVector), sizeof(MMVector));
 }
 
-static void gen_vreg_write_pair(DisasContext *ctx, intptr_t srcoff, int num,
-                                    VRegWriteType type)
+static void gen_vreg_write_pair(DisasContext *ctx, TCGv_ptr srcbase,
+                                intptr_t srcoff, int num, VRegWriteType type)
 {
-    gen_vreg_write(ctx, srcoff, num ^ 0, type);
+    gen_vreg_write(ctx, srcbase, srcoff, num ^ 0, type);
     srcoff += sizeof(MMVector);
-    gen_vreg_write(ctx, srcoff, num ^ 1, type);
+    gen_vreg_write(ctx, srcbase, srcoff, num ^ 1, type);
 }
 
-static intptr_t get_result_qreg(DisasContext *ctx, int qnum)
+static intptr_t get_result_qreg(DisasContext *ctx, int qnum, TCGv_ptr *base)
 {
     if (ctx->need_commit) {
+        *base = tcg_env;
         return  offsetof(CPUHexagonState, future_QRegs[qnum]);
     } else {
-        return  offsetof(CPUHexagonState, hvx_ctx.QRegs[qnum]);
+        *base = ctx->hvx_base;
+        return  offsetof(HexagonHVXContext, QRegs[qnum]);
     }
 }
 
-static void gen_vreg_load(DisasContext *ctx, intptr_t dstoff, TCGv src,
-                          bool aligned)
+static void gen_vreg_load(DisasContext *ctx, TCGv_ptr dstbase,
+                          intptr_t dstoff, TCGv src, bool aligned)
 {
     TCGv_i64 tmp = tcg_temp_new_i64();
     if (aligned) {
@@ -1487,12 +1509,12 @@ static void gen_vreg_load(DisasContext *ctx, intptr_t 
dstoff, TCGv src,
     for (int i = 0; i < sizeof(MMVector) / 8; i++) {
         tcg_gen_qemu_ld_i64(tmp, src, ctx->mem_idx, MO_LE | MO_UQ);
         tcg_gen_addi_tl(src, src, 8);
-        tcg_gen_st_i64(tmp, tcg_env, dstoff + i * 8);
+        tcg_gen_st_i64(tmp, dstbase, dstoff + i * 8);
     }
 }
 
-static void gen_vreg_store(DisasContext *ctx, TCGv EA, intptr_t srcoff,
-                           int slot, bool aligned)
+static void gen_vreg_store(DisasContext *ctx, TCGv EA, TCGv_ptr srcbase,
+                           intptr_t srcoff, int slot, bool aligned)
 {
     intptr_t dstoff = offsetof(CPUHexagonState, vstore[slot].data);
     intptr_t maskoff = offsetof(CPUHexagonState, vstore[slot].mask);
@@ -1513,13 +1535,16 @@ static void gen_vreg_store(DisasContext *ctx, TCGv EA, 
intptr_t srcoff,
     tcg_gen_movi_tl(hex_vstore_size[slot], sizeof(MMVector));
 
     /* Copy the data to the vstore buffer */
-    tcg_gen_gvec_mov(MO_64, dstoff, srcoff, sizeof(MMVector), 
sizeof(MMVector));
+    tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, srcbase, srcoff,
+                         sizeof(MMVector), sizeof(MMVector));
     /* Set the mask to all 1's */
     tcg_gen_gvec_dup_imm(MO_64, maskoff, sizeof(MMQReg), sizeof(MMQReg), ~0LL);
 }
 
-static void gen_vreg_masked_store(DisasContext *ctx, TCGv EA, intptr_t srcoff,
-                                  intptr_t bitsoff, int slot, bool invert)
+static void gen_vreg_masked_store(DisasContext *ctx, TCGv EA,
+                                  TCGv_ptr srcbase, intptr_t srcoff,
+                                  TCGv_ptr bitsbase, intptr_t bitsoff,
+                                  int slot, bool invert)
 {
     intptr_t dstoff = offsetof(CPUHexagonState, vstore[slot].data);
     intptr_t maskoff = offsetof(CPUHexagonState, vstore[slot].mask);
@@ -1530,16 +1555,19 @@ static void gen_vreg_masked_store(DisasContext *ctx, 
TCGv EA, intptr_t srcoff,
     tcg_gen_movi_tl(hex_vstore_size[slot], sizeof(MMVector));
 
     /* Copy the data to the vstore buffer */
-    tcg_gen_gvec_mov(MO_64, dstoff, srcoff, sizeof(MMVector), 
sizeof(MMVector));
+    tcg_gen_gvec_mov_var(MO_64, tcg_env, dstoff, srcbase, srcoff,
+                         sizeof(MMVector), sizeof(MMVector));
     /* Copy the mask */
-    tcg_gen_gvec_mov(MO_64, maskoff, bitsoff, sizeof(MMQReg), sizeof(MMQReg));
+    tcg_gen_gvec_mov_var(MO_64, tcg_env, maskoff, bitsbase, bitsoff,
+                         sizeof(MMQReg), sizeof(MMQReg));
     if (invert) {
         tcg_gen_gvec_not(MO_64, maskoff, maskoff,
                          sizeof(MMQReg), sizeof(MMQReg));
     }
 }
 
-static void vec_to_qvec(size_t size, intptr_t dstoff, intptr_t srcoff)
+static void vec_to_qvec(size_t size, TCGv_ptr dstbase, intptr_t dstoff,
+                        TCGv_ptr srcbase, intptr_t srcoff)
 {
     TCGv_i64 tmp = tcg_temp_new_i64();
     TCGv_i64 word = tcg_temp_new_i64();
@@ -1549,7 +1577,7 @@ static void vec_to_qvec(size_t size, intptr_t dstoff, 
intptr_t srcoff)
     TCGv_i64 ones = tcg_constant_i64(~0);
 
     for (int i = 0; i < sizeof(MMVector) / 8; i++) {
-        tcg_gen_ld_i64(tmp, tcg_env, srcoff + i * 8);
+        tcg_gen_ld_i64(tmp, srcbase, srcoff + i * 8);
         tcg_gen_movi_i64(mask, 0);
 
         for (int j = 0; j < 8; j += size) {
@@ -1558,7 +1586,7 @@ static void vec_to_qvec(size_t size, intptr_t dstoff, 
intptr_t srcoff)
             tcg_gen_deposit_i64(mask, mask, bits, j, size);
         }
 
-        tcg_gen_st8_i64(mask, tcg_env, dstoff + i);
+        tcg_gen_st8_i64(mask, dstbase, dstoff + i);
     }
 }
 
diff --git a/target/hexagon/translate.c b/target/hexagon/translate.c
index b05ac91846a..b9ebe4c3e77 100644
--- a/target/hexagon/translate.c
+++ b/target/hexagon/translate.c
@@ -82,14 +82,18 @@ static const char * const hexagon_prednames[] = {
 };
 
 intptr_t ctx_future_vreg_off(DisasContext *ctx, int regnum,
-                          int num, bool alloc_ok)
+                          int num, bool alloc_ok, TCGv_ptr *base)
 {
     intptr_t offset;
 
     if (!ctx->need_commit) {
-        return offsetof(CPUHexagonState, hvx_ctx.VRegs[regnum]);
+        /* Short circuit: the write goes straight to the register file. */
+        *base = ctx->hvx_base;
+        return offsetof(HexagonHVXContext, VRegs[regnum]);
     }
 
+    *base = tcg_env;
+
     /* See if it is already allocated */
     for (int i = 0; i < ctx->future_vregs_idx; i++) {
         if (ctx->future_vregs_num[i] == regnum) {
@@ -108,10 +112,12 @@ intptr_t ctx_future_vreg_off(DisasContext *ctx, int 
regnum,
 }
 
 intptr_t ctx_tmp_vreg_off(DisasContext *ctx, int regnum,
-                          int num, bool alloc_ok)
+                          int num, bool alloc_ok, TCGv_ptr *base)
 {
     intptr_t offset;
 
+    *base = tcg_env;
+
     /* See if it is already allocated */
     for (int i = 0; i < ctx->tmp_vregs_idx; i++) {
         if (ctx->tmp_vregs_num[i] == regnum) {
@@ -691,30 +697,39 @@ static void gen_start_packet(DisasContext *ctx)
         }
     }
 
+    ctx->hvx_base = NULL;
+    if (ctx->pkt.pkt_has_hvx) {
+        ctx->hvx_base = tcg_temp_new_ptr();
+        tcg_gen_ld_ptr(ctx->hvx_base, tcg_env,
+                       offsetof(CPUHexagonState, hvx));
+    }
+
     /* Preload the predicated HVX registers into future_VRegs and tmp_VRegs */
     if (!bitmap_empty(ctx->predicated_future_vregs, NUM_VREGS)) {
         i = find_first_bit(ctx->predicated_future_vregs, NUM_VREGS);
         while (i < NUM_VREGS) {
+            TCGv_ptr VdV_base;
             const intptr_t VdV_off =
-                ctx_future_vreg_off(ctx, i, 1, true);
-            intptr_t src_off = offsetof(CPUHexagonState, hvx_ctx.VRegs[i]);
-            tcg_gen_gvec_mov(MO_64, VdV_off,
-                             src_off,
-                             sizeof(MMVector),
-                             sizeof(MMVector));
+                ctx_future_vreg_off(ctx, i, 1, true, &VdV_base);
+            intptr_t src_off = offsetof(HexagonHVXContext, VRegs[i]);
+            tcg_gen_gvec_mov_var(MO_64, VdV_base, VdV_off,
+                                 ctx->hvx_base, src_off,
+                                 sizeof(MMVector),
+                                 sizeof(MMVector));
             i = find_next_bit(ctx->predicated_future_vregs, NUM_VREGS, i + 1);
         }
     }
     if (!bitmap_empty(ctx->predicated_tmp_vregs, NUM_VREGS)) {
         i = find_first_bit(ctx->predicated_tmp_vregs, NUM_VREGS);
         while (i < NUM_VREGS) {
+            TCGv_ptr VdV_base;
             const intptr_t VdV_off =
-                ctx_tmp_vreg_off(ctx, i, 1, true);
-            intptr_t src_off = offsetof(CPUHexagonState, hvx_ctx.VRegs[i]);
-            tcg_gen_gvec_mov(MO_64, VdV_off,
-                             src_off,
-                             sizeof(MMVector),
-                             sizeof(MMVector));
+                ctx_tmp_vreg_off(ctx, i, 1, true, &VdV_base);
+            intptr_t src_off = offsetof(HexagonHVXContext, VRegs[i]);
+            tcg_gen_gvec_mov_var(MO_64, VdV_base, VdV_off,
+                                 ctx->hvx_base, src_off,
+                                 sizeof(MMVector),
+                                 sizeof(MMVector));
             i = find_next_bit(ctx->predicated_tmp_vregs, NUM_VREGS, i + 1);
         }
     }
@@ -1017,11 +1032,13 @@ static void gen_commit_hvx(DisasContext *ctx)
      */
     for (i = 0; i < ctx->vreg_log_idx; i++) {
         int rnum = ctx->vreg_log[i];
-        intptr_t dstoff = offsetof(CPUHexagonState, hvx_ctx.VRegs[rnum]);
-        intptr_t srcoff = ctx_future_vreg_off(ctx, rnum, 1, false);
+        intptr_t dstoff = offsetof(HexagonHVXContext, VRegs[rnum]);
+        TCGv_ptr srcbase;
+        intptr_t srcoff = ctx_future_vreg_off(ctx, rnum, 1, false, &srcbase);
         size_t size = sizeof(MMVector);
 
-        tcg_gen_gvec_mov(MO_64, dstoff, srcoff, size, size);
+        tcg_gen_gvec_mov_var(MO_64, ctx->hvx_base, dstoff, srcbase, srcoff,
+                             size, size);
     }
 
     /*
@@ -1032,11 +1049,12 @@ static void gen_commit_hvx(DisasContext *ctx)
      */
     for (i = 0; i < ctx->qreg_log_idx; i++) {
         int rnum = ctx->qreg_log[i];
-        intptr_t dstoff = offsetof(CPUHexagonState, hvx_ctx.QRegs[rnum]);
+        intptr_t dstoff = offsetof(HexagonHVXContext, QRegs[rnum]);
         intptr_t srcoff = offsetof(CPUHexagonState, future_QRegs[rnum]);
         size_t size = sizeof(MMQReg);
 
-        tcg_gen_gvec_mov(MO_64, dstoff, srcoff, size, size);
+        tcg_gen_gvec_mov_var(MO_64, ctx->hvx_base, dstoff, tcg_env, srcoff,
+                             size, size);
     }
 
     if (pkt_has_hvx_store(&ctx->pkt)) {
diff --git a/target/hexagon/hex_common.py b/target/hexagon/hex_common.py
index ea3163132d9..2f5aa415ddf 100755
--- a/target/hexagon/hex_common.py
+++ b/target/hexagon/hex_common.py
@@ -434,6 +434,14 @@ def is_hvx_reg(self):
         return True
     def hvx_off(self):
         return f"{self.reg_tcg()}_off"
+    def hvx_base(self):
+        return f"{self.reg_tcg()}_base"
+    def decl_tcg_ptr(self, f):
+        ptr = self.reg_tcg()
+        f.write(code_fmt(f"""\
+            TCGv_ptr {ptr} = tcg_temp_new_ptr();
+            tcg_gen_addi_ptr({ptr}, {self.hvx_base()}, {self.hvx_off()});
+        """))
     def helper_proto_type(self):
         return "ptr"
     def helper_arg_type(self):
@@ -778,18 +786,17 @@ class VRegDest(Register, Hvx, Dest):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()};
             const intptr_t {self.hvx_off()} =
-                {vreg_offset_func(tag)}(ctx, {self.reg_num}, 1, true);
+                {vreg_offset_func(tag)}(ctx, {self.reg_num}, 1,
+                                        true, &{self.hvx_base()});
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def gen_zero(self, f):
         f.write(code_fmt(f"""\
-                tcg_gen_gvec_dup_imm(MO_64, {self.hvx_off()},
-                    sizeof(MMVector), sizeof(MMVector), 0);
+                tcg_gen_gvec_dup_imm_var(MO_64, {self.hvx_base()},
+                    {self.hvx_off()}, sizeof(MMVector), sizeof(MMVector), 0);
             """))
     def gen_write(self, f, tag):
         pass
@@ -809,13 +816,12 @@ class VRegSource(Register, Hvx, OldSource):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
-            const intptr_t {self.hvx_off()} = vreg_src_off(ctx, 
{self.reg_num});
+            TCGv_ptr {self.hvx_base()};
+            const intptr_t {self.hvx_off()} =
+                vreg_src_off(ctx, {self.reg_num}, &{self.hvx_base()});
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def helper_hvx_desc(self, f):
         f.write(code_fmt(f"""\
             /* {self.reg_tcg()} is *(MMVector *)({self.helper_arg_name()}) */
@@ -830,8 +836,10 @@ def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         if skip_qemu_helper(tag):
             f.write(code_fmt(f"""\
+                TCGv_ptr {self.hvx_base()};
                 const intptr_t {self.hvx_off()} =
-                    ctx_future_vreg_off(ctx, {self.reg_num}, 1, true);
+                    ctx_future_vreg_off(ctx, {self.reg_num}, 1,
+                                        true, &{self.hvx_base()});
             """))
     def helper_hvx_desc(self, f):
         f.write(code_fmt(f"""\
@@ -846,21 +854,24 @@ class VRegReadWrite(Register, Hvx, ReadWrite):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()};
+            TCGv_ptr {self.reg_tcg()}_srcbase;
             const intptr_t {self.hvx_off()} =
-                {vreg_offset_func(tag)}(ctx, {self.reg_num}, 1, true);
-            tcg_gen_gvec_mov(MO_64, {self.hvx_off()},
-                             vreg_src_off(ctx, {self.reg_num}),
-                             sizeof(MMVector), sizeof(MMVector));
+                {vreg_offset_func(tag)}(ctx, {self.reg_num}, 1,
+                                        true, &{self.hvx_base()});
+            const intptr_t {self.reg_tcg()}_srcoff =
+                vreg_src_off(ctx, {self.reg_num}, &{self.reg_tcg()}_srcbase);
+            tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()}, {self.hvx_off()},
+                                 {self.reg_tcg()}_srcbase,
+                                 {self.reg_tcg()}_srcoff,
+                                 sizeof(MMVector), sizeof(MMVector));
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def gen_zero(self, f):
         f.write(code_fmt(f"""\
-                tcg_gen_gvec_dup_imm(MO_64, {self.hvx_off()},
-                    sizeof(MMVector), sizeof(MMVector), 0);
+                tcg_gen_gvec_dup_imm_var(MO_64, {self.hvx_base()},
+                    {self.hvx_off()}, sizeof(MMVector), sizeof(MMVector), 0);
             """))
     def gen_write(self, f, tag):
         pass
@@ -884,15 +895,21 @@ class VRegTmp(Register, Hvx, ReadWrite):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()} = tcg_env;
             const intptr_t {self.hvx_off()} = offsetof(CPUHexagonState, vtmp);
         """))
         if not skip_qemu_helper(tag):
+            self.decl_tcg_ptr(f)
             f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-                tcg_gen_gvec_mov(MO_64, {self.hvx_off()},
-                                 vreg_src_off(ctx, {self.reg_num}),
-                                 sizeof(MMVector), sizeof(MMVector));
+                TCGv_ptr {self.reg_tcg()}_srcbase;
+                const intptr_t {self.reg_tcg()}_srcoff =
+                    vreg_src_off(ctx, {self.reg_num},
+                                 &{self.reg_tcg()}_srcbase);
+                tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()},
+                                     {self.hvx_off()},
+                                     {self.reg_tcg()}_srcbase,
+                                     {self.reg_tcg()}_srcoff,
+                                     sizeof(MMVector), sizeof(MMVector));
             """))
     def gen_zero(self, f):
         f.write(code_fmt(f"""\
@@ -901,8 +918,8 @@ def gen_zero(self, f):
             """))
     def gen_write(self, f, tag):
         f.write(code_fmt(f"""\
-            gen_vreg_write(ctx, {self.hvx_off()}, {self.reg_num},
-                           {hvx_newv(tag)});
+            gen_vreg_write(ctx, {self.hvx_base()}, {self.hvx_off()},
+                           {self.reg_num}, {hvx_newv(tag)});
         """))
     def helper_hvx_desc(self, f):
         f.write(code_fmt(f"""\
@@ -924,17 +941,16 @@ class VRegPairDest(Register, Hvx, Dest):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()};
             const intptr_t {self.hvx_off()} =
-                {vreg_offset_func(tag)}(ctx, {self.reg_num}, 2, true);
+                {vreg_offset_func(tag)}(ctx, {self.reg_num}, 2,
+                                        true, &{self.hvx_base()});
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def gen_zero(self, f):
         f.write(code_fmt(f"""\
-            tcg_gen_gvec_dup_imm(MO_64, {self.hvx_off()},
+            tcg_gen_gvec_dup_imm_var(MO_64, {self.hvx_base()}, 
{self.hvx_off()},
                 sizeof(MMVectorPair), sizeof(MMVectorPair), 0);
         """))
     def gen_write(self, f, tag):
@@ -955,20 +971,27 @@ class VRegPairSource(Register, Hvx, OldSource):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()} = tcg_env;
+            TCGv_ptr {self.reg_tcg()}_srcbase;
             const intptr_t {self.hvx_off()} =
                 offsetof(CPUHexagonState, {self.reg_tcg()});
-            tcg_gen_gvec_mov(MO_64, {self.hvx_off()},
-                             vreg_src_off(ctx, {self.reg_num}),
-                             sizeof(MMVector), sizeof(MMVector));
-            tcg_gen_gvec_mov(MO_64, {self.hvx_off()} + sizeof(MMVector),
-                             vreg_src_off(ctx, {self.reg_num} ^ 1),
-                             sizeof(MMVector), sizeof(MMVector));
+            intptr_t {self.reg_tcg()}_srcoff =
+                vreg_src_off(ctx, {self.reg_num}, &{self.reg_tcg()}_srcbase);
+            tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()}, {self.hvx_off()},
+                                 {self.reg_tcg()}_srcbase,
+                                 {self.reg_tcg()}_srcoff,
+                                 sizeof(MMVector), sizeof(MMVector));
+            {self.reg_tcg()}_srcoff =
+                vreg_src_off(ctx, {self.reg_num} ^ 1,
+                             &{self.reg_tcg()}_srcbase);
+            tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()},
+                                 {self.hvx_off()} + sizeof(MMVector),
+                                 {self.reg_tcg()}_srcbase,
+                                 {self.reg_tcg()}_srcoff,
+                                 sizeof(MMVector), sizeof(MMVector));
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def helper_hvx_desc(self, f):
         f.write(code_fmt(f"""\
             /* {self.reg_tcg()} is *(MMVectorPair *)({self.helper_arg_name()}) 
*/
@@ -982,29 +1005,36 @@ class VRegPairReadWrite(Register, Hvx, ReadWrite):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()} = tcg_env;
+            TCGv_ptr {self.reg_tcg()}_srcbase;
             const intptr_t {self.hvx_off()} =
                 offsetof(CPUHexagonState, {self.reg_tcg()});
-            tcg_gen_gvec_mov(MO_64, {self.hvx_off()},
-                             vreg_src_off(ctx, {self.reg_num}),
-                             sizeof(MMVector), sizeof(MMVector));
-            tcg_gen_gvec_mov(MO_64, {self.hvx_off()} + sizeof(MMVector),
-                             vreg_src_off(ctx, {self.reg_num} ^ 1),
-                             sizeof(MMVector), sizeof(MMVector));
+            intptr_t {self.reg_tcg()}_srcoff =
+                vreg_src_off(ctx, {self.reg_num}, &{self.reg_tcg()}_srcbase);
+            tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()}, {self.hvx_off()},
+                                 {self.reg_tcg()}_srcbase,
+                                 {self.reg_tcg()}_srcoff,
+                                 sizeof(MMVector), sizeof(MMVector));
+            {self.reg_tcg()}_srcoff =
+                vreg_src_off(ctx, {self.reg_num} ^ 1,
+                             &{self.reg_tcg()}_srcbase);
+            tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()},
+                                 {self.hvx_off()} + sizeof(MMVector),
+                                 {self.reg_tcg()}_srcbase,
+                                 {self.reg_tcg()}_srcoff,
+                                 sizeof(MMVector), sizeof(MMVector));
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def gen_zero(self, f):
         f.write(code_fmt(f"""\
-            tcg_gen_gvec_dup_imm(MO_64, {self.hvx_off()},
+            tcg_gen_gvec_dup_imm_var(MO_64, {self.hvx_base()}, 
{self.hvx_off()},
                 sizeof(MMVectorPair), sizeof(MMVectorPair), 0);
         """))
     def gen_write(self, f, tag):
         f.write(code_fmt(f"""\
-            gen_vreg_write_pair(ctx, {self.hvx_off()}, {self.reg_num},
-                                {hvx_newv(tag)});
+            gen_vreg_write_pair(ctx, {self.hvx_base()}, {self.hvx_off()},
+                                {self.reg_num}, {hvx_newv(tag)});
         """))
     def helper_hvx_desc(self, f):
         f.write(code_fmt(f"""\
@@ -1026,14 +1056,12 @@ class QRegDest(Register, Hvx, Dest):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()};
             const intptr_t {self.hvx_off()} =
-                get_result_qreg(ctx, {self.reg_num});
+                get_result_qreg(ctx, {self.reg_num}, &{self.hvx_base()});
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def gen_write(self, f, tag):
         pass
     def helper_hvx_desc(self, f):
@@ -1049,14 +1077,12 @@ class QRegSource(Register, Hvx, OldSource):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()} = ctx->hvx_base;
             const intptr_t {self.hvx_off()} =
-                offsetof(CPUHexagonState, hvx_ctx.QRegs[{self.reg_num}]);
+                offsetof(HexagonHVXContext, QRegs[{self.reg_num}]);
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def helper_hvx_desc(self, f):
         f.write(code_fmt(f"""\
             /* {self.reg_tcg()} is *(MMQReg *)({self.helper_arg_name()}) */
@@ -1070,18 +1096,17 @@ class QRegReadWrite(Register, Hvx, ReadWrite):
     def decl_tcg(self, f, tag, regno):
         self.decl_reg_num(f, regno)
         f.write(code_fmt(f"""\
+            TCGv_ptr {self.hvx_base()};
             const intptr_t {self.hvx_off()} =
-                get_result_qreg(ctx, {self.reg_num});
-            tcg_gen_gvec_mov(MO_64, {self.hvx_off()},
-                             offsetof(CPUHexagonState,
-                                      hvx_ctx.QRegs[{self.reg_num}]),
-                             sizeof(MMQReg), sizeof(MMQReg));
+                get_result_qreg(ctx, {self.reg_num}, &{self.hvx_base()});
+            tcg_gen_gvec_mov_var(MO_64, {self.hvx_base()}, {self.hvx_off()},
+                                 ctx->hvx_base,
+                                 offsetof(HexagonHVXContext,
+                                          QRegs[{self.reg_num}]),
+                                 sizeof(MMQReg), sizeof(MMQReg));
         """))
         if not skip_qemu_helper(tag):
-            f.write(code_fmt(f"""\
-                TCGv_ptr {self.reg_tcg()} = tcg_temp_new_ptr();
-                tcg_gen_addi_ptr({self.reg_tcg()}, tcg_env, {self.hvx_off()});
-            """))
+            self.decl_tcg_ptr(f)
     def gen_write(self, f, tag):
         pass
     def helper_hvx_desc(self, f):
-- 
2.34.1

Reply via email to