On 24/01/2019 12:07, Norbert Manthey wrote:
> On 1/23/19 14:20, Jan Beulich wrote:
>>>>> On 23.01.19 at 12:51, <nmant...@amazon.de> wrote:
>>> --- a/xen/include/xen/nospec.h
>>> +++ b/xen/include/xen/nospec.h
>>> @@ -58,6 +58,21 @@ static inline unsigned long 
>>> array_index_mask_nospec(unsigned long index,
>>>      (typeof(_i)) (_i & _mask);                                          \
>>>  })
>>>  
>>> +/*
>>> + * allow to insert a read memory barrier into conditionals
>>> + */
>>> +#ifdef CONFIG_X86
>>> +static inline bool lfence_true(void) { rmb(); return true; }
>>> +#else
>>> +static inline bool lfence_true(void) { return true; }
>>> +#endif
>>> +
>>> +/*
>>> + * protect evaluation of conditional with respect to speculation
>>> + */
>>> +#define evaluate_nospec(condition)                                      \
>>> +    (((condition) && lfence_true()) || !lfence_true())
>> It may be just me, but I think
>>
>> #define evaluate_nospec(condition)                                      \
>>     ((condition) ? lfence_true() : !lfence_true())
>>
>> would better express the two-way nature of this.
> I compared the binary output of the two variants, and they are the same
> (for my build environment). I'll switch to your variant, in case nobody
> objects.

Is it safe though?  The original variant is required by C to only
evaluate one of the lfence_true() blocks, whereas the second variation
could execute both of them and cmov the 1 and 0 together, which is wasteful.

~Andrew

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xenproject.org
https://lists.xenproject.org/mailman/listinfo/xen-devel

Reply via email to