Skip to content

Commit 5077f20

Browse files
committed
Don't panic on malformed format specifiers.
When a malformed format secifier is encountered, treat the entire string as not having format specifiers.
1 parent 42f6f0c commit 5077f20

1 file changed

Lines changed: 5 additions & 2 deletions

File tree

source/gettext.d

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -409,16 +409,19 @@ version (xgettext) // String extraction mode.
409409
import std.format : FormatSpec;
410410
import std.exception : ifThrown;
411411

412-
static void ns(const(char)[] arr) {} // the simplest output range
412+
static void ns(const(char)[]) {} // the simplest output range
413413
auto nullSink = &ns;
414-
return FormatSpec!char(fmt).writeUpToNextSpec(nullSink).ifThrown!FormatException(false);
414+
// Only catching FormatException is not enough. Checking "0%." causes an array bounds violation
415+
// in std\format\spec.d(461,29), so we need to catch all errors; which is not @safe in general.
416+
return (() @trusted => FormatSpec!char(fmt).writeUpToNextSpec(nullSink).ifThrown!Throwable(false))();
415417
}
416418
unittest
417419
{
418420
assert ("On %2$s I eat %3$s and walk for %1$d hours.".hasFormatSpecifiers);
419421
assert ("On %%2$s I eat %%3$s and walk for %1$d hours.".hasFormatSpecifiers);
420422
assert (!"On %%2$s I eat %%3$s and walk for hours.".hasFormatSpecifiers);
421423
assert (!"98%".hasFormatSpecifiers);
424+
assert (!"0%.".hasFormatSpecifiers);
422425
}
423426
}
424427
else // Translation mode.

0 commit comments

Comments
 (0)