Skip to content

Commit d801e69

Browse files
bjarki-andreasencarlescufi
authored andcommitted
modem: chat: Implement TRANSMIT_IDLE event
Refactors modem chat module to use TRANSMIT_IDLE event instead of polling when transmitting, cleaning up the transmit handler by combining duplicate code and using an internal state instead of multiple iterators to track send state. Signed-off-by: Bjarki Arge Andreasen <[email protected]>
1 parent 27b0d4e commit d801e69

File tree

2 files changed

+71
-86
lines changed

2 files changed

+71
-86
lines changed

include/zephyr/modem/chat.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -240,8 +240,8 @@ struct modem_chat {
240240
struct k_sem script_stopped_sem;
241241

242242
/* Script sending */
243-
uint16_t script_send_request_pos;
244-
uint16_t script_send_delimiter_pos;
243+
enum modem_chat_script_send_state script_send_state;
244+
uint16_t script_send_pos;
245245
struct k_work script_send_work;
246246
struct k_work_delayable script_send_timeout_work;
247247

subsys/modem/modem_chat.c

Lines changed: 69 additions & 84 deletions
Original file line numberDiff line numberDiff line change
@@ -110,13 +110,16 @@ static void modem_chat_script_stop(struct modem_chat *chat, enum modem_chat_scri
110110
k_sem_give(&chat->script_stopped_sem);
111111
}
112112

113-
static void modem_chat_script_send(struct modem_chat *chat)
113+
static void modem_chat_set_script_send_state(struct modem_chat *chat,
114+
enum modem_chat_script_send_state state)
114115
{
115-
/* Initialize script send work */
116-
chat->script_send_request_pos = 0;
117-
chat->script_send_delimiter_pos = 0;
116+
chat->script_send_pos = 0;
117+
chat->script_send_state = state;
118+
}
118119

119-
/* Schedule script send work */
120+
static void modem_chat_script_send(struct modem_chat *chat)
121+
{
122+
modem_chat_set_script_send_state(chat, MODEM_CHAT_SCRIPT_SEND_STATE_REQUEST);
120123
k_work_submit(&chat->script_send_work);
121124
}
122125

@@ -219,119 +222,92 @@ static void modem_chat_script_abort_handler(struct k_work *item)
219222
modem_chat_script_stop(chat, MODEM_CHAT_SCRIPT_RESULT_ABORT);
220223
}
221224

222-
static bool modem_chat_script_send_request(struct modem_chat *chat)
225+
static bool modem_chat_script_chat_is_no_response(struct modem_chat *chat)
223226
{
224227
const struct modem_chat_script_chat *script_chat =
225228
&chat->script->script_chats[chat->script_chat_it];
226229

227-
uint8_t *script_chat_request_start;
228-
uint16_t script_chat_request_remaining;
229-
int ret;
230-
231-
/* Validate data to send */
232-
if (script_chat->request_size == chat->script_send_request_pos) {
233-
return true;
234-
}
235-
236-
script_chat_request_start = (uint8_t *)&script_chat->request[chat->script_send_request_pos];
237-
script_chat_request_remaining = script_chat->request_size - chat->script_send_request_pos;
238-
239-
/* Send data through pipe */
240-
ret = modem_pipe_transmit(chat->pipe, script_chat_request_start,
241-
script_chat_request_remaining);
242-
243-
/* Validate transmit successful */
244-
if (ret < 1) {
245-
return false;
246-
}
247-
248-
/* Update script send position */
249-
chat->script_send_request_pos += (uint16_t)ret;
230+
return (script_chat->response_matches_size == 0) ? true : false;
231+
}
250232

251-
/* Check if data remains */
252-
if (chat->script_send_request_pos < script_chat->request_size) {
253-
return false;
254-
}
233+
static uint16_t modem_chat_script_chat_get_send_timeout(struct modem_chat *chat)
234+
{
235+
const struct modem_chat_script_chat *script_chat =
236+
&chat->script->script_chats[chat->script_chat_it];
255237

256-
return true;
238+
return script_chat->timeout;
257239
}
258240

259-
static bool modem_chat_script_send_delimiter(struct modem_chat *chat)
241+
/* Returns true when request part has been sent */
242+
static bool modem_chat_send_script_request_part(struct modem_chat *chat)
260243
{
261-
uint8_t *script_chat_delimiter_start;
262-
uint8_t script_chat_delimiter_remaining;
263-
int ret;
244+
const struct modem_chat_script_chat *script_chat =
245+
&chat->script->script_chats[chat->script_chat_it];
264246

265-
/* Validate data to send */
266-
if (chat->delimiter_size == chat->script_send_delimiter_pos) {
267-
return true;
268-
}
247+
uint8_t *request_part;
248+
uint16_t request_size;
249+
uint16_t request_part_size;
250+
int ret;
269251

270-
script_chat_delimiter_start = (uint8_t *)&chat->delimiter[chat->script_send_delimiter_pos];
271-
script_chat_delimiter_remaining = chat->delimiter_size - chat->script_send_delimiter_pos;
252+
switch (chat->script_send_state) {
253+
case MODEM_CHAT_SCRIPT_SEND_STATE_REQUEST:
254+
request_part = (uint8_t *)(&script_chat->request[chat->script_send_pos]);
255+
request_size = script_chat->request_size;
256+
break;
272257

273-
/* Send data through pipe */
274-
ret = modem_pipe_transmit(chat->pipe, script_chat_delimiter_start,
275-
script_chat_delimiter_remaining);
258+
case MODEM_CHAT_SCRIPT_SEND_STATE_DELIMITER:
259+
request_part = (uint8_t *)(&chat->delimiter[chat->script_send_pos]);
260+
request_size = chat->delimiter_size;
261+
break;
276262

277-
/* Validate transmit successful */
278-
if (ret < 1) {
263+
default:
279264
return false;
280265
}
281266

282-
/* Update script send position */
283-
chat->script_send_delimiter_pos += (uint8_t)ret;
284-
285-
/* Check if data remains */
286-
if (chat->script_send_delimiter_pos < chat->delimiter_size) {
267+
request_part_size = request_size - chat->script_send_pos;
268+
ret = modem_pipe_transmit(chat->pipe, request_part, request_part_size);
269+
if (ret < 1) {
287270
return false;
288271
}
289272

290-
return true;
291-
}
292-
293-
static bool modem_chat_script_chat_is_no_response(struct modem_chat *chat)
294-
{
295-
const struct modem_chat_script_chat *script_chat =
296-
&chat->script->script_chats[chat->script_chat_it];
297-
298-
return (script_chat->response_matches_size == 0) ? true : false;
299-
}
273+
chat->script_send_pos += (uint16_t)ret;
300274

301-
static uint16_t modem_chat_script_chat_get_send_timeout(struct modem_chat *chat)
302-
{
303-
const struct modem_chat_script_chat *script_chat =
304-
&chat->script->script_chats[chat->script_chat_it];
305-
306-
return script_chat->timeout;
275+
/* Return true if all data was sent */
276+
return request_size <= chat->script_send_pos;
307277
}
308278

309279
static void modem_chat_script_send_handler(struct k_work *item)
310280
{
311281
struct modem_chat *chat = CONTAINER_OF(item, struct modem_chat, script_send_work);
312282
uint16_t timeout;
313283

314-
/* Validate script running */
315284
if (chat->script == NULL) {
316285
return;
317286
}
318287

319-
/* Send request */
320-
if (modem_chat_script_send_request(chat) == false) {
321-
k_work_submit(&chat->script_send_work);
288+
switch (chat->script_send_state) {
289+
case MODEM_CHAT_SCRIPT_SEND_STATE_IDLE:
322290
return;
323-
}
324291

325-
/* Send delimiter */
326-
if (modem_chat_script_send_delimiter(chat) == false) {
327-
k_work_submit(&chat->script_send_work);
328-
return;
292+
case MODEM_CHAT_SCRIPT_SEND_STATE_REQUEST:
293+
if (!modem_chat_send_script_request_part(chat)) {
294+
return;
295+
}
296+
297+
modem_chat_set_script_send_state(chat, MODEM_CHAT_SCRIPT_SEND_STATE_DELIMITER);
298+
__fallthrough;
299+
300+
case MODEM_CHAT_SCRIPT_SEND_STATE_DELIMITER:
301+
if (!modem_chat_send_script_request_part(chat)) {
302+
return;
303+
}
304+
305+
modem_chat_set_script_send_state(chat, MODEM_CHAT_SCRIPT_SEND_STATE_IDLE);
306+
break;
329307
}
330308

331-
/* Check if script command is no response */
332309
if (modem_chat_script_chat_is_no_response(chat)) {
333310
timeout = modem_chat_script_chat_get_send_timeout(chat);
334-
335311
if (timeout == 0) {
336312
modem_chat_script_next(chat, false);
337313
} else {
@@ -708,8 +684,17 @@ static void modem_chat_pipe_callback(struct modem_pipe *pipe, enum modem_pipe_ev
708684
{
709685
struct modem_chat *chat = (struct modem_chat *)user_data;
710686

711-
if (event == MODEM_PIPE_EVENT_RECEIVE_READY) {
687+
switch (event) {
688+
case MODEM_PIPE_EVENT_RECEIVE_READY:
712689
k_work_submit(&chat->receive_work);
690+
break;
691+
692+
case MODEM_PIPE_EVENT_TRANSMIT_IDLE:
693+
k_work_submit(&chat->script_send_work);
694+
break;
695+
696+
default:
697+
break;
713698
}
714699
}
715700

@@ -840,8 +825,8 @@ void modem_chat_release(struct modem_chat *chat)
840825
atomic_set(&chat->script_state, 0);
841826
chat->script_result = MODEM_CHAT_SCRIPT_RESULT_ABORT;
842827
k_sem_reset(&chat->script_stopped_sem);
843-
chat->script_send_request_pos = 0;
844-
chat->script_send_delimiter_pos = 0;
828+
chat->script_send_state = MODEM_CHAT_SCRIPT_SEND_STATE_IDLE;
829+
chat->script_send_pos = 0;
845830
chat->parse_match = NULL;
846831
chat->parse_match_len = 0;
847832
chat->parse_arg_len = 0;

0 commit comments

Comments
 (0)