Setup
With Premake
Clone the repository to the location of your choice. Create a new premake workspace and include the file c_log/premake5.lua inside your own premake file. Then link your executable project to the c_log project using this line links c_log. Finally compile the project. For a full setup of premake go to the premake github page.
Without Premake
Copy the files c_log.c, c_log.h and internal.h into your project directory and compile your project with these files.
Including to project
Once added to your project the file can be included as follows. Make sure the c_log.h file is in the include path of your project.
#include <c_log.h>
Example
The following example will create 2 loggers and show some output to demonstrate the capabilities of the library.
#include <stdlib.h>
#include <stdint.h>
#include <stdio.h>
//#define CL_LOG_DISABLED
#include <c_log.h>
int main(int argc, char **argv)
{
CL_Logger *logger = CL_LOGGER_CREATE("LOGGER", "[%T] (%N) %% %C%V\t%F, %L %M%C", 1, stdout);
CL_Logger *logger2 = CL_LOGGER_CREATE("LOGGER2", NULL, 1, stdout);
CL_LOG_TRACE(logger, "Hello World! %d", rand());
CL_LOG_INFO(logger, "Hello World! %d", rand());
CL_LOG_WARN(logger, "Hello World! %d", rand());
CL_LOG_ERROR(logger, "Hello World! %d", rand());
CL_LOG_FATAL(logger, "Hello World! %d", rand());
CL_LOG_TRACE(logger2, "Hello World! %d", rand());
CL_LOG_INFO(logger2, "Hello World! %d", rand());
CL_LOG_WARN(logger2, "Hello World! %d", rand());
CL_LOG_ERROR(logger2, "Hello World! %d", rand());
CL_LOG_FATAL(logger2, "Hello World! %d", rand());
CL_LOGGER_DESTROY(logger);
CL_LOGGER_DESTROY(logger2);
}
Functions
This section provides in-depth information on the functions available.
CL_LOGGER_CREATE
CL_Logger *CL_LOGGER_CREATE(const char *name, const char *pattern, uint64_t output_count, ...);
Parameters
-
name-> the name of the logger which can be output when logging if it is contained in the pattern. If left NULL the logger will be named "UNNAMED". -
pattern-> a string that will define the format of the output when logging. It can contain any character and any of the following formats:%F-> the source file at which the logging was done (__FILE__ macro)%L-> the line of the file at which the logging was done (__LINE__ macro)%T-> the time at which the logging was done in HH:MM:SS format%M-> the message that is passed to the loggin function. If %M is not present in the pattern the message will not be printed.%N-> the name of the logger%C-> the start and end of color. ex: %C Hello world %C ; in this case Hello world will be printed in color.%V-> the name of the log level which can be TRACE, INFO, WARN, ERROR or FATAL
If NULL is passed the pattern will be set to CL_DEFAULT_PATTERN which is defined in
c_log.h. To insert a%character in the pattern write%%. -
output_count-> the count of how manyFILE *are to be passed as the next parameters. -
...-> theFILE *(s) to where the logger will output.
The function returns the pointer to the logger.
Usage
To output with default pattern:
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stdout);
To output with custom pattern:
CL_Logger *logger = CL_LOGGER_CREATE("TEST", "%C[%V]%C(%F,%L)%C%M%C", 1, stdout);
To output to stderr:
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stderr);
To output to a file:
FILE *file = fopen("log.txt", "w");
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, file);
To write to multiple outputs:
FILE *file = fopen("log.txt", "w");
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 2, stderr file);
CL_LOGGER_DESTROY
void CL_LOGGER_DESTROY(Logger *logger);
This function will free the data related to the logger. The passed logger cannot be used after calling this function.
Usage
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stdout);
// ...
CL_LOGGER_DESTROY(logger);
CL_LOG_...
void CL_LOG_TRACE(Logger *logger, const char *format, ...);
void CL_LOG_INFO(Logger *logger, const char *format, ...);
void CL_LOG_WARN(Logger *logger, const char *format, ...);
void CL_LOG_ERROR(Logger *logger, const char *format, ...);
void CL_LOG_FATAL(Logger *logger, const char *format, ...);
These functions are used to log using a specific logger. A new line is always printed at the end of the function.
Parameters
logger-> The logger used to print.formatand...-> The message to log. These two parameters work the same as forprintfin the standard library.
Usage
To print a random integer as INFO:
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stdout);
// ...
CL_LOG_INFO(logger, "%d", rand());
// ...
CL_LOGGER_DESTROY(logger);
CL_LOG_LVL_SET
void CL_LOGGER_LVL_SET(CL_Logger *logger, CL_LogLevel lvl);
Sets the log level at which the logger is to output.
Parameters
logger-> the logger to modifylvl-> the log level to set
Usage
To set the level to INFO:
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stdout);
CL_LOGGER_LVL_SET(logger, CL_LOG_LEVEL_INFO);
// ...
CL_LOG_TRACE(logger, "will not be output")
CL_LOG_INFO(logger, "will be output");
CL_LOG_WARN(logger, "will be output");
// ...
CL_LOGGER_DESTROY(logger);
CL_LOG_LVL_GET
CL_LogLevel CL_LOGGER_LVL_GET(CL_Logger *logger);
Returns the log level of the passed logger.
Parameters
logger-> the logger from which the log level is retrieved.
Usage
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stdout);
// ...
CL_LogLevel level = CL_LOGGER_LVL_GET(logger);
// ...
CL_LOGGER_DESTROY(logger);
Log Levels
The different levels a logger can be at:
typedef enum CL_LogLevel
{
CL_LOG_LEVEL_FATAL = 0,
CL_LOG_LEVEL_ERROR,
CL_LOG_LEVEL_WARN,
CL_LOG_LEVEL_INFO,
CL_LOG_LEVEL_TRACE
} CL_LogLevel;
Usage
No output will occur if the level of the logger is higher than the level of the function being called. For example:
CL_Logger *logger = CL_LOGGER_CREATE("TEST", NULL, 1, stdout);
CL_LOGGER_LVL_SET(logger, CL_LOG_LEVEL_WARN);
// ...
CL_LOG_INFO(logger, "will not be output");
CL_LOG_WARN(logger, "will be output");
CL_LOG_ERROR(logger, "will be output");
// ...
CL_LOGGER_DESTROY(logger);
By default the level of a logger is CL_LOG_LEVEL_TRACE.