qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [PATCH for-8.1 v2 0/2] target/mips: Avoid shift by negative number in page_table_walk_refill()
@ 2023-07-17 21:35 Philippe Mathieu-Daudé
  2023-07-17 21:35 ` [PATCH for-8.1 v2 1/2] target/mips: Pass directory/leaf shift values to walk_directory() Philippe Mathieu-Daudé
  2023-07-17 21:35 ` [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
  0 siblings, 2 replies; 6+ messages in thread
From: Philippe Mathieu-Daudé @ 2023-07-17 21:35 UTC (permalink / raw)
  To: qemu-devel
  Cc: Philippe Mathieu-Daudé, Jiaxun Yang, Aleksandar Rikalo,
	Aurelien Jarno

This is a respin of Peter's patch, but
- pass already-evaluated values to walk_directory() instead
  of an assert(),
- check 'ptew > 1' instead of directory/leaf_shift == -1,
- use unsigned type

Since v1: walk_directory() doesn't have to rely on the to sanitize
          the input values.

Peter, if you don't see this as an improvement I'll take your original
patch.

Regards,

Phil.

Supersedes: <20230717162940.814078-1-peter.maydell@linaro.org>

Philippe Mathieu-Daudé (2):
  target/mips: Pass directory/leaf shift values to walk_directory()
  target/mips: Avoid shift by negative number in
    page_table_walk_refill()

 target/mips/tcg/sysemu/tlb_helper.c | 48 ++++++++++++++---------------
 1 file changed, 24 insertions(+), 24 deletions(-)

-- 
2.38.1



^ permalink raw reply	[flat|nested] 6+ messages in thread

* [PATCH for-8.1 v2 1/2] target/mips: Pass directory/leaf shift values to walk_directory()
  2023-07-17 21:35 [PATCH for-8.1 v2 0/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
@ 2023-07-17 21:35 ` Philippe Mathieu-Daudé
  2023-07-18 10:20   ` Peter Maydell
  2023-07-17 21:35 ` [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
  1 sibling, 1 reply; 6+ messages in thread
From: Philippe Mathieu-Daudé @ 2023-07-17 21:35 UTC (permalink / raw)
  To: qemu-devel
  Cc: Philippe Mathieu-Daudé, Jiaxun Yang, Aleksandar Rikalo,
	Aurelien Jarno

We already evaluated directory_shift and leaf_shift in
page_table_walk_refill(), no need to do that again: pass
as argument.

Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
---
 target/mips/tcg/sysemu/tlb_helper.c | 18 ++++++++----------
 1 file changed, 8 insertions(+), 10 deletions(-)

diff --git a/target/mips/tcg/sysemu/tlb_helper.c b/target/mips/tcg/sysemu/tlb_helper.c
index e5e1e9dd3f..e7be649b02 100644
--- a/target/mips/tcg/sysemu/tlb_helper.c
+++ b/target/mips/tcg/sysemu/tlb_helper.c
@@ -623,18 +623,13 @@ static uint64_t get_tlb_entry_layout(CPUMIPSState *env, uint64_t entry,
 
 static int walk_directory(CPUMIPSState *env, uint64_t *vaddr,
         int directory_index, bool *huge_page, bool *hgpg_directory_hit,
-        uint64_t *pw_entrylo0, uint64_t *pw_entrylo1)
+        uint64_t *pw_entrylo0, uint64_t *pw_entrylo1,
+        int directory_shift, int leaf_shift)
 {
     int dph = (env->CP0_PWCtl >> CP0PC_DPH) & 0x1;
     int psn = (env->CP0_PWCtl >> CP0PC_PSN) & 0x3F;
     int hugepg = (env->CP0_PWCtl >> CP0PC_HUGEPG) & 0x1;
     int pf_ptew = (env->CP0_PWField >> CP0PF_PTEW) & 0x3F;
-    int ptew = (env->CP0_PWSize >> CP0PS_PTEW) & 0x3F;
-    int native_shift = (((env->CP0_PWSize >> CP0PS_PS) & 1) == 0) ? 2 : 3;
-    int directory_shift = (ptew > 1) ? -1 :
-            (hugepg && (ptew == 1)) ? native_shift + 1 : native_shift;
-    int leaf_shift = (ptew > 1) ? -1 :
-            (ptew == 1) ? native_shift + 1 : native_shift;
     uint32_t direntry_size = 1 << (directory_shift + 3);
     uint32_t leafentry_size = 1 << (leaf_shift + 3);
     uint64_t entry;
@@ -779,7 +774,8 @@ static bool page_table_walk_refill(CPUMIPSState *env, vaddr address,
     if (gdw > 0) {
         vaddr |= goffset;
         switch (walk_directory(env, &vaddr, pf_gdw, &huge_page, &hgpg_gdhit,
-                               &pw_entrylo0, &pw_entrylo1))
+                               &pw_entrylo0, &pw_entrylo1,
+                               directory_shift, leaf_shift))
         {
         case 0:
             return false;
@@ -795,7 +791,8 @@ static bool page_table_walk_refill(CPUMIPSState *env, vaddr address,
     if (udw > 0) {
         vaddr |= uoffset;
         switch (walk_directory(env, &vaddr, pf_udw, &huge_page, &hgpg_udhit,
-                               &pw_entrylo0, &pw_entrylo1))
+                               &pw_entrylo0, &pw_entrylo1,
+                               directory_shift, leaf_shift))
         {
         case 0:
             return false;
@@ -811,7 +808,8 @@ static bool page_table_walk_refill(CPUMIPSState *env, vaddr address,
     if (mdw > 0) {
         vaddr |= moffset;
         switch (walk_directory(env, &vaddr, pf_mdw, &huge_page, &hgpg_mdhit,
-                               &pw_entrylo0, &pw_entrylo1))
+                               &pw_entrylo0, &pw_entrylo1,
+                               directory_shift, leaf_shift))
         {
         case 0:
             return false;
-- 
2.38.1



^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill()
  2023-07-17 21:35 [PATCH for-8.1 v2 0/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
  2023-07-17 21:35 ` [PATCH for-8.1 v2 1/2] target/mips: Pass directory/leaf shift values to walk_directory() Philippe Mathieu-Daudé
@ 2023-07-17 21:35 ` Philippe Mathieu-Daudé
  2023-07-18  5:59   ` Philippe Mathieu-Daudé
  2023-07-18 10:25   ` Peter Maydell
  1 sibling, 2 replies; 6+ messages in thread
From: Philippe Mathieu-Daudé @ 2023-07-17 21:35 UTC (permalink / raw)
  To: qemu-devel
  Cc: Philippe Mathieu-Daudé, Jiaxun Yang, Aleksandar Rikalo,
	Aurelien Jarno, Peter Maydell

Coverity points out that in page_table_walk_refill() we can shift by
a negative number, which is undefined behaviour (CID 1452918,
1452920, 1452922).  We already catch the negative directory_shift and
leaf_shift as being a "bail out early" case, but not until we've
already used them to calculated some offset values.

Move the calculation of the offset values to after we've done the
"return early if ptew > 1" check.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
[PMD: Check for ptew > 1, use unsigned type]
Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
---
 target/mips/tcg/sysemu/tlb_helper.c | 32 +++++++++++++++--------------
 1 file changed, 17 insertions(+), 15 deletions(-)

diff --git a/target/mips/tcg/sysemu/tlb_helper.c b/target/mips/tcg/sysemu/tlb_helper.c
index e7be649b02..7dbc2e24c4 100644
--- a/target/mips/tcg/sysemu/tlb_helper.c
+++ b/target/mips/tcg/sysemu/tlb_helper.c
@@ -624,7 +624,7 @@ static uint64_t get_tlb_entry_layout(CPUMIPSState *env, uint64_t entry,
 static int walk_directory(CPUMIPSState *env, uint64_t *vaddr,
         int directory_index, bool *huge_page, bool *hgpg_directory_hit,
         uint64_t *pw_entrylo0, uint64_t *pw_entrylo1,
-        int directory_shift, int leaf_shift)
+        unsigned directory_shift, unsigned leaf_shift)
 {
     int dph = (env->CP0_PWCtl >> CP0PC_DPH) & 0x1;
     int psn = (env->CP0_PWCtl >> CP0PC_PSN) & 0x3F;
@@ -730,21 +730,11 @@ static bool page_table_walk_refill(CPUMIPSState *env, vaddr address,
 
     /* Other HTW configs */
     int hugepg = (env->CP0_PWCtl >> CP0PC_HUGEPG) & 0x1;
-
-    /* HTW Shift values (depend on entry size) */
-    int directory_shift = (ptew > 1) ? -1 :
-            (hugepg && (ptew == 1)) ? native_shift + 1 : native_shift;
-    int leaf_shift = (ptew > 1) ? -1 :
-            (ptew == 1) ? native_shift + 1 : native_shift;
+    unsigned directory_shift, leaf_shift;
 
     /* Offsets into tables */
-    int goffset = gindex << directory_shift;
-    int uoffset = uindex << directory_shift;
-    int moffset = mindex << directory_shift;
-    int ptoffset0 = (ptindex >> 1) << (leaf_shift + 1);
-    int ptoffset1 = ptoffset0 | (1 << (leaf_shift));
-
-    uint32_t leafentry_size = 1 << (leaf_shift + 3);
+    unsigned goffset, uoffset, moffset, ptoffset0, ptoffset1;
+    uint32_t leafentry_size;
 
     /* Starting address - Page Table Base */
     uint64_t vaddr = env->CP0_PWBase;
@@ -766,10 +756,22 @@ static bool page_table_walk_refill(CPUMIPSState *env, vaddr address,
         /* no structure to walk */
         return false;
     }
-    if ((directory_shift == -1) || (leaf_shift == -1)) {
+    if (ptew > 1) {
         return false;
     }
 
+    /* HTW Shift values (depend on entry size) */
+    directory_shift = (hugepg && (ptew == 1)) ? native_shift + 1 : native_shift;
+    leaf_shift = (ptew == 1) ? native_shift + 1 : native_shift;
+
+    goffset = gindex << directory_shift;
+    uoffset = uindex << directory_shift;
+    moffset = mindex << directory_shift;
+    ptoffset0 = (ptindex >> 1) << (leaf_shift + 1);
+    ptoffset1 = ptoffset0 | (1 << (leaf_shift));
+
+    leafentry_size = 1 << (leaf_shift + 3);
+
     /* Global Directory */
     if (gdw > 0) {
         vaddr |= goffset;
-- 
2.38.1



^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill()
  2023-07-17 21:35 ` [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
@ 2023-07-18  5:59   ` Philippe Mathieu-Daudé
  2023-07-18 10:25   ` Peter Maydell
  1 sibling, 0 replies; 6+ messages in thread
From: Philippe Mathieu-Daudé @ 2023-07-18  5:59 UTC (permalink / raw)
  To: qemu-devel; +Cc: Jiaxun Yang, Aleksandar Rikalo, Aurelien Jarno, Peter Maydell

On 17/7/23 23:35, Philippe Mathieu-Daudé wrote:

Oops, invalid authorship, this should be:

From: Peter Maydell <peter.maydell@linaro.org>

> Coverity points out that in page_table_walk_refill() we can shift by
> a negative number, which is undefined behaviour (CID 1452918,
> 1452920, 1452922).  We already catch the negative directory_shift and
> leaf_shift as being a "bail out early" case, but not until we've
> already used them to calculated some offset values.
> 
> Move the calculation of the offset values to after we've done the
> "return early if ptew > 1" check.
> 
> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
> [PMD: Check for ptew > 1, use unsigned type]
> Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
> ---
>   target/mips/tcg/sysemu/tlb_helper.c | 32 +++++++++++++++--------------
>   1 file changed, 17 insertions(+), 15 deletions(-)



^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH for-8.1 v2 1/2] target/mips: Pass directory/leaf shift values to walk_directory()
  2023-07-17 21:35 ` [PATCH for-8.1 v2 1/2] target/mips: Pass directory/leaf shift values to walk_directory() Philippe Mathieu-Daudé
@ 2023-07-18 10:20   ` Peter Maydell
  0 siblings, 0 replies; 6+ messages in thread
From: Peter Maydell @ 2023-07-18 10:20 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé
  Cc: qemu-devel, Jiaxun Yang, Aleksandar Rikalo, Aurelien Jarno

On Mon, 17 Jul 2023 at 22:36, Philippe Mathieu-Daudé <philmd@linaro.org> wrote:
>
> We already evaluated directory_shift and leaf_shift in
> page_table_walk_refill(), no need to do that again: pass
> as argument.
>
> Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
> ---
>  target/mips/tcg/sysemu/tlb_helper.c | 18 ++++++++----------

Yeah, this is definitely better.

Reviewed-by: Peter Maydell <peter.maydell@linaro.org>

thanks
-- PMM


^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill()
  2023-07-17 21:35 ` [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
  2023-07-18  5:59   ` Philippe Mathieu-Daudé
@ 2023-07-18 10:25   ` Peter Maydell
  1 sibling, 0 replies; 6+ messages in thread
From: Peter Maydell @ 2023-07-18 10:25 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé
  Cc: qemu-devel, Jiaxun Yang, Aleksandar Rikalo, Aurelien Jarno

On Mon, 17 Jul 2023 at 22:35, Philippe Mathieu-Daudé <philmd@linaro.org> wrote:
>
> Coverity points out that in page_table_walk_refill() we can shift by
> a negative number, which is undefined behaviour (CID 1452918,
> 1452920, 1452922).  We already catch the negative directory_shift and
> leaf_shift as being a "bail out early" case, but not until we've
> already used them to calculated some offset values.
>
> Move the calculation of the offset values to after we've done the
> "return early if ptew > 1" check.
>
> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
> [PMD: Check for ptew > 1, use unsigned type]
> Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>

I think I would expand the commit message a bit, so instead
of the current paragraph 2, something like:

The shifts can be negative only if ptew > 1, so make the
bail-out-early check look directly at that, and only
calculate the shift amounts and the offsets based on them
after we have done that check. This allows
us to simplify the expressions used to calculate the
shift amounts, use an unsigned type, and avoids the
undefined behaviour.


?

Anyway

Reviewed-by: Peter Maydell <peter.maydell@linaro.org>

thanks
-- PMM


^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2023-07-18 10:26 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2023-07-17 21:35 [PATCH for-8.1 v2 0/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
2023-07-17 21:35 ` [PATCH for-8.1 v2 1/2] target/mips: Pass directory/leaf shift values to walk_directory() Philippe Mathieu-Daudé
2023-07-18 10:20   ` Peter Maydell
2023-07-17 21:35 ` [PATCH for-8.1 v2 2/2] target/mips: Avoid shift by negative number in page_table_walk_refill() Philippe Mathieu-Daudé
2023-07-18  5:59   ` Philippe Mathieu-Daudé
2023-07-18 10:25   ` Peter Maydell

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).