X-Git-Url: https://git.xonotic.org/?p=xonotic%2Fgmqcc.git;a=blobdiff_plain;f=conout.c;h=c4c285bb59ec0f21c5c71d6af175a3f6d1626546;hp=7fb50b98612d3d5228b89615485f1feb509f1779;hb=ff37abb0c7c60481e1264914fa5e02e9986c5cd9;hpb=90e2e5a4ad11147fb8e76d112b24aac096f93897 diff --git a/conout.c b/conout.c index 7fb50b9..c4c285b 100644 --- a/conout.c +++ b/conout.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2012, 2013 + * Copyright (C) 2012, 2013, 2014, 2015 * Dale Weiler * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -20,168 +20,20 @@ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE * SOFTWARE. */ +#include #include "gmqcc.h" -/* - * isatty/STDERR_FILENO/STDOUT_FILNO - * + some other things likewise. - */ -#ifndef _WIN32 -# include -#else -# include - /* - * Windows and it's posix underscore bullshit. We simply fix this - * with yay, another macro :P - */ -# define isatty _isatty -#endif - -#define GMQCC_IS_STDOUT(X) ((FILE*)((void*)X) == stdout) -#define GMQCC_IS_STDERR(X) ((FILE*)((void*)X) == stderr) +#define GMQCC_IS_STDOUT(X) ((fs_file_t*)((void*)X) == (fs_file_t*)stdout) +#define GMQCC_IS_STDERR(X) ((fs_file_t*)((void*)X) == (fs_file_t*)stderr) #define GMQCC_IS_DEFINE(X) (GMQCC_IS_STDERR(X) || GMQCC_IS_STDOUT(X)) typedef struct { - FILE *handle_err; - FILE *handle_out; - - int color_err; - int color_out; + fs_file_t *handle_err; + fs_file_t *handle_out; + int color_err; + int color_out; } con_t; -/* - * Doing colored output on windows is fucking stupid. The linux way is - * the real way. So we emulate it on windows :) - */ -#ifdef _WIN32 -#define WIN32_LEAN_AND_MEAN -#include - -/* - * Windows doesn't have constants for FILENO, sadly but the docs tell - * use the constant values. - */ -#undef STDERR_FILENO -#undef STDOUT_FILENO -#define STDERR_FILENO 2 -#define STDOUT_FILENO 1 - -enum { - RESET = 0, - BOLD = 1, - BLACK = 30, - RED, - GREEN, - YELLOW, - BLUE, - MAGENTA, - CYAN, - GRAY, - WHITE = GRAY -}; - -enum { - WBLACK, - WBLUE, - WGREEN = 2, - WRED = 4, - WINTENSE = 8, - WCYAN = WBLUE | WGREEN, - WMAGENTA = WBLUE | WRED, - WYELLOW = WGREEN | WRED, - WWHITE = WBLUE | WGREEN | WRED -}; - -static const int ansi2win[] = { - WBLACK, - WRED, - WGREEN, - WYELLOW, - WBLUE, - WMAGENTA, - WCYAN, - WWHITE -}; - -static int win_fputs(FILE *h, const char *str) { - /* state for translate */ - int acolor = 0; - int wcolor = 0; - int icolor = 0; - int state = 0; - - /* attributes */ - int intense = -1; - int colors[] = {-1, -1 }; - int colorpos = 1; - int length = 0; - CONSOLE_SCREEN_BUFFER_INFO cinfo; - GetConsoleScreenBufferInfo ( - (GMQCC_IS_STDOUT(h)) ? - GetStdHandle(STD_OUTPUT_HANDLE) : - GetStdHandle(STD_ERROR_HANDLE), &cinfo - ); - icolor = cinfo.wAttributes; - - while (*str) { - if (*str == '\x1B') - state = '\x1B'; - else if (state == '\x1B' && *str == '[') - state = '['; - else if (state == '[') { - if (*str != 'm') { - colors[colorpos] = *str; - colorpos--; - } else { - int find; - int mult; - for (find = colorpos + 1, acolor = 0, mult = 1; find < 2; find++) { - acolor += (colors[find] - 48) * mult; - mult *= 10; - } - - /* convert to windows color */ - if (acolor == BOLD) - intense = WINTENSE; - else if (acolor == RESET) { - intense = WBLACK; - wcolor = icolor; - } - else if (BLACK <= acolor && acolor <= WHITE) - wcolor = ansi2win[acolor - 30]; - else if (acolor == 90) { - /* special gray really white man */ - wcolor = WWHITE; - intense = WBLACK; - } - - SetConsoleTextAttribute ( - (GMQCC_IS_STDOUT(h)) ? - GetStdHandle(STD_OUTPUT_HANDLE) : - GetStdHandle(STD_ERROR_HANDLE), - - wcolor | intense | (icolor & 0xF0) - ); - colorpos = 1; - state = -1; - } - } else { - fs_file_write(str, 1, 1, stdout); - length ++; - } - str++; - } - /* restore */ - SetConsoleTextAttribute( - (GMQCC_IS_STDOUT(h)) ? - GetStdHandle(STD_OUTPUT_HANDLE) : - GetStdHandle(STD_ERROR_HANDLE), - icolor - ); - return length; -} -#endif - /* * We use standard files as default. These can be changed at any time * with con_change(F, F) @@ -197,10 +49,8 @@ static con_t console; * checks. */ static void con_enablecolor(void) { - if (console.handle_err == stderr || console.handle_err == stdout) - console.color_err = true; /*!!(isatty(STDERR_FILENO));*/ - if (console.handle_out == stderr || console.handle_out == stdout) - console.color_out = true; /*!!(isatty(STDOUT_FILENO));*/ + console.color_err = util_isatty(console.handle_err); + console.color_out = util_isatty(console.handle_out); } /* @@ -208,23 +58,8 @@ static void con_enablecolor(void) { * arguments. This colorizes for windows as well via translate * step. */ -static int con_write(FILE *handle, const char *fmt, va_list va) { - int ln; - #ifndef _WIN32 - ln = vfprintf(handle, fmt, va); - #else - { - char data[4096]; - memset(data, 0, sizeof(data)); -#ifdef _MSC_VER - vsnprintf_s(data, sizeof(data), sizeof(data), fmt, va); -#else - vsnprintf(data, sizeof(data), fmt, va); -#endif - ln = (GMQCC_IS_DEFINE(handle)) ? win_fputs(handle, data) : fs_file_puts(handle, data); - } - #endif - return ln; +static int con_write(fs_file_t *handle, const char *fmt, va_list va) { + return vfprintf((FILE*)handle, fmt, va); } /********************************************************************** @@ -248,8 +83,8 @@ void con_color(int state) { } void con_init() { - console.handle_err = stderr; - console.handle_out = stdout; + console.handle_err = (fs_file_t*)stderr; + console.handle_out = (fs_file_t*)stdout; con_enablecolor(); } @@ -271,16 +106,16 @@ void con_reset() { int con_change(const char *out, const char *err) { con_close(); - if (!out) out = (const char *)((!console.handle_out) ? stdout : console.handle_out); - if (!err) err = (const char *)((!console.handle_err) ? stderr : console.handle_err); + if (!out) out = (const char *)((!console.handle_out) ? (fs_file_t*)stdout : console.handle_out); + if (!err) err = (const char *)((!console.handle_err) ? (fs_file_t*)stderr : console.handle_err); if (GMQCC_IS_DEFINE(out)) { - console.handle_out = GMQCC_IS_STDOUT(out) ? stdout : stderr; + console.handle_out = (fs_file_t*)(GMQCC_IS_STDOUT(out) ? stdout : stderr); con_enablecolor(); } else if (!(console.handle_out = fs_file_open(out, "w"))) return 0; if (GMQCC_IS_DEFINE(err)) { - console.handle_err = GMQCC_IS_STDOUT(err) ? stdout : stderr; + console.handle_err = (fs_file_t*)(GMQCC_IS_STDOUT(err) ? stdout : stderr); con_enablecolor(); } else if (!(console.handle_err = fs_file_open(err, "w"))) return 0; @@ -291,11 +126,11 @@ int con_change(const char *out, const char *err) { * Defaultizer because stdio.h shouldn't be used anywhere except here * and inside file.c To prevent mis-match of wrapper-interfaces. */ -FILE *con_default_out() { - return (console.handle_out = stdout); +fs_file_t *con_default_out() { + return (fs_file_t*)(console.handle_out = (fs_file_t*)stdout); } -FILE *con_default_err() { - return (console.handle_err = stderr); +fs_file_t *con_default_err() { + return (fs_file_t*)(console.handle_err = (fs_file_t*)stderr); } int con_verr(const char *fmt, va_list va) { @@ -326,7 +161,6 @@ int con_out(const char *fmt, ...) { return ln; } -#ifndef QCVM_EXECUTOR /* * Utility console message writes for lexer contexts. These will allow * for reporting of file:line based on lexer context, These are used @@ -340,10 +174,10 @@ static void con_vprintmsg_c(int level, const char *name, size_t line, size_t col CON_RED }; - int err = !!(level == LVL_ERROR); - int color = (err) ? console.color_err : console.color_out; - int (*print) (const char *, ...) = (err) ? &con_err : &con_out; - int (*vprint)(const char *, va_list) = (err) ? &con_verr : &con_vout; + int err = !!(level == LVL_ERROR); + int color = (err) ? console.color_err : console.color_out; + int (*print) (const char *, ...) = (err) ? &con_err : &con_out; + int (*vprint)(const char *, va_list) = (err) ? &con_verr : &con_vout; if (color) print("\033[0;%dm%s:%d:%d: \033[0;%dm%s: \033[0m", CON_CYAN, name, (int)line, (int)column, sel[level], msgtype); @@ -379,7 +213,7 @@ void con_cprintmsg(lex_ctx_t ctx, int lvl, const char *msgtype, const char *msg, va_end (va); } -/* General error interface */ +/* General error interface: TODO seperate as part of the compiler front-end */ size_t compile_errors = 0; size_t compile_warnings = 0; size_t compile_Werrors = 0; @@ -444,4 +278,3 @@ bool GMQCC_WARN compile_warning(lex_ctx_t ctx, int warntype, const char *fmt, .. va_end(ap); return r; } -#endif