Exemplo n.º 1
0
int
Curl_sec_fflush_fd(struct connectdata *conn, int fd)
{
  if(conn->data_prot != prot_clear) {
    if(conn->out_buffer.index > 0){
      Curl_sec_write(conn, fd,
                conn->out_buffer.data, conn->out_buffer.index);
      conn->out_buffer.index = 0;
    }
    sec_send(conn, fd, NULL, 0);
  }
  return 0;
}
Exemplo n.º 2
0
int
Curl_sec_putc(struct connectdata *conn, int c, FILE *F)
{
  char ch = c;
  if(conn->data_prot == prot_clear)
    return putc(c, F);
    
  buffer_write(&conn->out_buffer, &ch, 1);
  if(c == '\n' || conn->out_buffer.index >= 1024 /* XXX */) {
    Curl_sec_write(conn, fileno(F), conn->out_buffer.data,
                   conn->out_buffer.index);
    conn->out_buffer.index = 0;
  }
  return c;
}
Exemplo n.º 3
0
/*
 * Curl_write() is an internal write function that sends plain (binary) data
 * to the server. Works with plain sockets, SSL or kerberos.
 */
CURLcode Curl_write(struct connectdata *conn,
                    curl_socket_t sockfd,
                    void *mem,
                    size_t len,
                    ssize_t *written)
{
  ssize_t bytes_written;
  CURLcode retcode;
  int num = (sockfd == conn->sock[SECONDARYSOCKET]);

  if (conn->ssl[num].use)
    /* only TRUE if SSL enabled */
    bytes_written = Curl_ssl_send(conn, num, mem, len);
  else {
    if(conn->sec_complete)
      /* only TRUE if krb4 enabled */
      bytes_written = Curl_sec_write(conn, sockfd, mem, len);
    else
      bytes_written = (ssize_t)swrite(sockfd, mem, len);

    if(-1 == bytes_written) {
      int err = Curl_ourerrno();

      if(
#ifdef WSAEWOULDBLOCK
        /* This is how Windows does it */
        (WSAEWOULDBLOCK == err)
#else
        /* As pointed out by Christophe Demory on March 11 2003, errno
           may be EWOULDBLOCK or on some systems EAGAIN when it returned
           due to its inability to send off data without blocking. We
           therefor treat both error codes the same here */
        (EWOULDBLOCK == err) || (EAGAIN == err) || (EINTR == err)
#endif
        )
        /* this is just a case of EWOULDBLOCK */
        bytes_written=0;
      else
        failf(conn->data, "Send failure: %s",
              Curl_strerror(conn, err));
    }
  }
  *written = bytes_written;
  retcode = (-1 != bytes_written)?CURLE_OK:CURLE_SEND_ERROR;

  return retcode;
}
Exemplo n.º 4
0
/*
 * Curl_write() is an internal write function that sends plain (binary) data
 * to the server. Works with plain sockets, SSL or kerberos.
 */
CURLcode Curl_write(struct connectdata *conn,
                    curl_socket_t sockfd,
                    void *mem,
                    size_t len,
                    ssize_t *written)
{
    ssize_t bytes_written;
    CURLcode retcode;

#ifdef USE_SSLEAY
    /* Set 'num' to 0 or 1, depending on which socket that has been sent here.
       If it is the second socket, we set num to 1. Otherwise to 0. This lets
       us use the correct ssl handle. */
    int num = (sockfd == conn->sock[SECONDARYSOCKET]);
    /* SSL_write() is said to return 'int' while write() and send() returns
       'size_t' */
    if (conn->ssl[num].use) {
        int err;
        char error_buffer[120]; /* OpenSSL documents that this must be at least
                               120 bytes long. */
        unsigned long sslerror;
        int rc = SSL_write(conn->ssl[num].handle, mem, (int)len);

        if(rc < 0) {
            err = SSL_get_error(conn->ssl[num].handle, rc);

            switch(err) {
            case SSL_ERROR_WANT_READ:
            case SSL_ERROR_WANT_WRITE:
                /* The operation did not complete; the same TLS/SSL I/O function
                   should be called again later. This is basicly an EWOULDBLOCK
                   equivalent. */
                *written = 0;
                return CURLE_OK;
            case SSL_ERROR_SYSCALL:
                failf(conn->data, "SSL_write() returned SYSCALL, errno = %d\n",
                      Curl_ourerrno());
                return CURLE_SEND_ERROR;
            case SSL_ERROR_SSL:
                /*  A failure in the SSL library occurred, usually a protocol error.
                    The OpenSSL error queue contains more information on the error. */
                sslerror = ERR_get_error();
                failf(conn->data, "SSL_write() error: %s\n",
                      ERR_error_string(sslerror, error_buffer));
                return CURLE_SEND_ERROR;
            }
            /* a true error */
            failf(conn->data, "SSL_write() return error %d\n", err);
            return CURLE_SEND_ERROR;
        }
        bytes_written = rc;
    }
    else {
#else
    (void)conn;
#endif
#ifdef HAVE_KRB4
        if(conn->sec_complete) {
            bytes_written = Curl_sec_write(conn, sockfd, mem, len);
        }
        else
#endif /* HAVE_KRB4 */
        {
            bytes_written = (ssize_t)swrite(sockfd, mem, len);
        }
        if(-1 == bytes_written) {
            int err = Curl_ourerrno();

            if(
#ifdef WSAEWOULDBLOCK
                /* This is how Windows does it */
                (WSAEWOULDBLOCK == err)
#else
                /* As pointed out by Christophe Demory on March 11 2003, errno
                   may be EWOULDBLOCK or on some systems EAGAIN when it returned
                   due to its inability to send off data without blocking. We
                   therefor treat both error codes the same here */
                (EWOULDBLOCK == err) || (EAGAIN == err) || (EINTR == err)
#endif
            )
                /* this is just a case of EWOULDBLOCK */
                bytes_written=0;
        }
#ifdef USE_SSLEAY
    }
#endif

    *written = bytes_written;
    retcode = (-1 != bytes_written)?CURLE_OK:CURLE_SEND_ERROR;

    return retcode;
}