Hi, 

Thanks for the information. 

Yes, providing a unary operator similar as __counted_by(PTR) as suggested by 
multiple people previously is a cleaner approach. 

Then the programmer will use the following:

 __builtin_choose_expr(
     __builtin_has_attribute (__p->FAM, "counted_by”) 
         __builtin_get_counted_by(__p->FAM) = COUNT, 0);

From the programmer’s point of view, it’s cleaner too.

However, there is one issue with “__builtin_choose_expr” currently in GCC, its 
documentation explicitly mentions this limitation:  
(https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html#index-_005f_005fbuiltin_005fchoose_005fexpr)

"Note: This construct is only available for C. Furthermore, the unused 
expression (exp1 or exp2 depending on the value of const_exp) may still 
generate syntax errors. This may change in future revisions.”

So, due to this limitation, when there is no counted_by attribute, the 
__builtin_get_counted_by() still is evaluated by the compiler and errors is 
issued and the compilation stops, this can be show from the small testing case:

[opc@qinzhao-ol8u3-x86 gcc]$ cat ttt.c

struct flex {
  unsigned int b;
  int c[];
} *array_flex;

#define MY_ALLOC(P, FAM, COUNT) ({ \
  typeof(P) __p; \
  unsigned int __size = sizeof(*P) + sizeof(*P->FAM) * COUNT; \
  __p = (typeof(P)) __builtin_malloc(__size); \
  __builtin_choose_expr( \
    __builtin_has_attribute (__p->FAM, counted_by), \
    __builtin_counted_by_ref(__p->FAM) = COUNT, 0); \
  P = __p; \
})

int main(int argc, char *argv[])
{
  MY_ALLOC(array_flex, c, 20);
  return 0;
}
[opc@qinzhao-ol8u3-x86 gcc]$ sh t
ttt.c: In function ‘main’:
ttt.c:13:5: error: the argument must have ‘counted_by’ attribute 
‘__builtin_counted_by_ref’
ttt.c:19:3: note: in expansion of macro ‘MY_ALLOC’

I checked the FE code on handling “__buiiltin_choose_expr”, Yes, it does parse 
the __builtin_counted_by_ref(__p->FAM) even when 
__builtin_has_attribute(__p->FAM, counted_by) is FALSE, and issued the error 
when parsing __builtin_counted_by_ref and stopped the compilation. 

So, in order to support this approach, we first must fix the issue in the 
current __builtin_choose_expr in GCC. Otherwise, it’s impossible for the user 
to use this new builtin. 

Let me know your comments and suggestions.

thanks.

Qing


> On Aug 27, 2024, at 14:46, Bill Wendling <isanb...@gmail.com> wrote:
>>> 
>>> It would make it easier for your use case.  I wonder though
>>> whether other people might want to have the compile time error
>>> when there is no attribute.
>> 
>> Then this will go back to the previous discussion: whether we should go the 
>> approach  for the unary operator __counted_by(PTR), then the other builtin 
>> __builtin_has_attribute(PTR, counted_by) should be provided to the user.
>> 
>> For GCC, there is no issue, we already have the __builtin_has_attribute 
>> (PTR, counted_by) available.
>> But CLANG doesn’t have this builtin currently, need to implement it before 
>> the unary operator __counted_by(PTR).
>> 
>> Let me know your opinion.
> 
> We have a bit of an issue with the current design. The group at Apple,
> who are implementing a lot of the bounds safety checks need to prevent
> the address of the 'count' from being taken. See [1] for details, but
> the upshot is that they try to ensure that the 'count' and flexible
> array member aren't modified independently. The discussion is ongoing,
> but they suggested an alternative that is similar to ones discussed in
> this thread and the bugzilla.
> 
> A brief description of their proposal is adding the builtin
> '__builtin_bounds_attr_arg'. It would take counted_by's argument and
> return the counter directly:
> 
>  __builtin_choose_expr(
>      __builtin_has_attribute(__p->FAM, "counted_by"),
>          __builtin_bounds_attr_arg(__p->FAM) = COUNT,
>          (void)
>  );
> 
> This is similar to one of the original proposals for
> __builtin_get_counted_by, but we changed because Clang didn't have
> __builtin_has_attribute. Clang should implement
> __builtin_has_attribute regardless, and if this is a better way of
> doing things, and doesn't interfere with Apple's work, then I can add
> __builtin_has_attribute to Clang so that we "do the right thing."
> 
> As I said though, the discussion is ongoing at [1], but just wanted to
> give everyone a warning, and feel free to jump in with comments /
> suggestions.
> 
> [1] 
> https://discourse.llvm.org/t/rfc-introducing-new-clang-builtin-builtin-get-counted-by/80836
> 
> -bw


Reply via email to