Re: Expanding the use of FLEXIBLE_ARRAY_MEMBER for declarations like foo[1] - Mailing list pgsql-hackers

From Tom Lane
Subject Re: Expanding the use of FLEXIBLE_ARRAY_MEMBER for declarations like foo[1]
Date
Msg-id 31479.1424325485@sss.pgh.pa.us
Whole thread Raw
In response to Re: Expanding the use of FLEXIBLE_ARRAY_MEMBER for declarations like foo[1]  (Michael Paquier <michael.paquier@gmail.com>)
Responses Re: Expanding the use of FLEXIBLE_ARRAY_MEMBER for declarations like foo[1]  (Michael Paquier <michael.paquier@gmail.com>)
List pgsql-hackers
Michael Paquier <michael.paquier@gmail.com> writes:
> 1-2) sizeof(ParamListInfoData) is present in a couple of places,
> assuming that sizeof(ParamListInfoData) has the equivalent of 1
> parameter, like prepare.c, functions.c, spi.c and postgres.c:
> -       /* sizeof(ParamListInfoData) includes the first array element */
>         paramLI = (ParamListInfo)
>                 palloc(sizeof(ParamListInfoData) +
> -                          (num_params - 1) * sizeof(ParamExternData));
> +                          num_params * sizeof(ParamExternData));
> 1-3) FuncCandidateList in namespace.c (thanks Andres!):
>                 newResult = (FuncCandidateList)
> -                       palloc(sizeof(struct _FuncCandidateList) - sizeof(Oid)
> -                                  + effective_nargs * sizeof(Oid));
> +                       palloc(sizeof(struct _FuncCandidateList) +
> +                                  effective_nargs * sizeof(Oid));
> I imagine that we do not want for those palloc calls to use ifdef
> FLEXIBLE_ARRAY_MEMBER to save some memory for code readability even if
> compiler does not support flexible-array length, right?

These are just wrong.  As a general rule, we do not want to *ever* take
sizeof() a struct that contains a flexible array: the results will not
be consistent across platforms.  The right thing is to use offsetof()
instead.  See the helpful comment autoconf provides:

/* Define to nothing if C supports flexible array members, and to 1 if it does  not. That way, with a declaration like
`structs { int n; double  d[FLEXIBLE_ARRAY_MEMBER]; };', the struct hack can be used with pre-C99  compilers. When
computingthe size of such an object, don't use 'sizeof  (struct s)' as it overestimates the size. Use 'offsetof (struct
s,d)'  instead. Don't use 'offsetof (struct s, d[0])', as this doesn't work with  MSVC and with C++ compilers. */
 
#define FLEXIBLE_ARRAY_MEMBER /**/

This point is actually the main reason we've not done this change long
since.  People did not feel like running around to make sure there were
no overlooked uses of sizeof().
        regards, tom lane



pgsql-hackers by date:

Previous
From: Michael Paquier
Date:
Subject: Re: Expanding the use of FLEXIBLE_ARRAY_MEMBER for declarations like foo[1]
Next
From: Naoya Anzai
Date:
Subject: Re: Table-level log_autovacuum_min_duration