cosmopolitan/libc/log/log.h
Justine Tunney 7b26b42769 Pay off more technical debt
This makes breaking changes to add underscores to many non-standard
function names provided by the c library. MODE=tiny is now tinier and
we now use smaller locks that are better for tiny apps in this mode.
Some headers have been renamed to be in the same folder as the build
package, so it'll be easier to know which build dependency is needed.
Certain old misguided interfaces have been removed. Intel intrinsics
headers are now listed in libc/isystem (but not in the amalgamation)
to help further improve open source compatibility. Header complexity
has also been reduced. Lastly, more shell scripts are now available.

Compared to 6f7d0cb1c3, some tiny corrections were made in libc/intrin/g_fds.c and libc/zipos/open.c including double semi colons and incorrect indentation for existing vista changes that were manually pulled from this commit previously.
2023-03-20 21:07:01 -04:00

231 lines
9.8 KiB
C

#ifndef COSMOPOLITAN_LIBC_LOG_LOG_H_
#define COSMOPOLITAN_LIBC_LOG_LOG_H_
#include "libc/stdio/stdio.h"
#define kLogFatal 0
#define kLogError 1
#define kLogWarn 2
#define kLogInfo 3
#define kLogVerbose 4
#define kLogDebug 5
#define kLogNoise 6
/**
* Log level for compile-time DCE.
*/
#ifndef LOGGABLELEVEL
#ifndef TINY
#define LOGGABLELEVEL kLogNoise
/* #elif IsTiny() */
/* #define LOGGABLELEVEL kLogInfo */
#else
#define LOGGABLELEVEL kLogVerbose
#endif
#endif
#ifdef TINY
#define _LOG_TINY 1
#else
#define _LOG_TINY 0
#endif
#if !(__ASSEMBLER__ + __LINKER__ + 0)
COSMOPOLITAN_C_START_
extern FILE *__log_file;
int __watch(void *, size_t);
void __die(void) relegated wontreturn; /* print backtrace and abort() */
void _meminfo(int); /* shows malloc statistics &c. */
void _memsummary(int); /* light version of same thing */
bool IsTerminalInarticulate(void) nosideeffect;
const char *commandvenv(const char *, const char *);
const char *GetAddr2linePath(void);
const char *GetGdbPath(void);
void ShowCrashReports(void);
bool32 IsDebuggerPresent(bool);
bool IsRunningUnderMake(void);
const char *GetSiCodeName(int, int);
char *GetSymbolByAddr(int64_t);
void PrintGarbage(void);
void PrintGarbageNumeric(FILE *);
void CheckForMemoryLeaks(void);
#ifndef __STRICT_ANSI__
#define _LOG_UNLIKELY(x) __builtin_expect(!!(x), 0)
extern unsigned __log_level; /* log level for runtime check */
#define LOGGABLE(LEVEL) \
((!__builtin_constant_p(LEVEL) || (LEVEL) <= LOGGABLELEVEL) && \
(LEVEL) <= __log_level)
// log a message with the specified log level (not checking if LOGGABLE)
#define LOGF(LEVEL, FMT, ...) \
do { \
if (!_LOG_TINY) _log_untrace(); \
flogf(LEVEL, __FILE__, __LINE__, NULL, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} while (0)
// report an error without backtrace and debugger invocation
#define FATALF(FMT, ...) \
do { \
if (!_LOG_TINY) _log_untrace(); \
flogf(kLogError, __FILE__, __LINE__, NULL, FMT, ##__VA_ARGS__); \
_log_exit(1); \
} while (0)
#define DIEF(FMT, ...) \
do { \
if (!_LOG_TINY) _log_untrace(); \
ffatalf(kLogFatal, __FILE__, __LINE__, NULL, FMT, ##__VA_ARGS__); \
unreachable; \
} while (0)
#define ERRORF(FMT, ...) \
do { \
if (LOGGABLE(kLogError)) { \
LOGF(kLogError, FMT, ##__VA_ARGS__); \
} \
} while (0)
#define WARNF(FMT, ...) \
do { \
if (LOGGABLE(kLogWarn)) { \
LOGF(kLogWarn, FMT, ##__VA_ARGS__); \
} \
} while (0)
#define INFOF(FMT, ...) \
do { \
if (LOGGABLE(kLogInfo)) { \
LOGF(kLogInfo, FMT, ##__VA_ARGS__); \
} \
} while (0)
#define VERBOSEF(FMT, ...) \
do { \
if (LOGGABLE(kLogVerbose)) { \
if (!_LOG_TINY) _log_untrace(); \
fverbosef(kLogVerbose, __FILE__, __LINE__, NULL, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define DEBUGF(FMT, ...) \
do { \
if (_LOG_UNLIKELY(LOGGABLE(kLogDebug))) { \
if (!_LOG_TINY) _log_untrace(); \
fdebugf(kLogDebug, __FILE__, __LINE__, NULL, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define NOISEF(FMT, ...) \
do { \
if (_LOG_UNLIKELY(LOGGABLE(kLogNoise))) { \
if (!_LOG_TINY) _log_untrace(); \
fnoisef(kLogNoise, __FILE__, __LINE__, NULL, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define FLOGF(F, FMT, ...) \
do { \
if (LOGGABLE(kLogInfo)) { \
if (!_LOG_TINY) _log_untrace(); \
flogf(kLogInfo, __FILE__, __LINE__, F, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define FWARNF(F, FMT, ...) \
do { \
if (LOGGABLE(kLogWarn)) { \
if (!_LOG_TINY) _log_untrace(); \
flogf(kLogWarn, __FILE__, __LINE__, F, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define FFATALF(F, FMT, ...) \
do { \
if (!_LOG_TINY) _log_untrace(); \
flogf(kLogError, __FILE__, __LINE__, F, FMT, ##__VA_ARGS__); \
_log_exit(1); \
} while (0)
#define FDEBUGF(F, FMT, ...) \
do { \
if (_LOG_UNLIKELY(LOGGABLE(kLogDebug))) { \
if (!_LOG_TINY) _log_untrace(); \
fdebugf(kLogDebug, __FILE__, __LINE__, F, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define FNOISEF(F, FMT, ...) \
do { \
if (_LOG_UNLIKELY(LOGGABLE(kLogNoise))) { \
if (!_LOG_TINY) _log_untrace(); \
fnoisef(kLogNoise, __FILE__, __LINE__, F, FMT, ##__VA_ARGS__); \
if (!_LOG_TINY) _log_retrace(); \
} \
} while (0)
#define LOGIFNEG1(FORM) \
({ \
int e = _log_get_errno(); \
autotype(FORM) Ax = (FORM); \
if (_LOG_UNLIKELY(Ax == (typeof(Ax))(-1)) && LOGGABLE(kLogWarn)) { \
if (!_LOG_TINY) _log_untrace(); \
_log_errno(__FILE__, __LINE__, #FORM); \
if (!_LOG_TINY) _log_retrace(); \
_log_set_errno(e); \
} \
Ax; \
})
#define LOGIFNULL(FORM) \
({ \
int e = _log_get_errno(); \
autotype(FORM) Ax = (FORM); \
if (Ax == NULL && LOGGABLE(kLogWarn)) { \
if (!_LOG_TINY) _log_untrace(); \
_log_errno(__FILE__, __LINE__, #FORM); \
if (!_LOG_TINY) _log_retrace(); \
_log_set_errno(e); \
} \
Ax; \
})
void _log_errno(const char *, int, const char *) relegated;
int _log_get_errno(void);
void _log_set_errno(int);
void _log_untrace(void);
void _log_retrace(void);
void _log_exit(int) wontreturn;
#define ARGS unsigned, const char *, int, FILE *, const char *
#define ATTR paramsnonnull((5)) printfesque(5)
#define ATTRV paramsnonnull((5, 6))
void flogf(ARGS, ...) ATTR libcesque;
void vflogf(ARGS, va_list) ATTRV libcesque;
void fverbosef(ARGS, ...) asm("flogf") ATTR relegated libcesque;
void vfverbosef(ARGS, va_list) asm("vflogf") ATTRV relegated libcesque;
void fdebugf(ARGS, ...) asm("flogf") ATTR relegated libcesque;
void vfdebugf(ARGS, va_list) asm("vflogf") ATTRV relegated libcesque;
void fnoisef(ARGS, ...) asm("flogf") ATTR relegated libcesque;
void vfnoisef(ARGS, va_list) asm("vflogf") ATTRV relegated libcesque;
void ffatalf(ARGS, ...) asm("flogf") ATTR relegated wontreturn libcesque;
void vffatalf(ARGS, va_list) asm("vflogf") ATTRV relegated wontreturn libcesque;
#undef ARGS
#undef ATTR
#undef ATTRV
#endif /* __STRICT_ANSI__ */
COSMOPOLITAN_C_END_
#endif /* !(__ASSEMBLER__ + __LINKER__ + 0) */
#endif /* COSMOPOLITAN_LIBC_LOG_LOG_H_ */