コード例 #1
0
ファイル: tunnel.c プロジェクト: CeKMTL/polipo
static int
tunnelError(TunnelPtr tunnel, int code, AtomPtr message)
{
    int n;
    if(tunnel->fd2 > 0) {
        CLOSE(tunnel->fd2);
        tunnel->fd2 = -1;
    }

    if(tunnel->buf2.buf == NULL)
        tunnel->buf2.buf = get_chunk();
    if(tunnel->buf2.buf == NULL)
        goto fail;

    n = httpWriteErrorHeaders(tunnel->buf2.buf, CHUNK_SIZE - 1, 0,
                              1, code, message, 1, NULL,
                              NULL, 0, NULL);

    if(n <= 0) goto fail;

    tunnel->buf2.head = n;

    tunnelDispatch(tunnel);
    return 1;

 fail:
    CLOSE(tunnel->fd1);
    tunnel->fd1 = -1;
    tunnelDispatch(tunnel);
    return 1;
}
コード例 #2
0
ファイル: tunnel.c プロジェクト: CeKMTL/polipo
static int
tunnelWrite2Handler(int status,
                   FdEventHandlerPtr event, StreamRequestPtr request)
{
    TunnelPtr tunnel = request->data;
    if(status || (tunnel->flags & TUNNEL_EPIPE2)) {
        tunnel->flags |= TUNNEL_EPIPE2;
        if(status < 0 && status != -EPIPE)
            do_log_error(L_ERROR, -status, "Couldn't write to server");
        /* Empty the buffer to avoid a deadlock */
        tunnel->buf1.tail = tunnel->buf1.head;
        goto done;
    }
    tunnel->buf1.tail = request->offset % CHUNK_SIZE;
 done:
    tunnel->flags &= ~TUNNEL_WRITER2;
    tunnelDispatch(tunnel);
    return 1;
}
コード例 #3
0
ファイル: tunnel.c プロジェクト: CeKMTL/polipo
static int
tunnelRead2Handler(int status, 
                   FdEventHandlerPtr event, StreamRequestPtr request)
{
    TunnelPtr tunnel = request->data;
    if(status) {
        if(status < 0 && status != -EPIPE && status != -ECONNRESET)
            do_log_error(L_ERROR, -status, "Couldn't read from server");
        tunnel->flags |= TUNNEL_EOF2;
        goto done;
    }
    tunnel->buf2.head = request->offset % CHUNK_SIZE;
done:
    /* Keep buffer empty to avoid a deadlock */
    if((tunnel->flags & TUNNEL_EPIPE1))
        tunnel->buf2.tail = tunnel->buf2.head;
    tunnel->flags &= ~TUNNEL_READER2;
    tunnelDispatch(tunnel);
    return 1;
}
コード例 #4
0
ファイル: tunnel.c プロジェクト: garrybodsworth/polipo
static int
tunnelRead1Handler(int status, 
                   FdEventHandlerPtr event, StreamRequestPtr request)
{
    TunnelPtr tunnel = request->data;
    if(status) {
        if(status < 0)
            do_log_error(L_ERROR, -status, "Couldn't read from client");
        tunnel->flags |= TUNNEL_EOF1;
        goto done;
    }
    tunnel->buf1.head = request->offset % CHUNK_SIZE;
 done:
    /* Keep buffer empty to avoid a deadlock */
    if((tunnel->flags & TUNNEL_EPIPE2))
        tunnel->buf1.tail = tunnel->buf1.head;
    tunnel->flags &= ~TUNNEL_READER1;
    tunnelDispatch(tunnel);
    return 1;
}
コード例 #5
0
ファイル: tunnel.c プロジェクト: CeKMTL/polipo
static int
tunnelHandlerParent(int fd, TunnelPtr tunnel)
{
    char *message;
    int n;

    if(tunnel->buf1.buf == NULL)
        tunnel->buf1.buf = get_chunk();
    if(tunnel->buf1.buf == NULL) {
        message = "Couldn't allocate buffer";
        goto fail;
    }
    if(tunnel->buf1.tail != tunnel->buf1.head) {
        message = "Pipelined connect to parent proxy not implemented";
        goto fail;
    }

    n = snnprintf(tunnel->buf1.buf, tunnel->buf1.tail, CHUNK_SIZE,
                  "CONNECT %s:%d HTTP/1.1",
                  tunnel->hostname->string, tunnel->port);
    if (parentAuthCredentials)
        n = buildServerAuthHeaders(tunnel->buf1.buf, n, CHUNK_SIZE,
                                   parentAuthCredentials);
    n = snnprintf(tunnel->buf1.buf, n, CHUNK_SIZE, "\r\n\r\n");

    if(n < 0) {
        message = "Buffer overflow";
        goto fail;
    }
    tunnel->buf1.head = n;
    tunnelDispatch(tunnel);
    return 1;

 fail:
    CLOSE(fd);
    tunnel->fd2 = -1;
    tunnelError(tunnel, 501, internAtom(message));
    return 1;
}
コード例 #6
0
ファイル: tunnel.c プロジェクト: CeKMTL/polipo
static int
tunnelHandlerCommon(int fd, TunnelPtr tunnel)
{
    const char *message = "HTTP/1.1 200 Tunnel established\r\n\r\n";

    tunnel->fd2 = fd;

    if(parentHost)
        return tunnelHandlerParent(fd, tunnel);

    if(tunnel->buf2.buf == NULL)
        tunnel->buf2.buf = get_chunk();
    if(tunnel->buf2.buf == NULL) {
        CLOSE(fd);
        tunnelError(tunnel, 501, internAtom("Couldn't allocate buffer"));
        return 1;
    }

    memcpy(tunnel->buf2.buf, message, MIN(CHUNK_SIZE - 1, strlen(message)));
    tunnel->buf2.head = MIN(CHUNK_SIZE - 1, strlen(message));

    tunnelDispatch(tunnel);
    return 1;
}