static int do_read(struct userdata *u) {
    pa_assert(u);

    if (!pa_iochannel_is_readable(u->io))
        return 0;

    if (u->state == STATE_AUTH || u->state == STATE_LATENCY) {
        ssize_t r;

        if (!u->read_data)
            return 0;

        pa_assert(u->read_index < u->read_length);

        if ((r = pa_iochannel_read(u->io, (uint8_t*) u->read_data + u->read_index, u->read_length - u->read_index)) <= 0) {
            pa_log("read() failed: %s", r < 0 ? pa_cstrerror(errno) : "EOF");
            return -1;
        }

        u->read_index += (size_t) r;
        pa_assert(u->read_index <= u->read_length);

        if (u->read_index == u->read_length)
            return handle_response(u);
    }

    return 0;
}
Beispiel #2
0
static void do_work(connection *c) {
    connection_assert_ref(c);

    if (c->dead)
        return;

    if (pa_iochannel_is_readable(c->io))
        if (do_read(c) < 0)
            goto fail;

    if (!c->sink_input && pa_iochannel_is_hungup(c->io))
        goto fail;

    if (pa_iochannel_is_writable(c->io))
        if (do_write(c) < 0)
            goto fail;

    return;

fail:

    if (c->sink_input) {

        /* If there is a sink input, we first drain what we already have read before shutting down the connection */
        c->dead = TRUE;

        pa_iochannel_free(c->io);
        c->io = NULL;

        pa_asyncmsgq_post(c->sink_input->sink->asyncmsgq, PA_MSGOBJECT(c->sink_input), SINK_INPUT_MESSAGE_DISABLE_PREBUF, NULL, 0, NULL, NULL);
    } else
        connection_unlink(c);
}