I try to understand the logic of mod_proxy_http2 with respect to timeouts. I am 
currently stuck at this piece of code in
h2_proxy_session_process in h2_proxy_session.c

        case H2_PROXYS_ST_BUSY:
        case H2_PROXYS_ST_LOCAL_SHUTDOWN:
        case H2_PROXYS_ST_REMOTE_SHUTDOWN:
            have_written = send_loop(session);

            if (nghttp2_session_want_read(session->ngh2)) {
                status = h2_proxy_session_read(session, 0, 0);
                if (status == APR_SUCCESS) {
                    have_read = 1;
                }
            }

            if (!have_written && !have_read
                && !nghttp2_session_want_write(session->ngh2)) {
                dispatch_event(session, H2_PROXYS_EV_NO_IO, 0, NULL);
                goto run_loop;
            }
            break;

        case H2_PROXYS_ST_WAIT:
            if (check_suspended(session) == APR_EAGAIN) {
                /* no stream has become resumed. Do a blocking read with
                 * ever increasing timeouts... */
                if (session->wait_timeout < 25) {
                    session->wait_timeout = 25;
                }
                else {
                    session->wait_timeout = H2MIN(apr_time_from_msec(100),
                                                  2*session->wait_timeout);
                }

                status = h2_proxy_session_read(session, 1, 
session->wait_timeout);
                ap_log_cerror(APLOG_MARK, APLOG_TRACE3, status, session->c,
                              APLOGNO(03365)
                              "h2_proxy_session(%s): WAIT read, timeout=%fms",
                              session->id, session->wait_timeout/1000.0);
                if (status == APR_SUCCESS) {
                    have_read = 1;
                    dispatch_event(session, H2_PROXYS_EV_DATA_READ, 0, NULL);
                }
                else if (APR_STATUS_IS_TIMEUP(status)
                    || APR_STATUS_IS_EAGAIN(status)) {
                    /* go back to checking all inputs again */
                    transit(session, "wait cycle", H2_PROXYS_ST_BUSY);
                }


Doesn't that loop forever with in the end 100ms blocking reads from the backend 
if the backend never replies?
The state of the session seems to switch between H2_PROXYS_ST_BUSY (set in line 
1454) and H2_PROXYS_ST_WAIT set
by ev_no_io. Do I miss the exit?


Regards

RĂ¼diger

Reply via email to