Air quality sensor
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

194 lines
5.1 KiB

// enable "vasprintf" from stdio.h
#ifndef _GNU_SOURCE
#define _GNU_SOURCE
#endif
#include "console/console.h"
#include <stdio.h>
#include <stdbool.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
// These are either implemented using unix file descriptors, or in a platform specific way through a void* context
// - then the user code must provide the implementations.
#if CONSOLE_USE_FILE_IO_STREAMS
#include <unistd.h>
bool console_have_stdin_ctx(console_ctx_t *ctx)
{
return ctx && ctx->in &&
!feof(ctx->in);
}
/**
* Write to console context.
*
* This is also a Linenoise write callback.
*
* Return number of characters written, -1 on error.
*/
int __attribute__((weak)) console_write_ctx(console_ctx_t *ctx, const char *text, size_t len) {
if (!ctx || !ctx->out) {
return -1;
}
size_t written = fwrite(text, 1, len, ctx->out);
if (written != len) {
return -1;
}
return (int) written;
}
/**
* Read from console context's input stream.
*
* This is also a Linenoise read callback.
*
* Return number of characters read, -1 on error
*/
int __attribute__((weak)) console_read_ctx(console_ctx_t *ctx, char *dest, size_t count) {
if (!console_have_stdin_ctx(ctx)) return -1;
ssize_t readn = fread(dest, 1, (size_t) count, ctx->in);
return (int) readn;
}
#if CONSOLE_USE_TERMIOS
#include <termio.h>
int console_can_read_ctx(console_ctx_t *ctx) {
if (!console_have_stdin_ctx(ctx)) return -1;
int fd = fileno(ctx->in);
struct termios original;
tcgetattr(fd, &original);
struct termios term;
memcpy(&term, &original, sizeof(term));
term.c_lflag &= ~ICANON;
tcsetattr(fd, TCSANOW, &term);
int characters_buffered = 0;
ioctl(fd, FIONREAD, &characters_buffered);
tcsetattr(fd, TCSANOW, &original);
return characters_buffered;
}
#endif // CONSOLE_USE_TERMIOS
#endif // CONSOLE_USE_FILEDES_IO
ssize_t console_printf_ctx(console_ctx_t *ctx, console_color_t color, const char *format, ...) {
if (!ctx) return -1;
va_list list;
va_start(list, format);
ssize_t len = console_vprintf_ctx(ctx, color, format, list);
va_end(list);
return len;
}
ssize_t console_vprintf_ctx(console_ctx_t *ctx, console_color_t color, const char *format, va_list args) {
if (!ctx) return -1;
if (ctx->use_colors && color != COLOR_RESET) {
switch(color) {
case COLOR_BLACK:
console_write_ctx(ctx, "\x1b[30;1m", 7);
break;
case COLOR_RED:
console_write_ctx(ctx, "\x1b[31;1m", 7);
break;
case COLOR_GREEN:
console_write_ctx(ctx, "\x1b[32;1m", 7);
break;
case COLOR_YELLOW:
console_write_ctx(ctx, "\x1b[33;1m", 7);
break;
case COLOR_BLUE:
console_write_ctx(ctx, "\x1b[34;1m", 7);
break;
case COLOR_MAGENTA:
console_write_ctx(ctx, "\x1b[35;1m", 7);
break;
case COLOR_CYAN:
console_write_ctx(ctx, "\x1b[36;1m", 7);
break;
//case COLOR_WHITE:
default:
console_write_ctx(ctx, "\x1b[37;1m", 7);
break;
}
}
char *buf = NULL;
ssize_t len = vasprintf(&buf, format, args);
if (buf && len >= 0) {
// change to actual len written, can also result in -1 on error
len = console_write_ctx(ctx, buf, (size_t) len);
free(buf); // allocated by vasprintf
}
if (ctx->use_colors && color != COLOR_RESET) {
console_write_ctx(ctx, "\x1b[0m", 4);
len += 7+4;
}
return len;
}
int console_print_ctx(console_ctx_t *ctx, const char *text) {
if (!ctx) return -1;
return console_write_ctx(ctx, text, (int) strlen(text));
}
ssize_t console_println_ctx(console_ctx_t *ctx, const char *text) {
if (!ctx) return -1;
ssize_t n = console_write_ctx(ctx, text, (int) strlen(text));
if (n < 0) return n;
ssize_t m = console_write_ctx(ctx, "\n", 2);
if (m < 0) return m;
return n + m;
}
// ---------------- convenience functions -------------------
bool console_have_stdin(void) {
if (!console_context_available()) return false;
return console_have_stdin_ctx(console_active_ctx);
}
int console_can_read(void) {
if (!console_have_stdin()) return -1; // Input not available
return console_can_read_ctx(console_active_ctx);
}
/**
* Linenoise read callback.
*
* Return number of characters read, -1 on error
*/
ssize_t console_read(char *dest, size_t count) {
if (!console_have_stdin()) return -1;
return console_read_ctx(console_active_ctx, dest, count);
}
/**
* Linenoise write callback.
*
* Return number of characters written, -1 on error.
*/
ssize_t console_write(const char *text, size_t len) {
if (!console_context_available()) return -1;
return console_write_ctx(console_active_ctx, text, len);
}
ssize_t console_println(const char *text) {
if (!console_context_available()) return -1;
return console_println_ctx(console_active_ctx, text);
}