libc: attribute minimal libc printf style functions with __printf_like

Add __printf_like attribute to printf style functions in minimal libc to
enable the compiler checking this provides.  We fixup the associated
issues that are now found by utilizing these checks.

Change-Id: I74ac0d0345782463d9fb454f7161d6b4af211ba5
Signed-off-by: Kumar Gala <kumar.gala@linaro.org>
This commit is contained in:
Kumar Gala 2017-02-27 14:50:45 -06:00
commit 91e9f87499
20 changed files with 70 additions and 96 deletions

View file

@ -9,6 +9,7 @@
#ifndef __INC_stdio_h__
#define __INC_stdio_h__
#include <toolchain.h>
#include <stdarg.h> /* Needed to get definition of va_list */
#include <bits/restrict.h>
#include <stddef.h>
@ -35,21 +36,24 @@ typedef int FILE;
* declared below.
*/
int printf(const char *_MLIBC_RESTRICT fmt, ...);
int snprintf(char *_MLIBC_RESTRICT s, size_t len,
const char *_MLIBC_RESTRICT fmt, ...);
int sprintf(char *_MLIBC_RESTRICT s, const char *_MLIBC_RESTRICT fmt, ...);
int fprintf(FILE *_MLIBC_RESTRICT stream,
const char *_MLIBC_RESTRICT format, ...);
int __printf_like(1, 2) printf(const char *_MLIBC_RESTRICT fmt, ...);
int __printf_like(3, 4) snprintf(char *_MLIBC_RESTRICT s, size_t len,
const char *_MLIBC_RESTRICT fmt, ...);
int __printf_like(2, 3) sprintf(char *_MLIBC_RESTRICT s,
const char *_MLIBC_RESTRICT fmt, ...);
int __printf_like(2, 3) fprintf(FILE * _MLIBC_RESTRICT stream,
const char *_MLIBC_RESTRICT format, ...);
int vprintf(const char *_MLIBC_RESTRICT fmt, va_list list);
int vsnprintf(char *_MLIBC_RESTRICT s, size_t len,
const char *_MLIBC_RESTRICT fmt, va_list list);
int vsprintf(char *_MLIBC_RESTRICT s,
const char *_MLIBC_RESTRICT fmt, va_list list);
int vfprintf(FILE *_MLIBC_RESTRICT stream, const char *_MLIBC_RESTRICT format,
va_list ap);
int __printf_like(1, 0) vprintf(const char *_MLIBC_RESTRICT fmt, va_list list);
int __printf_like(3, 0) vsnprintf(char *_MLIBC_RESTRICT s, size_t len,
const char *_MLIBC_RESTRICT fmt,
va_list list);
int __printf_like(2, 0) vsprintf(char *_MLIBC_RESTRICT s,
const char *_MLIBC_RESTRICT fmt, va_list list);
int __printf_like(2, 0) vfprintf(FILE * _MLIBC_RESTRICT stream,
const char *_MLIBC_RESTRICT format,
va_list ap);
int puts(const char *s);

View file

@ -24,21 +24,6 @@ const char sz_success[] = "SUCCESSFUL";
const char sz_partial[] = "PARTIAL";
const char sz_fail[] = "FAILED";
const char sz_module_title_fmt[] = "\nMODULE: %s";
const char sz_module_result_fmt[] = "\n\nPROJECT EXECUTION %s\n";
const char sz_module_end_fmt[] = "\nEND MODULE";
const char sz_date_fmt[] = "\nBUILD_DATE: %s %s";
const char sz_kernel_ver_fmt[] = "\nKERNEL VERSION: 0x%x";
const char sz_description[] = "\nTEST COVERAGE: %s";
const char sz_test_case_fmt[] = "\n\nTEST CASE: %s";
const char sz_test_start_fmt[] = "\nStarting test. Please wait...";
const char sz_case_result_fmt[] = "\nTEST RESULT: %s";
const char sz_case_details_fmt[] = "\nDETAILS: %s";
const char sz_case_end_fmt[] = "\nEND TEST CASE";
const char sz_case_timing_fmt[] = "%ld nSec";
/* time necessary to read the time */
uint32_t tm_off;

View file

@ -26,20 +26,20 @@ extern const char sz_success[];
extern const char sz_partial[];
extern const char sz_fail[];
extern const char sz_module_title_fmt[];
extern const char sz_module_result_fmt[];
extern const char sz_module_end_fmt[];
#define sz_module_title_fmt "\nMODULE: %s"
#define sz_module_result_fmt "\n\nPROJECT EXECUTION %s\n"
#define sz_module_end_fmt "\nEND MODULE"
extern const char sz_product_fmt[];
extern const char sz_kernel_ver_fmt[];
extern const char sz_description[];
#define sz_date_fmt "\nBUILD_DATE: %s %s"
#define sz_kernel_ver_fmt "\nKERNEL VERSION: 0x%x"
#define sz_description "\nTEST COVERAGE: %s"
extern const char sz_test_case_fmt[];
extern const char sz_test_start_fmt[];
extern const char sz_case_result_fmt[];
extern const char sz_case_details_fmt[];
extern const char sz_case_end_fmt[];
extern const char sz_case_timing_fmt[];
#define sz_test_case_fmt "\n\nTEST CASE: %s"
#define sz_test_start_fmt "\nStarting test. Please wait..."
#define sz_case_result_fmt "\nTEST RESULT: %s"
#define sz_case_details_fmt "\nDETAILS: %s"
#define sz_case_end_fmt "\nEND TEST CASE"
#define sz_case_timing_fmt "%u nSec"
int check_result(int i, uint32_t ticks);

View file

@ -229,7 +229,7 @@ int vsnprintfTest(void)
buffer[0] = '\0';
len = tvsnprintf(buffer, 0, "%x", DEADBEEF);
if (len != strlen(DEADBEEF_LHEX_STR)) {
TC_ERROR("vsnprintf(%%x). Expected return value %d, not %d\n",
TC_ERROR("vsnprintf(%%x). Expected return value %d, not %zd\n",
strlen(DEADBEEF_LHEX_STR), len);
status = TC_FAIL;
}
@ -243,7 +243,7 @@ int vsnprintfTest(void)
/*******************/
len = tvsnprintf(buffer, 4, "%x", DEADBEEF);
if (len != strlen(DEADBEEF_LHEX_STR)) {
TC_ERROR("vsnprintf(%%x). Expected return value %d, not %d\n",
TC_ERROR("vsnprintf(%%x). Expected return value %d, not %zd\n",
strlen(DEADBEEF_LHEX_STR), len);
status = TC_FAIL;
}

View file

@ -18,7 +18,7 @@ static struct k_msg Message;
("| size(B) | time/packet (usec) | MB/sec" \
" |\n", output_file);
#define PRINT_ONE_RESULT() \
PRINT_F(output_file, "|%11lu|%32.3f|%32f|\n", putsize, puttime / 1000.0, \
PRINT_F(output_file, "|%11u|%32.3f|%32f|\n", putsize, puttime / 1000.0,\
(1000.0 * putsize) / puttime)
#define PRINT_OVERHEAD() \
@ -40,7 +40,7 @@ static struct k_msg Message;
" |\n", output_file);
#define PRINT_ONE_RESULT() \
PRINT_F(output_file, "|%11lu|%32lu|%32lu|\n", putsize, puttime, \
PRINT_F(output_file, "|%11u|%32u|%32u|\n", putsize, puttime, \
(uint32_t)((1000000 * (uint64_t)putsize) / puttime))
#define PRINT_OVERHEAD() \
@ -49,7 +49,7 @@ static struct k_msg Message;
" |\n", EmptyMsgPutTime)
#define PRINT_XFER_RATE() \
PRINT_F(output_file, "| raw transfer rate: %10lu KB/sec (without" \
PRINT_F(output_file, "| raw transfer rate: %10u KB/sec (without" \
" overhead) |\n", \
(uint32_t)(1000000 * (uint64_t)(putsize >> 1) \
/ (puttime - EmptyMsgPutTime)))

View file

@ -23,9 +23,6 @@ char data_bench[OCTET_TO_SIZEOFUNIT(MESSAGE_SIZE)];
#ifdef PIPE_BENCH
kpipe_t TestPipes[] = {PIPE_NOBUFF, PIPE_SMALLBUFF, PIPE_BIGBUFF};
#endif
const char dashline[] =
"|--------------------------------------"
"---------------------------------------|\n";
char sline[SLINE_LEN + 1];
const char newline[] = "\n";

View file

@ -25,7 +25,7 @@
/* #define FLOAT */
/* printf format defines. */
#define FORMAT "| %-65s|%10lu|\n"
#define FORMAT "| %-65s|%10u|\n"
/* global defines */
/* number of nsec per usec */
@ -51,10 +51,13 @@ extern char Msg[MAX_MSG];
extern char data_bench[OCTET_TO_SIZEOFUNIT(MESSAGE_SIZE)];
extern kpipe_t TestPipes[];
extern FILE * output_file;
extern const char dashline[];
extern const char newline[];
extern char sline[];
#define dashline \
"|--------------------------------------" \
"---------------------------------------|\n"
/* dummy_test is a function that is mapped when we */
/* do not want to test a specific Benchmark */
extern void dummy_test(void);
@ -113,7 +116,7 @@ extern void event_test(void);
* Macro to print an ASCII NULL terminated string. fprintf is used
* so output can go to console.
*/
#define PRINT_STRING(string, stream) fprintf(stream, string)
#define PRINT_STRING(string, stream) fputs(string, stream)
/* PRINT_F
* Macro to print a formatted output string. fprintf is used when

View file

@ -17,7 +17,7 @@
#define PRINT_ALL_TO_N() \
PRINT_F(output_file, \
"|%5lu|%5lu|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|\n", \
"|%5u|%5u|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|\n", \
putsize, putsize, puttime[0] / 1000.0, puttime[1] / 1000.0, \
puttime[2] / 1000.0, \
(1000.0 * putsize) / puttime[0], \
@ -31,7 +31,7 @@
#define PRINT_1_TO_N() \
PRINT_F(output_file, \
"|%5lu|%5d|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|\n",\
"|%5u|%5d|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|%10.3f|\n", \
putsize, \
getsize, \
puttime[0] / 1000.0, \
@ -48,7 +48,7 @@
#define PRINT_ALL_TO_N() \
PRINT_F(output_file, \
"|%5lu|%5lu|%10lu|%10lu|%10lu|%10lu|%10lu|%10lu|\n", \
"|%5u|%5u|%10u|%10u|%10u|%10u|%10u|%10u|\n", \
putsize, putsize, puttime[0], puttime[1], \
puttime[2], \
(1000000 * putsize) / puttime[0], \
@ -62,7 +62,7 @@
#define PRINT_1_TO_N() \
PRINT_F(output_file, \
"|%5lu|%5d|%10lu|%10lu|%10lu|%10lu|%10lu|%10lu|\n", \
"|%5u|%5d|%10u|%10u|%10u|%10u|%10u|%10u|\n", \
putsize, \
getsize, \
puttime[0], \

View file

@ -71,7 +71,7 @@ int microIntToTask(void)
TICK_SYNCH();
makeInt();
if (flagVar == 1) {
PRINT_FORMAT(" switching time is %lu tcs = %lu nsec",
PRINT_FORMAT(" switching time is %u tcs = %u nsec",
timestamp, SYS_CLOCK_HW_CYCLES_TO_NS(timestamp));
}
return 0;

View file

@ -71,7 +71,7 @@ int microIntToTaskEvt(void)
task_sem_give(INTSEMA);
task_event_recv(EVENT0, TICKS_UNLIMITED);
timestamp = TIME_STAMP_DELTA_GET(timestamp);
PRINT_FORMAT(" switch time is %lu tcs = %lu nsec",
PRINT_FORMAT(" switch time is %u tcs = %u nsec",
timestamp, SYS_CLOCK_HW_CYCLES_TO_NS(timestamp));
return 0;
}

View file

@ -50,7 +50,7 @@ int microSemaLockUnlock(void)
}
timestamp = TIME_STAMP_DELTA_GET(timestamp);
if (bench_test_end() == 0) {
PRINT_FORMAT(" Average semaphore signal time %lu tcs = %lu"
PRINT_FORMAT(" Average semaphore signal time %u tcs = %u"
" nsec",
timestamp / N_TEST_SEMA,
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp,
@ -67,7 +67,7 @@ int microSemaLockUnlock(void)
}
timestamp = TIME_STAMP_DELTA_GET(timestamp);
if (bench_test_end() == 0) {
PRINT_FORMAT(" Average semaphore test time %lu tcs = %lu "
PRINT_FORMAT(" Average semaphore test time %u tcs = %u "
"nsec",
timestamp / N_TEST_SEMA,
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp,
@ -99,7 +99,7 @@ int microMutexLockUnlock(void)
task_mutex_lock(TEST_MUTEX, TICKS_UNLIMITED);
}
timestamp = TIME_STAMP_DELTA_GET(timestamp);
PRINT_FORMAT(" Average time to lock the mutex %lu tcs = %lu nsec",
PRINT_FORMAT(" Average time to lock the mutex %u tcs = %u nsec",
timestamp / N_TEST_MUTEX,
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp, N_TEST_MUTEX));
timestamp = TIME_STAMP_DELTA_GET(0);
@ -107,7 +107,7 @@ int microMutexLockUnlock(void)
task_mutex_unlock(TEST_MUTEX);
}
timestamp = TIME_STAMP_DELTA_GET(timestamp);
PRINT_FORMAT(" Average time to unlock the mutex %lu tcs = %lu nsec",
PRINT_FORMAT(" Average time to unlock the mutex %u tcs = %u nsec",
timestamp / N_TEST_MUTEX,
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp, N_TEST_MUTEX));
return 0;

View file

@ -90,14 +90,14 @@ void microTaskSwitchYield(void)
* called yield without the other having chance to execute
*/
errorCount++;
PRINT_FORMAT(" Error, iteration:%lu, helper iteration:%lu",
PRINT_FORMAT(" Error, iteration:%u, helper iteration:%u",
iterations, helper_task_iterations);
} else {
/* task_yield is called (iterations + helper_task_iterations)
* times in total.
*/
PRINT_FORMAT(" Average task context switch using "
"yield %lu tcs = %lu nsec",
"yield %u tcs = %u nsec",
timestamp / (iterations + helper_task_iterations),
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp,
(iterations + helper_task_iterations)));

View file

@ -106,7 +106,7 @@ int nanoCtxSwitch(void)
errorCount++;
PRINT_OVERFLOW_ERROR();
} else {
PRINT_FORMAT(" Average context switch time is %lu tcs = %lu"
PRINT_FORMAT(" Average context switch time is %u tcs = %u"
" nsec",
timestamp / ctxSwitchCounter,
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp,

View file

@ -69,7 +69,7 @@ int nanoIntLatency(void)
TICK_SYNCH();
task_fiber_start(&fiberStack[0], STACKSIZE,
(nano_fiber_entry_t) fiberInt, 0, 0, 6, 0);
PRINT_FORMAT(" switching time is %lu tcs = %lu nsec",
PRINT_FORMAT(" switching time is %u tcs = %u nsec",
timestamp, SYS_CLOCK_HW_CYCLES_TO_NS(timestamp));
return 0;
}

View file

@ -46,7 +46,7 @@ int nanoIntLockUnlock(void)
timestamp = TIME_STAMP_DELTA_GET(timestamp);
if (bench_test_end() == 0) {
PRINT_FORMAT(" Average time for lock then unlock "
"is %lu tcs = %lu nsec",
"is %u tcs = %u nsec",
timestamp / NTESTS,
SYS_CLOCK_HW_CYCLES_TO_NS_AVG(timestamp, NTESTS));
} else {

View file

@ -79,7 +79,7 @@ int nanoIntToFiber(void)
task_fiber_start(&fiberStack[0], STACKSIZE,
(nano_fiber_entry_t) fiberInt, 0, 0, 6, 0);
if (flagVar == 1) {
PRINT_FORMAT(" switching time is %lu tcs = %lu nsec",
PRINT_FORMAT(" switching time is %u tcs = %u nsec",
timestamp, SYS_CLOCK_HW_CYCLES_TO_NS(timestamp));
}
return 0;

View file

@ -104,7 +104,7 @@ int nanoIntToFiberSem(void)
task_fiber_start(&intStack[0], STACKSIZE,
(nano_fiber_entry_t) fiberInt, 0, 0, 6, 0);
PRINT_FORMAT(" switching time is %lu tcs = %lu nsec",
PRINT_FORMAT(" switching time is %u tcs = %u nsec",
timestamp, SYS_CLOCK_HW_CYCLES_TO_NS(timestamp));
return 0;
}

View file

@ -71,7 +71,7 @@ static inline void printDashLine(void)
#define PRINT_TIME_BANNER() \
do { \
PRINT_FORMAT(" tcs = timer clock cycles: 1 tcs is %lu nsec", \
PRINT_FORMAT(" tcs = timer clock cycles: 1 tcs is %u nsec", \
SYS_CLOCK_HW_CYCLES_TO_NS(1)); \
printDashLine(); \
} while (0)

View file

@ -24,21 +24,6 @@ const char sz_success[] = "SUCCESSFUL";
const char sz_partial[] = "PARTIAL";
const char sz_fail[] = "FAILED";
const char sz_module_title_fmt[] = "\nMODULE: %s";
const char sz_module_result_fmt[] = "\n\nPROJECT EXECUTION %s\n";
const char sz_module_end_fmt[] = "\nEND MODULE";
const char sz_date_fmt[] = "\nBUILD_DATE: %s %s";
const char sz_kernel_ver_fmt[] = "\nKERNEL VERSION: 0x%x";
const char sz_description[] = "\nTEST COVERAGE: %s";
const char sz_test_case_fmt[] = "\n\nTEST CASE: %s";
const char sz_test_start_fmt[] = "\nStarting test. Please wait...";
const char sz_case_result_fmt[] = "\nTEST RESULT: %s";
const char sz_case_details_fmt[] = "\nDETAILS: %s";
const char sz_case_end_fmt[] = "\nEND TEST CASE";
const char sz_case_timing_fmt[] = "%ld nSec";
/* time necessary to read the time */
uint32_t tm_off;

View file

@ -26,20 +26,20 @@ extern const char sz_success[];
extern const char sz_partial[];
extern const char sz_fail[];
extern const char sz_module_title_fmt[];
extern const char sz_module_result_fmt[];
extern const char sz_module_end_fmt[];
#define sz_module_title_fmt "\nMODULE: %s"
#define sz_module_result_fmt "\n\nPROJECT EXECUTION %s\n"
#define sz_module_end_fmt "\nEND MODULE"
extern const char sz_product_fmt[];
extern const char sz_kernel_ver_fmt[];
extern const char sz_description[];
#define sz_date_fmt "\nBUILD_DATE: %s %s"
#define sz_kernel_ver_fmt "\nKERNEL VERSION: 0x%x"
#define sz_description "\nTEST COVERAGE: %s"
extern const char sz_test_case_fmt[];
extern const char sz_test_start_fmt[];
extern const char sz_case_result_fmt[];
extern const char sz_case_details_fmt[];
extern const char sz_case_end_fmt[];
extern const char sz_case_timing_fmt[];
#define sz_test_case_fmt "\n\nTEST CASE: %s"
#define sz_test_start_fmt "\nStarting test. Please wait..."
#define sz_case_result_fmt "\nTEST RESULT: %s"
#define sz_case_details_fmt "\nDETAILS: %s"
#define sz_case_end_fmt "\nEND TEST CASE"
#define sz_case_timing_fmt "%u nSec"
int check_result(int i, uint32_t ticks);