Start padding and alternate forms for integers

This commit is contained in:
apio 2022-11-19 13:59:06 +01:00
parent c48203997a
commit 88af7a915b

View File

@ -200,7 +200,7 @@ static bool is_integer_format_specifier(char c)
return (c == 'd') || (c == 'i') || (c == 'u') || (c == 'x') || (c == 'X') || (c == 'o') || (c == 'b');
}
template <typename T> static usize to_string(T value, T base, char* buf, usize max, bool uppercase)
static usize to_string(usize value, usize base, char* buf, usize max, bool uppercase)
{
usize i = 0;
if (!value && max)
@ -217,8 +217,7 @@ template <typename T> static usize to_string(T value, T base, char* buf, usize m
return i;
}
template <typename T>
static int output_integer(char specifier, const conv_state& vstate, format_state& state, T value, bool negative)
static int output_integer(char specifier, conv_state& vstate, format_state& state, usize value, bool negative)
{
usize base = 10;
bool uppercase = false;
@ -233,10 +232,37 @@ static int output_integer(char specifier, const conv_state& vstate, format_state
}
if (specifier == 'X') uppercase = true;
char buf[1024];
usize buflen = to_string(value, (T)base, buf, sizeof(buf), uppercase);
if (base == 10) vstate.flags &= ~FLAG_ALTERNATE; // decimal doesn't have an alternate form
// FIXME: Start padding and alternate forms.
char buf[1024];
usize buflen = to_string(value, base, buf, sizeof(buf), uppercase);
if (!(vstate.flags & FLAG_LEFT_ALIGN) &&
(vstate.flags & FLAG_ZERO_PAD)) // we're padding with zeroes from the beginning
{
bool extra_char =
negative || ((vstate.flags & FLAG_SIGN) ||
(vstate.flags & FLAG_BLANK_SIGNED)); // are we adding an extra character after the buffer?
if (vstate.width && extra_char) vstate.width--;
if (vstate.width && (vstate.flags & FLAG_ALTERNATE)) // fit in the characters we're using for the alternate form
{
vstate.width--;
if (vstate.width && (base == 2 || base == 16)) vstate.width--;
}
while (buflen < vstate.width && buflen < sizeof(buf)) buf[buflen++] = '0';
}
while (buflen < vstate.precision && buflen < sizeof(buf)) buf[buflen++] = '0';
if (vstate.flags & FLAG_ALTERNATE)
{
if (base == 16 && !uppercase && buflen < sizeof(buf)) buf[buflen++] = 'x';
if (base == 16 && uppercase && buflen < sizeof(buf)) buf[buflen++] = 'X';
if (base == 2 && buflen < sizeof(buf)) buf[buflen++] = 'b';
if (buflen < sizeof(buf)) buf[buflen++] = '0';
}
if (buflen < sizeof(buf))
{
@ -247,6 +273,8 @@ static int output_integer(char specifier, const conv_state& vstate, format_state
buf[buflen++] = ' ';
}
if (!(vstate.flags & FLAG_ZERO_PAD)) TRY_START_PAD(vstate, state, buflen);
usize i = buflen;
while (i--) TRY_PUTCHAR(buf[i], state);
@ -256,7 +284,7 @@ static int output_integer(char specifier, const conv_state& vstate, format_state
return 0;
}
static int va_output_integer(char specifier, const conv_state& vstate, format_state& state, va_list ap)
static int va_output_integer(char specifier, conv_state& vstate, format_state& state, va_list ap)
{
bool is_signed = false;
bool negative = false;