1#ifndef __VTERM_INTERNAL_H__
2#define __VTERM_INTERNAL_H__
3
4#include "vterm.h"
5
6#include <stdarg.h>
7
8#if defined(__GNUC__) && __GNUC__ > 2
9# define INTERNAL __attribute__((visibility("internal")))
10#else
11# define INTERNAL
12#endif
13
14typedef struct VTermEncoding VTermEncoding;
15
16typedef struct {
17  VTermEncoding *enc;
18
19  // This size should be increased if required by other stateful encodings
20  char           data[4*sizeof(uint32_t)];
21} VTermEncodingInstance;
22
23struct VTermPen
24{
25  VTermColor fg;
26  VTermColor bg;
27  unsigned int bold:1;
28  unsigned int underline:2;
29  unsigned int italic:1;
30  unsigned int blink:1;
31  unsigned int reverse:1;
32  unsigned int strike:1;
33  unsigned int font:4; /* To store 0-9 */
34};
35
36static inline int vterm_color_equal(VTermColor a, VTermColor b)
37{
38  return a.red == b.red && a.green == b.green && a.blue == b.blue;
39}
40
41struct VTermState
42{
43  VTerm *vt;
44
45  const VTermStateCallbacks *callbacks;
46  void *cbdata;
47
48  int rows;
49  int cols;
50
51  /* Current cursor position */
52  VTermPos pos;
53
54  int at_phantom; /* True if we're on the "81st" phantom column to defer a wraparound */
55
56  int scrollregion_top;
57  int scrollregion_bottom; /* -1 means unbounded */
58#define SCROLLREGION_BOTTOM(state) ((state)->scrollregion_bottom > -1 ? (state)->scrollregion_bottom : (state)->rows)
59  int scrollregion_left;
60#define SCROLLREGION_LEFT(state)  ((state)->mode.leftrightmargin ? (state)->scrollregion_left : 0)
61  int scrollregion_right; /* -1 means unbounded */
62#define SCROLLREGION_RIGHT(state) ((state)->mode.leftrightmargin && (state)->scrollregion_right > -1 ? (state)->scrollregion_right : (state)->cols)
63
64  /* Bitvector of tab stops */
65  unsigned char *tabstops;
66
67  VTermLineInfo *lineinfo;
68#define ROWWIDTH(state,row) ((state)->lineinfo[(row)].doublewidth ? ((state)->cols / 2) : (state)->cols)
69#define THISROWWIDTH(state) ROWWIDTH(state, (state)->pos.row)
70
71  /* Mouse state */
72  int mouse_col, mouse_row;
73  int mouse_buttons;
74  int mouse_flags;
75  enum { MOUSE_X10, MOUSE_UTF8, MOUSE_SGR, MOUSE_RXVT } mouse_protocol;
76
77  /* Last glyph output, for Unicode recombining purposes */
78  uint32_t *combine_chars;
79  size_t combine_chars_size; // Number of ELEMENTS in the above
80  int combine_width; // The width of the glyph above
81  VTermPos combine_pos;   // Position before movement
82
83  struct {
84    int keypad:1;
85    int cursor:1;
86    int autowrap:1;
87    int insert:1;
88    int newline:1;
89    int cursor_visible:1;
90    int cursor_blink:1;
91    unsigned int cursor_shape:2;
92    int alt_screen:1;
93    int origin:1;
94    int screen:1;
95    int leftrightmargin:1;
96  } mode;
97
98  VTermEncodingInstance encoding[4], encoding_utf8;
99  int gl_set, gr_set, gsingle_set;
100
101  struct VTermPen pen;
102
103  VTermColor default_fg;
104  VTermColor default_bg;
105  VTermColor colors[16]; // Store the 8 ANSI and the 8 ANSI high-brights only
106
107  int fg_index;
108  int bg_index;
109  int bold_is_highbright;
110
111  unsigned int protected_cell : 1;
112
113  /* Saved state under DEC mode 1048/1049 */
114  struct {
115    VTermPos pos;
116    struct VTermPen pen;
117
118    struct {
119      int cursor_visible:1;
120      int cursor_blink:1;
121      unsigned int cursor_shape:2;
122    } mode;
123  } saved;
124};
125
126struct VTerm
127{
128  VTermAllocatorFunctions *allocator;
129  void *allocdata;
130
131  int rows;
132  int cols;
133
134  struct {
135    int utf8:1;
136    int ctrl8bit:1;
137  } mode;
138
139  enum VTermParserState {
140    NORMAL,
141    CSI,
142    OSC,
143    DCS,
144    ESC,
145    ESC_IN_OSC,
146    ESC_IN_DCS,
147  } parser_state;
148  const VTermParserCallbacks *parser_callbacks;
149  void *cbdata;
150
151  /* len == malloc()ed size; cur == number of valid bytes */
152  char  *strbuffer;
153  size_t strbuffer_len;
154  size_t strbuffer_cur;
155
156  char  *outbuffer;
157  size_t outbuffer_len;
158  size_t outbuffer_cur;
159
160  VTermState *state;
161  VTermScreen *screen;
162};
163
164struct VTermEncoding {
165  void (*init) (VTermEncoding *enc, void *data);
166  void (*decode)(VTermEncoding *enc, void *data,
167                 uint32_t cp[], int *cpi, int cplen,
168                 const char bytes[], size_t *pos, size_t len);
169};
170
171typedef enum {
172  ENC_UTF8,
173  ENC_SINGLE_94
174} VTermEncodingType;
175
176void *vterm_allocator_malloc(VTerm *vt, size_t size);
177void  vterm_allocator_free(VTerm *vt, void *ptr);
178
179void vterm_push_output_bytes(VTerm *vt, const char *bytes, size_t len);
180void vterm_push_output_vsprintf(VTerm *vt, const char *format, va_list args);
181void vterm_push_output_sprintf(VTerm *vt, const char *format, ...);
182void vterm_push_output_sprintf_ctrl(VTerm *vt, unsigned char ctrl, const char *fmt, ...);
183void vterm_push_output_sprintf_dcs(VTerm *vt, const char *fmt, ...);
184
185void vterm_state_free(VTermState *state);
186
187void vterm_state_newpen(VTermState *state);
188void vterm_state_resetpen(VTermState *state);
189void vterm_state_setpen(VTermState *state, const long args[], int argcount);
190int  vterm_state_getpen(VTermState *state, long args[], int argcount);
191void vterm_state_savepen(VTermState *state, int save);
192
193enum {
194  C1_SS3 = 0x8f,
195  C1_DCS = 0x90,
196  C1_CSI = 0x9b,
197  C1_ST  = 0x9c,
198};
199
200void vterm_state_push_output_sprintf_CSI(VTermState *vts, const char *format, ...);
201
202void vterm_screen_free(VTermScreen *screen);
203
204VTermEncoding *vterm_lookup_encoding(VTermEncodingType type, char designation);
205
206int vterm_unicode_width(int codepoint);
207int vterm_unicode_is_combining(int codepoint);
208
209#endif
210