table

Помоћни програм из командне линије за форматирање и приказ CSV-а
git clone https://git.sr.ht/~strahinja/table
Дневник | Датотеке | Референце | ПРОЧИТАЈМЕ | ЛИЦЕНЦА

defs.h (7160B)


      1 /* This program is licensed under the terms of GNU GPL v3 or (at your option)
      2  * any later version. Copyright (C) 2020-2026  Страхиња Радић.
      3  * See the file LICENSE for exact copyright and license details. */
      4 
      5 #include "utf8.h"
      6 
      7 #define BUF_DEFAULT    4096
      8 #define BUF_DELTA      512
      9 #define FORMAT_DEFAULT 256
     10 
     11 // #define ANSI_SGR_RESET "\033[0m\033[?25h"
     12 #define ANSI_SGR_BOLD_ON  "\033[1m"
     13 #define ANSI_SGR_BOLD_OFF "\033[0m"
     14 
     15 #define CUSTOM_ERROR_START 200
     16 
     17 #define HASH(a, b) ((unsigned int)((a) << 8) | (b))
     18 #define LEN(x)	   (sizeof(x) / sizeof(x[0]))
     19 #define MAX(a, b)  (((a) > (b)) ? (a) : (b))
     20 #define MIN(a, b)  (((a) < (b)) ? (a) : (b))
     21 #define U32(c)	   ((u32)(0x00000000 | (c)))
     22 #define UNUSED(x)  ((void)(x))
     23 
     24 #define TAB ((u32)0x00000009)
     25 
     26 #define ENSURE_SIZE(to, temp, tosize, testsize, fromsize, type)      \
     27 	do                                                           \
     28 	{                                                            \
     29 		if (!to || tosize < testsize)                        \
     30 		{                                                    \
     31 			tosize = fromsize;                           \
     32 			temp   = realloc(to, tosize * sizeof(type)); \
     33 			if (!temp)                                   \
     34 			{                                            \
     35 				perror(PROGRAMNAME ": realloc");     \
     36 				exit(errno);                         \
     37 			}                                            \
     38 			to = temp;                                   \
     39 		}                                                    \
     40 	} while (0)
     41 
     42 #define CALLOC(ptr, ptrtype, nmemb)                     \
     43 	do                                              \
     44 	{                                               \
     45 		ptr = calloc(nmemb, sizeof(ptrtype));   \
     46 		if (!ptr)                               \
     47 		{                                       \
     48 			perror(PROGRAMNAME ": calloc"); \
     49 			exit(errno);                    \
     50 		}                                       \
     51 	} while (0)
     52 
     53 #define MALLOC(ptr, size)                               \
     54 	do                                              \
     55 	{                                               \
     56 		ptr = malloc(size);                     \
     57 		if (!ptr)                               \
     58 		{                                       \
     59 			perror(PROGRAMNAME ": malloc"); \
     60 			exit(errno);                    \
     61 		}                                       \
     62 	} while (0)
     63 
     64 #define REALLOC(ptr, ptrtype, newsize)                   \
     65 	do                                               \
     66 	{                                                \
     67 		ptrtype* newptr = realloc(ptr, newsize); \
     68 		if (!newptr)                             \
     69 		{                                        \
     70 			perror(PROGRAMNAME ": realloc"); \
     71 			exit(errno);                     \
     72 		}                                        \
     73 		ptr = newptr;                            \
     74 	} while (0)
     75 
     76 /* Copy *parg to *ptoken and increase ptoken */
     77 #define CHECKCOPY(token, ptoken, token_size, parg)        \
     78 	do                                                \
     79 	{                                                 \
     80 		if (ptoken + 2 > token + token_size)      \
     81 		{                                         \
     82 			size_t old_size = token_size;     \
     83 			token_size += BUF_DELTA;          \
     84 			REALLOC(token, char, token_size); \
     85 			ptoken = token + old_size - 1;    \
     86 		}                                         \
     87 		*ptoken++ = *parg++;                      \
     88 	} while (0)
     89 
     90 /* Set *pformat to num and increase pformat */
     91 #define CHECKSET(format, pformat, format_size, num)        \
     92 	do                                                 \
     93 	{                                                  \
     94 		if (pformat + 2 > format + format_size)    \
     95 		{                                          \
     96 			size_t old_size = format_size;     \
     97 			format_size += BUF_DELTA;          \
     98 			REALLOC(format, int, format_size); \
     99 			pformat = format + old_size - 1;   \
    100 		}                                          \
    101 		*pformat++ = num;                          \
    102 	} while (0)
    103 
    104 enum {
    105 	ERR_NONE,
    106 	ERR_NO_CL_ARG_PARAM,
    107 	ERR_BAD_CL_ARG,
    108 	ERR_BAD_ALIGN,
    109 	ERR_BAD_NUMBER,
    110 	ERR_BAD_FORMAT_SPEC,
    111 	ERR_BAD_QUOTES_ARG,
    112 	ERR_BAD_SET_SPEC,
    113 	ERR_ISDIR,
    114 	ERR_NOTREG_FILE,
    115 	ERR_UNMATCHED_QUOTE,
    116 	ERR_STREAM_ERROR,
    117 };
    118 
    119 enum { Q_PROCESS, Q_IGNORE };
    120 
    121 enum {
    122 	TABLE_SYMBOLS_ASCII,
    123 	TABLE_SYMBOLS_SINGLE,
    124 	TABLE_SYMBOLS_DOUBLE,
    125 	TABLE_SYMBOLS_EMPTY
    126 };
    127 
    128 enum {
    129 	TABLE_INNER_ASCII_ASCII,
    130 	TABLE_INNER_SINGLE_SINGLE,
    131 	TABLE_INNER_SINGLE_DOUBLE,
    132 	TABLE_INNER_DOUBLE_SINGLE,
    133 	TABLE_INNER_DOUBLE_DOUBLE,
    134 	TABLE_INNER_EMPTY_EMPTY,
    135 	TABLE_INNER_ASCII_EMPTY,
    136 	TABLE_INNER_SINGLE_EMPTY,
    137 	TABLE_INNER_DOUBLE_EMPTY,
    138 	TABLE_INNER_EMPTY_ASCII,
    139 	TABLE_INNER_EMPTY_SINGLE,
    140 	TABLE_INNER_EMPTY_DOUBLE,
    141 };
    142 
    143 typedef enum {
    144 	CMD_NONE,
    145 	CMD_ALIGN,
    146 	CMD_COLUMNS,
    147 	CMD_DELIMITER,
    148 	CMD_FORMAT,
    149 	CMD_QUOTES,
    150 	CMD_SYMBOLS,
    151 	CMD_VERSION,
    152 	CMD_FULL_VERSION
    153 } Command;
    154 
    155 typedef enum { ALIGN_LEFT, ALIGN_CENTER, ALIGN_RIGHT } Alignment;
    156 
    157 static const u32 table_symbols[][9] =
    158 {
    159 	[TABLE_SYMBOLS_ASCII] = {
    160 		// ascii
    161 		U32('+'),	U32('-'),	U32('+'),
    162 		U32('|'),	U32(' '),	U32('|'),
    163 		U32('+'),	U32('-'),	U32('+'),
    164 	},
    165 	[TABLE_SYMBOLS_SINGLE] = {
    166 		// single
    167 		U32(0x250c),	U32(0x2500),	U32(0x2510),
    168 		U32(0x2502),	U32(' '),	U32(0x2502),
    169 		U32(0x2514),	U32(0x2500),	U32(0x2518),
    170 	},
    171 	[TABLE_SYMBOLS_DOUBLE] = {
    172 		// double
    173 		U32(0x2554),	U32(0x2550),	U32(0x2557),
    174 		U32(0x2551),	U32(' '),	U32(0x2551),
    175 		U32(0x255a),	U32(0x2550),	U32(0x255d),
    176 	},
    177 	[TABLE_SYMBOLS_EMPTY] = {
    178 		// empty
    179 		U32(' '),	U32(' '),	U32(' '),
    180 		U32(' '),	U32(' '),	U32(' '),
    181 		U32(' '),	U32(' '),	U32(' '),
    182 	}
    183 };
    184 
    185 static const u32 table_inner_symbols[][3] =
    186 {
    187     [TABLE_INNER_ASCII_ASCII] = {
    188         // ascii -> ascii
    189         U32('+'),
    190         U32('|'),
    191         U32('+'),
    192     },
    193 
    194     [TABLE_INNER_SINGLE_SINGLE] = {
    195         // single -> single
    196         U32(0x252c),
    197         U32(0x2502),
    198         U32(0x2534),
    199     },
    200 
    201     [TABLE_INNER_SINGLE_DOUBLE] = {
    202         // single -> double
    203         U32(0x2565),
    204         U32(0x2551),
    205         U32(0x2568),
    206     },
    207 
    208     [TABLE_INNER_DOUBLE_SINGLE] = {
    209         // double -> single
    210         U32(0x2564),
    211         U32(0x2502),
    212         U32(0x2567),
    213     },
    214 
    215     [TABLE_INNER_DOUBLE_DOUBLE] = {
    216         // double -> double
    217         U32(0x2566),
    218         U32(0x2551),
    219         U32(0x2569),
    220     },
    221 
    222     [TABLE_INNER_EMPTY_EMPTY] = {
    223         // empty -> empty
    224         U32(' '),
    225         U32(' '),
    226         U32(' '),
    227     },
    228 
    229     [TABLE_INNER_ASCII_EMPTY] = {
    230         // ascii -> empty
    231         U32('-'),
    232         U32(' '),
    233         U32('-'),
    234     },
    235 
    236     [TABLE_INNER_SINGLE_EMPTY] = {
    237         // single -> empty
    238         U32(0x2500),
    239         U32(' '),
    240         U32(0x2500),
    241     },
    242 
    243     [TABLE_INNER_DOUBLE_EMPTY] = {
    244         // double -> empty
    245         U32(0x2550),
    246         U32(' '),
    247         U32(0x2550),
    248     },
    249 
    250     [TABLE_INNER_EMPTY_ASCII] = {
    251         // empty -> ascii
    252         U32(' '),
    253         U32('|'),
    254         U32(' '),
    255     },
    256 
    257     [TABLE_INNER_EMPTY_SINGLE] = {
    258         // empty -> single
    259         U32(' '),
    260         U32(0x2502),
    261         U32(' '),
    262     },
    263 
    264     [TABLE_INNER_EMPTY_DOUBLE] = {
    265         // empty -> double
    266         U32(' '),
    267         U32(0x2551),
    268         U32(' '),
    269     }
    270 
    271 };