#include "stream.h" #include #include void ivy_diag_stream_init_file(struct ivy_diag_stream *stream, FILE *fp) { memset(stream, 0x0, sizeof *stream); stream->s_type = IVY_DIAG_STREAM_FILE; stream->s_flags = IVY_DIAG_STREAM_F_NONE; stream->s_fp = fp; stream->s_row = 1; stream->s_col = 1; } void ivy_diag_stream_init_tty(struct ivy_diag_stream *stream, struct b_tty *tty) { memset(stream, 0x0, sizeof *stream); stream->s_type = IVY_DIAG_STREAM_TTY; stream->s_flags = IVY_DIAG_STREAM_F_COLOUR; stream->s_tty = tty; stream->s_row = 1; stream->s_col = 1; } enum ivy_status diag_stream_get_dimensions( struct ivy_diag_stream *stream, size_t *out_rows, size_t *out_cols) { switch (stream->s_type) { case IVY_DIAG_STREAM_FILE: if (out_rows) { *out_rows = (size_t)-1; } if (out_cols) { *out_cols = (size_t)-1; } break; case IVY_DIAG_STREAM_TTY: { unsigned int w, h; b_tty_get_dimensions(stream->s_tty, &w, &h); if (out_rows) { *out_rows = h; } if (out_cols) { *out_cols = w; } break; } default: return IVY_ERR_BAD_STATE; } return IVY_OK; } enum ivy_status diag_stream_putc(struct ivy_diag_stream *stream, char c) { enum ivy_status status = IVY_OK; switch (stream->s_type) { case IVY_DIAG_STREAM_FILE: fputc(c, stream->s_fp); status = (ferror(stream->s_fp)) ? IVY_ERR_IO_FAILURE : IVY_OK; break; case IVY_DIAG_STREAM_TTY: b_tty_putc(stream->s_tty, 0, c); status = IVY_OK; break; default: status = IVY_ERR_BAD_STATE; break; } if (stream->s_esc) { if (c == '[' || c == ']') { stream->s_esc = 0; } return status; } if (!stream->s_esc && c == '[') { stream->s_esc = 1; return status; } switch (c) { case '\r': stream->s_col = 1; break; case '\n': stream->s_col = 1; stream->s_row++; break; default: stream->s_col++; break; } return status; } enum ivy_status diag_stream_puts(struct ivy_diag_stream *stream, const char *s) { enum ivy_status status = IVY_OK; while (*s && status == IVY_OK) { status = diag_stream_putc(stream, *s); s++; } return status; } enum ivy_status diag_stream_printf( struct ivy_diag_stream *stream, const char *format, ...) { enum ivy_status status = IVY_OK; va_list arg; va_start(arg, format); char buf[256]; vsnprintf(buf, sizeof buf, format, arg); va_end(arg); return diag_stream_puts(stream, buf); }