mirror of
https://github.com/kovidgoyal/kitty.git
synced 2025-12-13 20:36:22 +01:00
391 lines
12 KiB
C
Generated
391 lines
12 KiB
C
Generated
// This file is generated by apc_parsers.py do not edit!
|
|
|
|
#pragma once
|
|
|
|
#include "base64.h"
|
|
|
|
static inline void parse_graphics_code(PS *self, uint8_t *parser_buf,
|
|
const size_t parser_buf_pos) {
|
|
unsigned int pos = 1;
|
|
|
|
enum PARSER_STATES { KEY, EQUAL, UINT, INT, FLAG, AFTER_VALUE, PAYLOAD };
|
|
enum PARSER_STATES state = KEY, value_state = FLAG;
|
|
GraphicsCommand g = {0};
|
|
unsigned int i, code;
|
|
uint64_t lcode;
|
|
int64_t accumulator;
|
|
bool is_negative;
|
|
(void)is_negative;
|
|
size_t sz;
|
|
|
|
enum KEYS {
|
|
action = 'a',
|
|
delete_action = 'd',
|
|
transmission_type = 't',
|
|
compressed = 'o',
|
|
format = 'f',
|
|
more = 'm',
|
|
id = 'i',
|
|
image_number = 'I',
|
|
placement_id = 'p',
|
|
quiet = 'q',
|
|
width = 'w',
|
|
height = 'h',
|
|
x_offset = 'x',
|
|
y_offset = 'y',
|
|
data_height = 'v',
|
|
data_width = 's',
|
|
data_sz = 'S',
|
|
data_offset = 'O',
|
|
num_cells = 'c',
|
|
num_lines = 'r',
|
|
cell_x_offset = 'X',
|
|
cell_y_offset = 'Y',
|
|
z_index = 'z',
|
|
cursor_movement = 'C',
|
|
unicode_placement = 'U',
|
|
parent_id = 'P',
|
|
parent_placement_id = 'Q',
|
|
offset_from_parent_x = 'H',
|
|
offset_from_parent_y = 'V'
|
|
};
|
|
|
|
enum KEYS key = 'a';
|
|
if (parser_buf[pos] == ';')
|
|
state = AFTER_VALUE;
|
|
|
|
while (pos < parser_buf_pos) {
|
|
switch (state) {
|
|
case KEY:
|
|
key = parser_buf[pos++];
|
|
state = EQUAL;
|
|
switch (key) {
|
|
case action:
|
|
value_state = FLAG;
|
|
break;
|
|
case delete_action:
|
|
value_state = FLAG;
|
|
break;
|
|
case transmission_type:
|
|
value_state = FLAG;
|
|
break;
|
|
case compressed:
|
|
value_state = FLAG;
|
|
break;
|
|
case format:
|
|
value_state = UINT;
|
|
break;
|
|
case more:
|
|
value_state = UINT;
|
|
break;
|
|
case id:
|
|
value_state = UINT;
|
|
break;
|
|
case image_number:
|
|
value_state = UINT;
|
|
break;
|
|
case placement_id:
|
|
value_state = UINT;
|
|
break;
|
|
case quiet:
|
|
value_state = UINT;
|
|
break;
|
|
case width:
|
|
value_state = UINT;
|
|
break;
|
|
case height:
|
|
value_state = UINT;
|
|
break;
|
|
case x_offset:
|
|
value_state = UINT;
|
|
break;
|
|
case y_offset:
|
|
value_state = UINT;
|
|
break;
|
|
case data_height:
|
|
value_state = UINT;
|
|
break;
|
|
case data_width:
|
|
value_state = UINT;
|
|
break;
|
|
case data_sz:
|
|
value_state = UINT;
|
|
break;
|
|
case data_offset:
|
|
value_state = UINT;
|
|
break;
|
|
case num_cells:
|
|
value_state = UINT;
|
|
break;
|
|
case num_lines:
|
|
value_state = UINT;
|
|
break;
|
|
case cell_x_offset:
|
|
value_state = UINT;
|
|
break;
|
|
case cell_y_offset:
|
|
value_state = UINT;
|
|
break;
|
|
case z_index:
|
|
value_state = INT;
|
|
break;
|
|
case cursor_movement:
|
|
value_state = UINT;
|
|
break;
|
|
case unicode_placement:
|
|
value_state = UINT;
|
|
break;
|
|
case parent_id:
|
|
value_state = UINT;
|
|
break;
|
|
case parent_placement_id:
|
|
value_state = UINT;
|
|
break;
|
|
case offset_from_parent_x:
|
|
value_state = INT;
|
|
break;
|
|
case offset_from_parent_y:
|
|
value_state = INT;
|
|
break;
|
|
default:
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, invalid key "
|
|
"character: 0x%x",
|
|
key);
|
|
return;
|
|
}
|
|
break;
|
|
|
|
case EQUAL:
|
|
if (parser_buf[pos++] != '=') {
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, no = after key, "
|
|
"found: 0x%x instead",
|
|
parser_buf[pos - 1]);
|
|
return;
|
|
}
|
|
state = value_state;
|
|
break;
|
|
|
|
case FLAG:
|
|
switch (key) {
|
|
|
|
case action: {
|
|
g.action = parser_buf[pos++];
|
|
if (g.action != 'T' && g.action != 'a' && g.action != 'c' &&
|
|
g.action != 'd' && g.action != 'f' && g.action != 'p' &&
|
|
g.action != 'q' && g.action != 't') {
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, unknown flag "
|
|
"value for action: 0x%x",
|
|
g.action);
|
|
return;
|
|
};
|
|
} break;
|
|
|
|
case delete_action: {
|
|
g.delete_action = parser_buf[pos++];
|
|
if (g.delete_action != 'A' && g.delete_action != 'C' &&
|
|
g.delete_action != 'F' && g.delete_action != 'I' &&
|
|
g.delete_action != 'N' && g.delete_action != 'P' &&
|
|
g.delete_action != 'Q' && g.delete_action != 'R' &&
|
|
g.delete_action != 'X' && g.delete_action != 'Y' &&
|
|
g.delete_action != 'Z' && g.delete_action != 'a' &&
|
|
g.delete_action != 'c' && g.delete_action != 'f' &&
|
|
g.delete_action != 'i' && g.delete_action != 'n' &&
|
|
g.delete_action != 'p' && g.delete_action != 'q' &&
|
|
g.delete_action != 'r' && g.delete_action != 'x' &&
|
|
g.delete_action != 'y' && g.delete_action != 'z') {
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, unknown flag "
|
|
"value for delete_action: 0x%x",
|
|
g.delete_action);
|
|
return;
|
|
};
|
|
} break;
|
|
|
|
case transmission_type: {
|
|
g.transmission_type = parser_buf[pos++];
|
|
if (g.transmission_type != 'd' && g.transmission_type != 'f' &&
|
|
g.transmission_type != 's' && g.transmission_type != 't') {
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, unknown flag "
|
|
"value for transmission_type: 0x%x",
|
|
g.transmission_type);
|
|
return;
|
|
};
|
|
} break;
|
|
|
|
case compressed: {
|
|
g.compressed = parser_buf[pos++];
|
|
if (g.compressed != 'z') {
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, unknown flag "
|
|
"value for compressed: 0x%x",
|
|
g.compressed);
|
|
return;
|
|
};
|
|
} break;
|
|
|
|
default:
|
|
break;
|
|
}
|
|
state = AFTER_VALUE;
|
|
break;
|
|
|
|
case INT:
|
|
#define READ_UINT \
|
|
for (i = pos, accumulator = 0; i < MIN(parser_buf_pos, pos + 10); i++) { \
|
|
int64_t n = parser_buf[i] - '0'; \
|
|
if (n < 0 || n > 9) \
|
|
break; \
|
|
accumulator += n * digit_multipliers[i - pos]; \
|
|
} \
|
|
if (i == pos) { \
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, expecting an " \
|
|
"integer value for key: %c", \
|
|
key & 0xFF); \
|
|
return; \
|
|
} \
|
|
lcode = accumulator / digit_multipliers[i - pos - 1]; \
|
|
pos = i; \
|
|
if (lcode > UINT32_MAX) { \
|
|
REPORT_ERROR( \
|
|
"Malformed GraphicsCommand control block, number is too large"); \
|
|
return; \
|
|
} \
|
|
code = lcode;
|
|
|
|
is_negative = false;
|
|
if (parser_buf[pos] == '-') {
|
|
is_negative = true;
|
|
pos++;
|
|
}
|
|
#define I(x) \
|
|
case x: \
|
|
g.x = is_negative ? 0 - (int32_t)code : (int32_t)code; \
|
|
break
|
|
READ_UINT;
|
|
switch (key) {
|
|
I(z_index);
|
|
I(offset_from_parent_x);
|
|
I(offset_from_parent_y);
|
|
default:
|
|
break;
|
|
}
|
|
state = AFTER_VALUE;
|
|
break;
|
|
#undef I
|
|
case UINT:
|
|
READ_UINT;
|
|
#define U(x) \
|
|
case x: \
|
|
g.x = code; \
|
|
break
|
|
switch (key) {
|
|
U(format);
|
|
U(more);
|
|
U(id);
|
|
U(image_number);
|
|
U(placement_id);
|
|
U(quiet);
|
|
U(width);
|
|
U(height);
|
|
U(x_offset);
|
|
U(y_offset);
|
|
U(data_height);
|
|
U(data_width);
|
|
U(data_sz);
|
|
U(data_offset);
|
|
U(num_cells);
|
|
U(num_lines);
|
|
U(cell_x_offset);
|
|
U(cell_y_offset);
|
|
U(cursor_movement);
|
|
U(unicode_placement);
|
|
U(parent_id);
|
|
U(parent_placement_id);
|
|
default:
|
|
break;
|
|
}
|
|
state = AFTER_VALUE;
|
|
break;
|
|
#undef U
|
|
#undef READ_UINT
|
|
|
|
case AFTER_VALUE:
|
|
switch (parser_buf[pos++]) {
|
|
default:
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, expecting a , "
|
|
"or semi-colon after a value, found: 0x%x",
|
|
parser_buf[pos - 1]);
|
|
return;
|
|
case ',':
|
|
state = KEY;
|
|
break;
|
|
case ';':
|
|
state = PAYLOAD;
|
|
break;
|
|
}
|
|
break;
|
|
|
|
case PAYLOAD: {
|
|
sz = parser_buf_pos - pos;
|
|
g.payload_sz = MAX(BUF_EXTRA, sz);
|
|
if (!base64_decode8(parser_buf + pos, sz, parser_buf, &g.payload_sz)) {
|
|
g.payload_sz = MAX(BUF_EXTRA, sz);
|
|
REPORT_ERROR("Failed to parse GraphicsCommand command payload with "
|
|
"error: invalid base64 data in chunk of size: %zu "
|
|
"with output buffer size: %zu",
|
|
sz, g.payload_sz);
|
|
return;
|
|
}
|
|
pos = parser_buf_pos;
|
|
} break;
|
|
|
|
} // end switch
|
|
} // end while
|
|
|
|
switch (state) {
|
|
case EQUAL:
|
|
REPORT_ERROR("Malformed GraphicsCommand control block, no = after key");
|
|
return;
|
|
case INT:
|
|
case UINT:
|
|
REPORT_ERROR(
|
|
"Malformed GraphicsCommand control block, expecting an integer value");
|
|
return;
|
|
case FLAG:
|
|
REPORT_ERROR(
|
|
"Malformed GraphicsCommand control block, expecting a flag value");
|
|
return;
|
|
default:
|
|
break;
|
|
}
|
|
|
|
REPORT_VA_COMMAND(
|
|
"K s {sc sc sc sc sI sI sI sI sI sI sI sI sI sI sI sI sI sI sI sI sI sI "
|
|
"sI sI sI sI si si si ss#}",
|
|
self->window_id, "graphics_command",
|
|
|
|
"action", g.action, "delete_action", g.delete_action, "transmission_type",
|
|
g.transmission_type, "compressed", g.compressed,
|
|
|
|
"format", (unsigned int)g.format, "more", (unsigned int)g.more, "id",
|
|
(unsigned int)g.id, "image_number", (unsigned int)g.image_number,
|
|
"placement_id", (unsigned int)g.placement_id, "quiet",
|
|
(unsigned int)g.quiet, "width", (unsigned int)g.width, "height",
|
|
(unsigned int)g.height, "x_offset", (unsigned int)g.x_offset, "y_offset",
|
|
(unsigned int)g.y_offset, "data_height", (unsigned int)g.data_height,
|
|
"data_width", (unsigned int)g.data_width, "data_sz",
|
|
(unsigned int)g.data_sz, "data_offset", (unsigned int)g.data_offset,
|
|
"num_cells", (unsigned int)g.num_cells, "num_lines",
|
|
(unsigned int)g.num_lines, "cell_x_offset", (unsigned int)g.cell_x_offset,
|
|
"cell_y_offset", (unsigned int)g.cell_y_offset, "cursor_movement",
|
|
(unsigned int)g.cursor_movement, "unicode_placement",
|
|
(unsigned int)g.unicode_placement, "parent_id", (unsigned int)g.parent_id,
|
|
"parent_placement_id", (unsigned int)g.parent_placement_id,
|
|
|
|
"z_index", (int)g.z_index, "offset_from_parent_x",
|
|
(int)g.offset_from_parent_x, "offset_from_parent_y",
|
|
(int)g.offset_from_parent_y,
|
|
|
|
"", (char *)parser_buf, g.payload_sz);
|
|
|
|
screen_handle_graphics_command(self->screen, &g, parser_buf);
|
|
}
|