Skip to content

Commit 6332174

Browse files
committed
py: compiler supports string juxtaposition=concatenation.
1 parent db4c361 commit 6332174

File tree

1 file changed

+25
-7
lines changed

1 file changed

+25
-7
lines changed

py/compile.c

Lines changed: 25 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2050,18 +2050,36 @@ void compile_power_dbl_star(compiler_t *comp, py_parse_node_struct_t *pns) {
20502050

20512051
void compile_atom_string(compiler_t *comp, py_parse_node_struct_t *pns) {
20522052
// a list of strings
2053-
EMIT(load_const_verbatim_start);
2054-
EMIT(load_const_verbatim_str, "'");
2053+
2054+
// check type of list (string or bytes) and count total number of bytes
20552055
int n = PY_PARSE_NODE_STRUCT_NUM_NODES(pns);
2056+
int n_bytes = 0;
2057+
int string_kind = PY_PARSE_NODE_NULL;
20562058
for (int i = 0; i < n; i++) {
2057-
// TODO allow concatenation of either strings or bytes, but not mixed
20582059
assert(PY_PARSE_NODE_IS_LEAF(pns->nodes[i]));
2059-
assert(PY_PARSE_NODE_LEAF_KIND(pns->nodes[i]) == PY_PARSE_NODE_STRING);
2060+
int pn_kind = PY_PARSE_NODE_LEAF_KIND(pns->nodes[i]);
2061+
assert(pn_kind == PY_PARSE_NODE_STRING || pn_kind == PY_PARSE_NODE_BYTES);
2062+
if (i == 0) {
2063+
string_kind = pn_kind;
2064+
} else if (pn_kind != string_kind) {
2065+
printf("SyntaxError: cannot mix bytes and nonbytes literals\n");
2066+
return;
2067+
}
20602068
const char *str = qstr_str(PY_PARSE_NODE_LEAF_ARG(pns->nodes[i]));
2061-
EMIT(load_const_verbatim_strn, str, strlen(str));
2069+
n_bytes += strlen(str);
20622070
}
2063-
EMIT(load_const_verbatim_str, "'");
2064-
EMIT(load_const_verbatim_end);
2071+
2072+
// allocate memory for concatenated string/bytes
2073+
char *cat_str = m_new(char, n_bytes + 1);
2074+
cat_str[0] = '\0';
2075+
2076+
// concatenate string/bytes
2077+
for (int i = 0; i < n; i++) {
2078+
const char *str = qstr_str(PY_PARSE_NODE_LEAF_ARG(pns->nodes[i]));
2079+
strcat(cat_str, str);
2080+
}
2081+
2082+
EMIT(load_const_str, qstr_from_str_take(cat_str), string_kind == PY_PARSE_NODE_BYTES);
20652083
}
20662084

20672085
// pns needs to have 2 nodes, first is lhs of comprehension, second is PN_comp_for node

0 commit comments

Comments
 (0)