added backslash escaping (to try it, use --test --test)

git-svn-id: https://svn.code.sf.net/p/acme-crossass/code-0/trunk@180 4df02467-bbd4-4a76-a152-e7ce94205b78
This commit is contained in:
marcobaye 2020-05-19 17:35:04 +00:00
parent 916bf9cbc8
commit ba168a3ea5

View File

@ -351,17 +351,29 @@ void Input_ensure_EOS(void) // Now GotByte = first char to test
// returns 1 on errors (unterminated, escaping error) // returns 1 on errors (unterminated, escaping error)
int Input_quoted_to_dynabuf(char closing_quote) int Input_quoted_to_dynabuf(char closing_quote)
{ {
boolean escaped = FALSE;
//DYNABUF_CLEAR(GlobalDynaBuf); // do not clear, caller might want to append to existing contents (TODO - check!) //DYNABUF_CLEAR(GlobalDynaBuf); // do not clear, caller might want to append to existing contents (TODO - check!)
for (;;) { for (;;) {
GetQuotedByte(); GetQuotedByte();
if (GotByte == CHAR_EOS) if (GotByte == CHAR_EOS)
return 1; // unterminated string constant; GetQuotedByte will have complained already return 1; // unterminated string constant; GetQuotedByte will have complained already
// FIXME - this will fail with backslash escaping! if (escaped) {
// it's not enough to check the previous char for backslash, because it might be an escaped backslash... // previous byte was backslash, so do not check for terminator nor backslash
if (GotByte == closing_quote) escaped = FALSE;
return 0; // ok // do not actually _convert_ escape sequences to their target byte, that is done by Input_unescape_dynabuf() below!
// TODO - but maybe check for illegal escape sequences?
// at the moment checking is only done when the string
// gets used for something...
} else {
// non-escaped: only terminator and backslash are of interest
if (GotByte == closing_quote)
return 0; // ok
if ((GotByte == '\\') && (config.backslash_escaping))
escaped = TRUE;
}
DYNABUF_APPEND(GlobalDynaBuf, GotByte); DYNABUF_APPEND(GlobalDynaBuf, GotByte);
} }
} }
@ -369,14 +381,43 @@ int Input_quoted_to_dynabuf(char closing_quote)
// process backslash escapes in GlobalDynaBuf (so size might shrink) // process backslash escapes in GlobalDynaBuf (so size might shrink)
// returns 1 on errors (escaping errors) // returns 1 on errors (escaping errors)
// TODO - check: if this is only ever called directly after Input_quoted_to_dynabuf, integrate that call here? // TODO - check: if this is only ever called directly after Input_quoted_to_dynabuf, integrate that call here?
int Input_unescape_dynabuf(int start_index) int Input_unescape_dynabuf(int read_index)
{ {
int write_index;
char byte;
boolean escaped;
if (!config.backslash_escaping) if (!config.backslash_escaping)
return 0; // ok return 0; // ok
// FIXME - implement backslash escaping! write_index = read_index;
// TODO - shorten GlobalDynaBuf->size accordingly escaped = FALSE;
// CAUTION - contents of dynabuf are not terminated! // CAUTION - contents of dynabuf are not terminated:
while (read_index < GlobalDynaBuf->size) {
byte = GLOBALDYNABUF_CURRENT[read_index++];
if (escaped) {
switch (byte) {
case '\\':
case '\'':
case '"':
break;
// TODO - convert '0' to 0, 'n' to 10, 'a' to BEL, etc.
default:
Throw_error("Unsupported backslash sequence."); // TODO - add to docs
}
GLOBALDYNABUF_CURRENT[write_index++] = byte;
escaped = FALSE;
} else {
if (byte == '\\') {
escaped = TRUE;
} else {
GLOBALDYNABUF_CURRENT[write_index++] = byte;
}
}
}
if (escaped)
Bug_found("PartialEscapeSequence", 0); // FIXME - add to docs!
GlobalDynaBuf->size = write_index;
return 0; // ok return 0; // ok
} }