Skip to content

Commit

Permalink
Add logging macros (#92)
Browse files Browse the repository at this point in the history
# Purpose
Explain the purpose of the PR here, including references to any existing
Notion tasks.
- add logging macros to make onboarding challenge more consistent with
our actual code base
# New Changes
- Explain new changes

# Testing
- Explain tests that you ran to verify code functionality.
- built successfully when I defined the address macro
- forced an error and ran integration test and it was correctly printed
# Outstanding Changes
- If there are non-critical changes (i.e. additional features) that can
be made to this feature in the future, indicate them here.
- Once merged, the onboarding challenge description on notion should
mention these macros
  • Loading branch information
Navtajh04 authored Sep 17, 2023
1 parent 0434f4e commit 1b38591
Show file tree
Hide file tree
Showing 8 changed files with 160 additions and 5 deletions.
2 changes: 2 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ elseif(CMAKE_BUILD_TYPE MATCHES FW)
main.c
sys/console_io/console.c
sys/i2c/i2c_io.c
sys/logging/logging.c
services/controller/controller.c

lm75bd/lm75bd.c
Expand All @@ -33,6 +34,7 @@ elseif(CMAKE_BUILD_TYPE MATCHES FW)
sys
sys/i2c
sys/console_io
sys/logging
lm75bd
services/controller
services/thermal_mgr
Expand Down
7 changes: 3 additions & 4 deletions lm75bd/lm75bd.c
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#include "lm75bd.h"
#include "i2c_io.h"
#include "errors.h"
#include "logging.h"

#include <stdint.h>
#include <string.h>
Expand All @@ -14,10 +15,8 @@ error_code_t lm75bdInit(lm75bd_config_t *config) {

if (config == NULL) return ERR_CODE_INVALID_ARG;

errCode = writeConfigLM75BD(config->devAddr, config->osFaultQueueSize, config->osPolarity,
config->osOperationMode, config->devOperationMode);

if (errCode != ERR_CODE_SUCCESS) return errCode;
RETURN_IF_ERROR_CODE(writeConfigLM75BD(config->devAddr, config->osFaultQueueSize, config->osPolarity,
config->osOperationMode, config->devOperationMode));

// Assume that the overtemperature and hysteresis thresholds are already set
// Hysteresis: 75 degrees Celsius
Expand Down
2 changes: 2 additions & 0 deletions services/controller/controller.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include "lm75bd.h"
#include "errors.h"
#include "i2c_io.h"
#include "logging.h"

#include <FreeRTOS.h>
#include <os_task.h>
Expand Down Expand Up @@ -39,6 +40,7 @@ static void controller(void *pvParameters) {
// Initialize the mutex that protects the console output
initConsole();
initI2C();
initLogger();

static lm75bd_config_t config = {0};
config.devAddr = LM75BD_OBC_I2C_ADDR;
Expand Down
4 changes: 4 additions & 0 deletions sys/errors.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,8 @@ typedef enum {

/* Driver errors */
ERR_CODE_I2C_TRANSFER_TIMEOUT = 200,

/* Logging errors */
ERR_CODE_BUFF_TOO_SMALL = 300,
ERR_CODE_LOG_MSG_SILENCED = 301,
} error_code_t;
57 changes: 57 additions & 0 deletions sys/logging/logging.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
#include "logging.h"
#include "errors.h"
#include "console.h"

#include <stdarg.h>
#include <stdint.h>
#include <stdio.h>

#define MAX_MSG_SIZE 128U
#define MAX_FNAME_LINENUM_SIZE 128U
// Extra 10 for the small extra pieces in "%s - %s\r\n"
#define MAX_LOG_SIZE (MAX_MSG_SIZE + MAX_FNAME_LINENUM_SIZE + 10U)

#define UART_MUTEX_BLOCK_TIME portMAX_DELAY

static const char *LEVEL_STRINGS[] = {"TRACE", "DEBUG", "INFO", "WARN", "ERROR", "FATAL"};

static log_level_t logLevel;

void initLogger(void) {
logLevel = LOG_DEFAULT_LEVEL;
}

void logSetLevel(log_level_t newLogLevel) { logLevel = newLogLevel; }

error_code_t logLog(log_level_t msgLevel, const char *file, uint32_t line, const char *s, ...) {
if (msgLevel < logLevel) return ERR_CODE_LOG_MSG_SILENCED;

if (file == NULL || s == NULL) return ERR_CODE_INVALID_ARG;

int ret = 0;

// Message
char msgbuf[MAX_MSG_SIZE] = {0};
va_list args;
va_start(args, s);
ret = vsnprintf(msgbuf, MAX_MSG_SIZE, s, args);
va_end(args);
if (ret < 0) return ERR_CODE_INVALID_ARG;
if ((uint32_t)ret >= MAX_MSG_SIZE) return ERR_CODE_BUFF_TOO_SMALL;

// File & line number
char infobuf[MAX_FNAME_LINENUM_SIZE] = {0};
ret = snprintf(infobuf, MAX_FNAME_LINENUM_SIZE, "%-5s -> %s:%u", LEVEL_STRINGS[msgLevel], file, line);
if (ret < 0) return ERR_CODE_INVALID_ARG;
if ((uint32_t)ret >= MAX_FNAME_LINENUM_SIZE) return ERR_CODE_BUFF_TOO_SMALL;

// Prepare entire output
char buf[MAX_LOG_SIZE] = {0};
ret = snprintf(buf, MAX_LOG_SIZE, "%s - %s\r\n", infobuf, msgbuf);
if (ret < 0) return ERR_CODE_INVALID_ARG;
if ((uint32_t)ret >= MAX_LOG_SIZE) return ERR_CODE_BUFF_TOO_SMALL;

printConsole((unsigned char *)buf);

return ERR_CODE_SUCCESS;
}
77 changes: 77 additions & 0 deletions sys/logging/logging.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
#pragma once

#include "errors.h"

#include <stdint.h>
#include <stdarg.h>

/**
* @enum log_level_t
* @brief Log levels enum.
*
* Enum containing all log levels.
*/
typedef enum { LOG_TRACE, LOG_DEBUG, LOG_INFO, LOG_WARN, LOG_ERROR, LOG_FATAL, LOG_OFF } log_level_t;

#ifndef LOG_DEFAULT_LEVEL
#define LOG_DEFAULT_LEVEL LOG_TRACE
#endif

#define LOG_TRACE(...) logLog(LOG_TRACE, __FILE__, __LINE__, __VA_ARGS__)
#define LOG_DEBUG(...) logLog(LOG_DEBUG, __FILE__, __LINE__, __VA_ARGS__)
#define LOG_INFO(...) logLog(LOG_INFO, __FILE__, __LINE__, __VA_ARGS__)
#define LOG_WARN(...) logLog(LOG_WARN, __FILE__, __LINE__, __VA_ARGS__)
#define LOG_ERROR(...) logLog(LOG_ERROR, __FILE__, __LINE__, __VA_ARGS__)
#define LOG_FATAL(...) logLog(LOG_FATAL, __FILE__, __LINE__, __VA_ARGS__)

#define LOG_ERROR_CODE(errCode) LOG_ERROR("Error code: %lu", (uint32_t)errCode)

#define RETURN_IF_ERROR_CODE(_ret) \
do { \
errCode = _ret; \
if (errCode != ERR_CODE_SUCCESS) { \
LOG_ERROR_CODE(errCode); \
return errCode; \
} \
} while (0)

#define LOG_IF_ERROR_CODE(_ret) \
do { \
errCode = _ret; \
if (errCode != ERR_CODE_SUCCESS) { \
LOG_ERROR_CODE(errCode); \
} \
} while (0)

#ifdef __cplusplus
extern "C" {
#endif

/**
* @brief Initialize the logger
*/
void initLogger(void);

/**
* @brief Set the logging level
*
* @param newLogLevel The new logging level
*/
void logSetLevel(log_level_t newLogLevel);

/**
* @brief Log a message
*
* @param msgLevel Level of the message
* @param file File of message
* @param line Line of message
* @param s Message to log
* @param ... Additional arguments for the message
* @return error_code_t
*
*/
error_code_t logLog(log_level_t msgLevel, const char *file, uint32_t line, const char *s, ...);

#ifdef __cplusplus
}
#endif
4 changes: 3 additions & 1 deletion test/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ set(TEST_DEPENDENCIES
set(TEST_SOURCES
${CMAKE_SOURCE_DIR}/test/main.cpp
${CMAKE_SOURCE_DIR}/test/test_driver.cpp
${CMAKE_SOURCE_DIR}/test/mock_logging.c
)

set(TEST_SOURCES ${TEST_SOURCES} ${TEST_DEPENDENCIES})
Expand All @@ -19,7 +20,8 @@ target_include_directories(${TEST_BINARY}
${CMAKE_SOURCE_DIR}/lm75bd
${CMAKE_SOURCE_DIR}/sys
${CMAKE_SOURCE_DIR}/sys/i2c
${CMAKE_SOURCE_DIR}/sys/console
${CMAKE_SOURCE_DIR}/sys/console_io
${CMAKE_SOURCE_DIR}/sys/logging
)

target_link_libraries(${TEST_BINARY} PRIVATE
Expand Down
12 changes: 12 additions & 0 deletions test/mock_logging.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#include "logging.h"
#include "errors.h"

#include <stdarg.h>
#include <stdint.h>
#include <stdio.h>

void logSetLevel(log_level_t newLogLevel) { /* do nothing */ }

error_code_t logLog(log_level_t msgLevel, const char *file, uint32_t line, const char *s, ...) {
return ERR_CODE_SUCCESS;
}

0 comments on commit 1b38591

Please sign in to comment.