AmendHub

Download:

jcs

/

subtext

/

amendments

/

42

session: Add session_flush, make output routines not autoflush

This lets us flush at certain places to send it out once we've built
up a whole line or whatever to smooth out the output

jcs made amendment 42 over 2 years ago
--- session.c Wed Dec 29 20:50:48 2021 +++ session.c Sun Jan 2 10:22:55 2022 @@ -91,7 +91,8 @@ session_run(struct uthread *uthread, void *arg) "Welcome to %s (%s)\r\n" "\r\n", db->config.name, s->node); } - + session_flush(s); + if (session_login(s) != AUTH_USER_OK) { session_close(&s); return; @@ -117,6 +118,7 @@ session_run(struct uthread *uthread, void *arg) s->user ? s->user->username : GUEST_USERNAME, ansi(s, ANSI_RESET, ANSI_END), sessions_tally, ordinal(sessions_tally)); + session_flush(s); len = session_load_view(s, DB_TEXT_MENU_ID, &view); if (len) { @@ -124,9 +126,11 @@ session_run(struct uthread *uthread, void *arg) free(view); } else session_output_string(s, "\r\n[ Menu missing! ]\r\n\r\n"); + session_flush(s); while (!done && !s->ending) { session_output_string(s, "Main Menu> "); + session_flush(s); get_another_char: c = session_input_char(s); @@ -136,6 +140,7 @@ get_another_char: goto get_another_char; session_printf(s, "%c\r\n", c); + session_flush(s); /* TODO: make letter->command dynamic from a resource */ switch (c) { @@ -147,6 +152,7 @@ get_another_char: case 'G': /* goodbye */ session_output_string(s, "Goodbye!\r\n"); + session_flush(s); done = 1; break; case 'w': @@ -155,10 +161,11 @@ get_another_char: break; default: session_output_string(s, "Invalid option\r\n"); + session_flush(s); break; } } - + session_close(&s); } @@ -176,7 +183,7 @@ session_close(struct session **session) (*session)->node_funcs->output(*session); uthread_yield(); } - + (*session)->ending = 1; } @@ -218,6 +225,23 @@ session_printf(struct session *session, const char *fo return session_output(session, session_tbuf, len); } +void +session_flush(struct session *session) +{ + if (session->ending) + return; + if (session->obuflen == 0) + return; + + while (session->obuflen != 0) { + session->node_funcs->output(session); + if (session->obuflen != 0) + uthread_yield(); + if (session->ending) + return; + } +} + size_t session_output(struct session *session, const char *str, size_t len) { @@ -226,8 +250,7 @@ session_output(struct session *session, const char *st while (len && !session->ending) { chunk = (sizeof(session->obuf) - session->obuflen); if (chunk == 0) { - /* wait until output buffer clears */ - uthread_yield(); + session_flush(session); if (session->ending) return 0; continue; @@ -239,10 +262,6 @@ session_output(struct session *session, const char *st session->obuflen += chunk; stroff += chunk; len -= chunk; - session->node_funcs->output(session); - - if (len) - uthread_yield(); } return olen; @@ -263,13 +282,15 @@ session_input_char(struct session *session) wait_for_char: while (session->ibuflen == 0) { session->node_funcs->input(session); - uthread_yield(); if (session->ending) return 0; + if (session->abort_input) + return 0; if (session->ibuflen != 0) break; if (session->obuflen != 0) return 0; + uthread_yield(); } ret = session->ibuf[0]; @@ -303,11 +324,13 @@ session_field_input(struct session *session, unsigned char *field; unsigned char c, redraw = 0; + session->abort_input = 0; + field = xmalloczero(size); for (;;) { c = session_input_char(session); - if (session->ending) + if (session->ending || session->abort_input) goto field_input_bail; switch (c) { case 0: /* session_input_char bailed */ @@ -336,9 +359,11 @@ session_field_input(struct session *session, unsigned if (redraw) { /* TODO */ - } else + } else { session_output_string(session, ansi(session, ANSI_BACKSPACE, ANSI_END)); + session_flush(session); + } break; case '\r': @@ -358,6 +383,7 @@ session_field_input(struct session *session, unsigned ilen++; field[ipos] = '\0'; session_output(session, mask ? &mask : (char *)&c, 1); + session_flush(session); } } @@ -380,12 +406,15 @@ session_login(struct session *s) if (s->autologin_username[0]) { session_printf(s, "%s\r\n", s->autologin_username); + session_flush(s); username = xstrdup(s->autologin_username); } else { + session_flush(s); username = session_field_input(s, DB_USERNAME_SIZE, DB_USERNAME_SIZE - 1, 0); session_output(s, "\r\n", 2); - + session_flush(s); + if (username == NULL || s->ending) goto login_bail; @@ -415,8 +444,10 @@ session_login(struct session *s) } session_output_string(s, "Password: "); + session_flush(s); password = session_field_input(s, 64, 64, '*'); session_output(s, "\r\n", 2); + session_flush(s); if (password == NULL || s->ending) goto login_bail; @@ -443,6 +474,7 @@ session_login(struct session *s) uthread_msleep(60); session_output_string(s, "Login incorrect\r\n"); + session_flush(s); } login_bail: @@ -451,6 +483,7 @@ login_bail: if (password) free(password); session_output_string(s, "Thanks for playing\r\n"); + session_flush(s); return AUTH_USER_FAILED; } @@ -634,6 +667,7 @@ session_pause_return(struct session *s, short enforce, session_output_string(s, msg); else session_output_string(s, "to return to the main menu..."); + session_flush(s); for (;;) { c = session_input_char(s); @@ -643,6 +677,7 @@ session_pause_return(struct session *s, short enforce, break; } session_output(s, "\r\n", 2); + session_flush(s); } void @@ -659,6 +694,7 @@ session_who(struct session *s) session_printf(s, "%sNode User Via Speed Idle%s\r\n", ansi(s, ANSI_BOLD, ANSI_END), ansi(s, ANSI_RESET, ANSI_END)); + session_flush(s); for (n = 0; n < nsessions; n++) { idle = Time - sessions[n]->last_input_at; @@ -677,8 +713,10 @@ session_who(struct session *s) sessions[n]->via, sessions[n]->tspeed, idle_s); + session_flush(s); } session_output(s, "\r\n", 2); + session_flush(s); session_pause_return(s, 0, NULL); } --- session.h Wed Dec 29 08:56:08 2021 +++ session.h Sun Jan 2 10:21:53 2022 @@ -48,16 +48,18 @@ struct session_log { unsigned long ip_address; }; + struct session { short ending; char node[10]; char via[10]; - unsigned char obuf[256]; /* telnet.obuf must be double this */ + unsigned char obuf[512]; /* telnet.obuf must be double this */ unsigned char ibuf[64]; short obuflen; short ibuflen; enum session_input_state input_state; unsigned char last_input; + unsigned char abort_input; unsigned long last_input_at; unsigned short terminal_columns; unsigned short terminal_lines; @@ -86,6 +88,7 @@ struct session *session_create(char *node, char *via, void session_close(struct session **session); void session_idle(struct session *session); char session_input_char(struct session *session); +void session_flush(struct session *session); size_t session_printf(struct session *session, const char *format, ...); size_t session_output(struct session *session, const char *str, size_t len); size_t session_output_string(struct session *session, const char *str);