[fpc-pascal] Header translation, argument list, array of const?

Sven Barth pascaldragon at googlemail.com
Sat Jun 30 12:06:38 CEST 2012


Am 30.06.2012 03:25 schrieb "kyan" <alfasud.ti at gmail.com>:
> A pascal open array of const which is the closest concept to a C
> ellipsis may have similar semantics but its binary representation on
> the parameter stack is completely different. First of all, since it
> has to work in all calling conventions and not just cdecl the high
> bound of passed array elements is pushed in the stack after a pointer
> to an array of TVarRec structures that each contains a type attribute
> and either a value or a pointer to the value of the parameter. So the
> open array doesn't need to be the last parameter like the C ellipsis
> and there can be more than one in a routine signature. So your
> declaration of purple_prpl_got_user_status
>
> procedure purple_prpl_got_user_status(account: PPurpleAccount;
>   name_, status_id: PChar;
>   par3: array of const);
>
> is equivalent to:
>
> procedure purple_prpl_got_user_status(account: PPurpleAccount;
>   name_, status_id: PChar;
>   par3: PVarRecArray; par3HighBound: Integer);
>
> So the caller pushes only a pointer to a TVarRec array and an integer
> while the function expects a continuous "stream" of parameters. If you
> pass [] the compiler generates code to push a nil pointer (zero
> PtrInt) and a high bound of -1. If the C function can handle these
> values on the stack it *sort of* works by accident, but it will
> probably fail if it tries to read past the -1 high bound for a
> specific value of status_id that requires more variable parameters.

Your explanation is very nice and mostly correct, but in case of external
cdecl functions in FPC the "varargs" modifier and a "array of const"
parameter imply the same C compatible parameter passing in the compiler.
See also here:
http://freepascal.org/docs-html/ref/refsu77.html#x180-19000014.9.17

The only difference is when calling the functions. E.g.:

procedure a(args: array of const); cdecl; external;
procedure b; cdecl; varargs; external;

begin
  a([1, 'foo', somevar]);
  b(1, 'foo', somevar);
end.

Regards,
Sven
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.freepascal.org/pipermail/fpc-pascal/attachments/20120630/b5af9287/attachment.html>


More information about the fpc-pascal mailing list