writef, compile-checked format, pointer
Ali Çehreli
acehreli at yahoo.com
Mon Aug 9 22:30:43 UTC 2021
On 8/9/21 3:01 PM, Patrick Schluter wrote:
> On Monday, 9 August 2021 at 19:38:28 UTC, novice2 wrote:
>> format!"fmt"() and writef!"fmt"() templates
>> with compile-time checked format string
>> not accept %X for pointers,
>>
>> but format() and writef() accept it
>>
>> https://run.dlang.io/is/aQ05Ux
>> ```
>> void main() {
>> import std.stdio: writefln;
>> int x;
>> writefln("%X", &x); //ok
>> writefln!"%s"(&x); //ok
>> //writefln!"%X"(&x); //compile error
>> }
>> ```
>>
>> is this intentional?
>
> Yes. %X is to format integers. Runtime evaluation of a format string
> does not allow for type checking. When using the template, the
> evaluation can be thorough and the types can be checked properly.
Sensible explanation but it conflicts both with the documentation at
https://dlang.org/phobos/std_format.html
and the error message for the following:
// Intentionally wrong specifier:
writefln!"%_"((int*).init);
Error: expression `FormatException("Expected one of %s, %x or %X for
pointer type.", "/usr/include/dmd/phobos/std/format/internal/write.d",
2990LU, null, null, 0u)` is not constant
Both the documentation and the error message suggest %x and %X.
> You
> have 2 solutions for your problem, either a type cast
>
> writefln!"%X"(cast(size_t)&x);
>
> or using the generic format specifier that will deduce itself the format
> to using depending in the passed type.
>
> writefln!"%s"(&x);
That would be my choice but I've just learned that %s prints the null
value as "null" instead of hex 0, which may be undesirable in some cases.
I think there really is a bug here.
I've been hitting a similar bug with some complex range expressions
where compile-time checked format strings would not work. I don't know
the reason but I suspect a bug in the compile-time checker that involves
.init values for arguments. I assume the checker uses .init values to
see whether the format expression compiles and works. In fact, the
mention of 'null' in the OP's error message makes me think it may be
related. Perhaps the un-typed 'null' literal is used somewhere. (?)
Ali
More information about the Digitalmars-d-learn
mailing list