qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [PATCH v2] target/arm: Merge arm_cpu_vq_map_next_smaller into sole c


From: Richard Henderson
Subject: Re: [PATCH v2] target/arm: Merge arm_cpu_vq_map_next_smaller into sole caller
Date: Mon, 18 Nov 2019 09:27:36 +0100
User-agent: Mozilla/5.0 (X11; Linux x86_64; rv:60.0) Gecko/20100101 Thunderbird/60.9.0

On 11/18/19 8:58 AM, Andrew Jones wrote:
> On Sat, Nov 16, 2019 at 12:06:42PM +0100, Richard Henderson wrote:
>> Coverity reports, in sve_zcr_get_valid_len,
>>
>> "Subtract operation overflows on operands
>> arm_cpu_vq_map_next_smaller(cpu, start_vq + 1U) and 1U"
>>
>> First, the aarch32 stub version of arm_cpu_vq_map_next_smaller,
>> returning 0, does exactly what Coverity reports.  Remove it.
>>
>> Second, the aarch64 version of arm_cpu_vq_map_next_smaller has
>> a set of asserts, but they don't cover the case in question.
>> Further, there is a fair amount of extra arithmetic needed to
>> convert from the 0-based zcr register, to the 1-base vq form,
>> to the 0-based bitmap, and back again.  This can be simplified
>> by leaving the value in the 0-based form.
>>
>> Finally, use test_bit to simplify the common case, where the
>> length in the zcr registers is in fact a supported length.
> 
> I don't see test_bit() getting used in the changes below.

Argh!  It's still uncommitted here in my tree.
I guess I forgot the -a on the git commit --append?

V3 coming up...


r~

> 
>>
>> Reported-by: Coverity (CID 1407217)
>> Signed-off-by: Richard Henderson <address@hidden>
>> ---
>>
>> v2: Merge arm_cpu_vq_map_next_smaller into sve_zcr_get_valid_len,
>>     as suggested by Andrew Jones.
>>
>>     Use test_bit to make the code even more obvious; the
>>     current_length + 1 thing to let us find current_length in the
>>     bitmap seemed unnecessarily clever.
>>
>> ---
>>  target/arm/cpu.h    |  3 ---
>>  target/arm/cpu64.c  | 15 ---------------
>>  target/arm/helper.c |  8 ++++++--
>>  3 files changed, 6 insertions(+), 20 deletions(-)
>>
>> diff --git a/target/arm/cpu.h b/target/arm/cpu.h
>> index e1a66a2d1c..47d24a5375 100644
>> --- a/target/arm/cpu.h
>> +++ b/target/arm/cpu.h
>> @@ -185,12 +185,9 @@ typedef struct {
>>  #ifdef TARGET_AARCH64
>>  # define ARM_MAX_VQ    16
>>  void arm_cpu_sve_finalize(ARMCPU *cpu, Error **errp);
>> -uint32_t arm_cpu_vq_map_next_smaller(ARMCPU *cpu, uint32_t vq);
>>  #else
>>  # define ARM_MAX_VQ    1
>>  static inline void arm_cpu_sve_finalize(ARMCPU *cpu, Error **errp) { }
>> -static inline uint32_t arm_cpu_vq_map_next_smaller(ARMCPU *cpu, uint32_t vq)
>> -{ return 0; }
>>  #endif
>>  
>>  typedef struct ARMVectorReg {
>> diff --git a/target/arm/cpu64.c b/target/arm/cpu64.c
>> index 68baf0482f..a39d6fcea3 100644
>> --- a/target/arm/cpu64.c
>> +++ b/target/arm/cpu64.c
>> @@ -458,21 +458,6 @@ void arm_cpu_sve_finalize(ARMCPU *cpu, Error **errp)
>>      cpu->sve_max_vq = max_vq;
>>  }
>>  
>> -uint32_t arm_cpu_vq_map_next_smaller(ARMCPU *cpu, uint32_t vq)
>> -{
>> -    uint32_t bitnum;
>> -
>> -    /*
>> -     * We allow vq == ARM_MAX_VQ + 1 to be input because the caller may want
>> -     * to find the maximum vq enabled, which may be ARM_MAX_VQ, but this
>> -     * function always returns the next smaller than the input.
>> -     */
>> -    assert(vq && vq <= ARM_MAX_VQ + 1);
>> -
>> -    bitnum = find_last_bit(cpu->sve_vq_map, vq - 1);
>> -    return bitnum == vq - 1 ? 0 : bitnum + 1;
>> -}
>> -
>>  static void cpu_max_get_sve_max_vq(Object *obj, Visitor *v, const char 
>> *name,
>>                                     void *opaque, Error **errp)
>>  {
>> diff --git a/target/arm/helper.c b/target/arm/helper.c
>> index be67e2c66d..b5ee35a174 100644
>> --- a/target/arm/helper.c
>> +++ b/target/arm/helper.c
>> @@ -5363,9 +5363,13 @@ int sve_exception_el(CPUARMState *env, int el)
>>  
>>  static uint32_t sve_zcr_get_valid_len(ARMCPU *cpu, uint32_t start_len)
>>  {
>> -    uint32_t start_vq = (start_len & 0xf) + 1;
>> +    uint32_t end_len;
>>  
>> -    return arm_cpu_vq_map_next_smaller(cpu, start_vq + 1) - 1;
>> +    start_len &= 0xf;
>> +    end_len = find_last_bit(cpu->sve_vq_map, start_len + 1);
>> +
>> +    assert(end_len <= start_len);
>> +    return end_len;
>>  }
>>  
>>  /*
>> -- 
>> 2.17.1
>>
>>
> 
> Besides the commit message referencing test_bit, but no use of it, this
> looks good to me
> 
> Reviewed-by: Andrew Jones <address@hidden>
> 




reply via email to

[Prev in Thread] Current Thread [Next in Thread]