Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8af1da40 authored by Mathieu Malaterre's avatar Mathieu Malaterre Committed by Michael Ellerman
Browse files

powerpc/prom: Fix %u/%llx usage since prom_printf() change



In commit eae5f709 ("powerpc: Add __printf verification to
prom_printf") __printf attribute was added to prom_printf(), which
means GCC started warning about type/format mismatches. As part of
that commit we changed some "%lx" formats to "%llx" where the type is
actually unsigned long long.

Unfortunately prom_printf() doesn't know how to print "%llx", it just
prints a literal "lx", eg:

  reserved memory map:
    lx - lx
    lx - lx

prom_printf() also doesn't know how to print "%u" (only "%lu"), it
just prints a literal "u", eg:

  Max number of cores passed to firmware: u (NR_CPUS = 2048)

Instead of:

  Max number of cores passed to firmware: 2048 (NR_CPUS = 2048)

This commit adds support for the missing formatters.

Fixes: eae5f709 ("powerpc: Add __printf verification to prom_printf")
Reported-by: default avatarMichael Ellerman <mpe@ellerman.id.au>
Reported-by: default avatarStephen Rothwell <sfr@canb.auug.org.au>
Signed-off-by: default avatarMathieu Malaterre <malat@debian.org>
Tested-by: default avatarMichael Ellerman <mpe@ellerman.id.au>
Signed-off-by: default avatarMichael Ellerman <mpe@ellerman.id.au>
parent 9a6d2022
Loading
Loading
Loading
Loading
+49 −24
Original line number Diff line number Diff line
@@ -301,6 +301,10 @@ static void __init prom_print(const char *msg)
}


/*
 * Both prom_print_hex & prom_print_dec takes an unsigned long as input so that
 * we do not need __udivdi3 or __umoddi3 on 32bits.
 */
static void __init prom_print_hex(unsigned long val)
{
	int i, nibbles = sizeof(val)*2;
@@ -341,6 +345,7 @@ static void __init prom_printf(const char *format, ...)
	va_list args;
	unsigned long v;
	long vs;
	int n = 0;

	va_start(args, format);
	for (p = format; *p != 0; p = q) {
@@ -359,6 +364,10 @@ static void __init prom_printf(const char *format, ...)
		++q;
		if (*q == 0)
			break;
		while (*q == 'l') {
			++q;
			++n;
		}
		switch (*q) {
		case 's':
			++q;
@@ -367,39 +376,55 @@ static void __init prom_printf(const char *format, ...)
			break;
		case 'x':
			++q;
			switch (n) {
			case 0:
				v = va_arg(args, unsigned int);
				break;
			case 1:
				v = va_arg(args, unsigned long);
			prom_print_hex(v);
				break;
		case 'd':
			++q;
			vs = va_arg(args, int);
			if (vs < 0) {
				prom_print("-");
				vs = -vs;
			case 2:
			default:
				v = va_arg(args, unsigned long long);
				break;
			}
			prom_print_dec(vs);
			prom_print_hex(v);
			break;
		case 'l':
		case 'u':
			++q;
			if (*q == 0)
			switch (n) {
			case 0:
				v = va_arg(args, unsigned int);
				break;
			else if (*q == 'x') {
				++q;
				v = va_arg(args, unsigned long);
				prom_print_hex(v);
			} else if (*q == 'u') { /* '%lu' */
				++q;
			case 1:
				v = va_arg(args, unsigned long);
				break;
			case 2:
			default:
				v = va_arg(args, unsigned long long);
				break;
			}
			prom_print_dec(v);
			} else if (*q == 'd') { /* %ld */
			break;
		case 'd':
			++q;
			switch (n) {
			case 0:
				vs = va_arg(args, int);
				break;
			case 1:
				vs = va_arg(args, long);
				break;
			case 2:
			default:
				vs = va_arg(args, long long);
				break;
			}
			if (vs < 0) {
				prom_print("-");
				vs = -vs;
			}
			prom_print_dec(vs);
			}
			break;
		}
	}