Skip to content

Commit 2410c70

Browse files
MarkusLassilanordicjm
authored andcommitted
applications: serial_lte_modem: Fix datamode quit_str handling
Fixes an issue where non-default quit strings, with non-repeating characters, such as "abc" and "aabbcc", did not interpret the start of the quit string properly, if the last characters of the data collided with the quit string start. For example, "*aabc" and "*aaabbcc" with our example quit strings. Signed-off-by: Markus Lassila <[email protected]>
1 parent 2266d1f commit 2410c70

File tree

1 file changed

+32
-24
lines changed

1 file changed

+32
-24
lines changed

applications/serial_lte_modem/src/slm_at_host.c

Lines changed: 32 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -220,21 +220,14 @@ K_TIMER_DEFINE(inactivity_timer, inactivity_timer_handler, NULL);
220220
/* Search for quit_str and send data prior to that. Tracks quit_str over several calls. */
221221
static size_t raw_rx_handler(const uint8_t *buf, const size_t len)
222222
{
223+
k_mutex_lock(&mutex_data, K_FOREVER);
224+
223225
const char *const quit_str = CONFIG_SLM_DATAMODE_TERMINATOR;
224226
size_t processed;
225227
bool quit_str_match = false;
226-
bool prev_quit_str_match = false;
227-
uint8_t quit_str_match_count;
228-
uint8_t prev_quit_str_match_count;
229-
230-
k_mutex_lock(&mutex_data, K_FOREVER);
231-
232-
/* Initialize from previous time.*/
233-
prev_quit_str_match_count = quit_str_partial_match;
234-
quit_str_match_count = prev_quit_str_match_count;
235-
if (prev_quit_str_match_count != 0) {
236-
prev_quit_str_match = true;
237-
}
228+
uint8_t quit_str_match_count = quit_str_partial_match;
229+
uint8_t prev_quit_str_match_count = quit_str_partial_match;
230+
uint8_t prev_quit_str_match_count_original = quit_str_partial_match;
238231

239232
/* Find quit_str or partial match at the end of the buffer. */
240233
for (processed = 0; processed < len && quit_str_match == false; processed++) {
@@ -243,22 +236,37 @@ static size_t raw_rx_handler(const uint8_t *buf, const size_t len)
243236
if (quit_str_match_count == strlen(quit_str)) {
244237
quit_str_match = true;
245238
}
246-
} else {
247-
/* No match. Possible previous partial quit_str match is data. */
248-
quit_str_match_count = 0;
249-
prev_quit_str_match = false;
239+
} else if (quit_str_match_count > 0) {
240+
/* Check if we match a beginning of a new quit_str.
241+
* We either match the first character, or in the edge case of
242+
* quit_str starting with multiple same characters, e.g. "aaabbb",
243+
* we match all but the current character (with input aaaa).
244+
*/
245+
for (int i = 0; i < quit_str_match_count; i++) {
246+
if (buf[processed] != quit_str[i]) {
247+
quit_str_match_count = i;
248+
break;
249+
}
250+
}
251+
if (quit_str_match_count == 0) {
252+
/* No match.
253+
* Previous partial quit_str is data.
254+
*/
255+
prev_quit_str_match_count = 0;
256+
} else if (prev_quit_str_match_count > 0) {
257+
/* Partial match.
258+
* Part of the previous partial quit_str is data.
259+
*/
260+
prev_quit_str_match_count--;
261+
}
250262
}
251263
}
252264

253-
if (prev_quit_str_match == false) {
254-
/* Write data which was previously interpreted as a possible partial quit_str. */
255-
write_data_buf(quit_str, prev_quit_str_match_count);
265+
/* Write data which was previously interpreted as a possible partial quit_str. */
266+
write_data_buf(quit_str, prev_quit_str_match_count_original - prev_quit_str_match_count);
256267

257-
/* Write data from buf until the start of the possible (partial) quit_str. */
258-
write_data_buf(buf, processed - quit_str_match_count);
259-
} else {
260-
/* Nothing to write this round.*/
261-
}
268+
/* Write data from buf until the start of the possible (partial) quit_str. */
269+
write_data_buf(buf, processed - (quit_str_match_count - prev_quit_str_match_count));
262270

263271
if (quit_str_match) {
264272
raw_send(SLM_DATAMODE_FLAGS_NONE);

0 commit comments

Comments
 (0)