static void http_debug_hex(const char *prefix, const char *buffer,
int bytes);
#endif /* DEBUG */
-static http_field_t http_field(const char *name);
static ssize_t http_read(http_t *http, char *buffer, size_t length);
static ssize_t http_read_buffered(http_t *http, char *buffer, size_t length);
static ssize_t http_read_chunk(http_t *http, char *buffer, size_t length);
size_t length);
#ifdef HAVE_SSL
static int http_read_ssl(http_t *http, char *buf, int len);
-# ifdef HAVE_CDSASSL
static int http_set_credentials(http_t *http);
-# endif /* HAVE_CDSASSL */
#endif /* HAVE_SSL */
static off_t http_set_length(http_t *http);
static void http_set_timeout(int fd, double timeout);
static void http_set_wait(http_t *http);
-#ifdef DEBUG
-static const char *http_state_string(http_state_t state);
-#endif /* DEBUG */
#ifdef HAVE_SSL
static int http_setup_ssl(http_t *http);
static void http_shutdown_ssl(http_t *http);
return (NULL);
}
- httpAddrString(&(http->addrlist->addr), http->hostname,
- sizeof(http->hostname));
+ http->hostaddr = &(http->addrlist->addr);
+
+ if (httpAddrLocalhost(http->hostaddr))
+ strlcpy(http->hostname, "localhost", sizeof(http->hostname));
+ else
+ httpAddrString(http->hostaddr, http->hostname, sizeof(http->hostname));
#ifdef SO_NOSIGPIPE
/*
*/
void
-httpBlocking(http_t *http, /* I - Connection to server */
+httpBlocking(http_t *http, /* I - HTTP connection */
int b) /* I - 1 = blocking, 0 = non-blocking */
{
if (http)
*/
int /* O - 0 = no data, 1 = data available */
-httpCheck(http_t *http) /* I - Connection to server */
+httpCheck(http_t *http) /* I - HTTP connection */
{
return (httpWait(http, 0));
}
*/
void
-httpClearCookie(http_t *http) /* I - Connection to server */
+httpClearCookie(http_t *http) /* I - HTTP connection */
{
if (!http)
return;
*/
void
-httpClearFields(http_t *http) /* I - Connection to server */
+httpClearFields(http_t *http) /* I - HTTP connection */
{
DEBUG_printf(("httpClearFields(http=%p)", http));
*/
void
-httpClose(http_t *http) /* I - Connection to server */
+httpClose(http_t *http) /* I - HTTP connection */
{
#ifdef HAVE_GSSAPI
OM_uint32 minor_status; /* Minor status code */
int /* O - Status of call (0 = success) */
httpCopyCredentials(
- http_t *http, /* I - Connection to server */
+ http_t *http, /* I - HTTP connection */
cups_array_t **credentials) /* O - Array of credentials */
{
# ifdef HAVE_LIBSSL
*/
int /* O - Status of call (0 = success) */
-httpDelete(http_t *http, /* I - Connection to server */
+httpDelete(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI to delete */
{
return (http_send(http, HTTP_STATE_DELETE, uri));
*/
void
-_httpDisconnect(http_t *http) /* I - Connection to server */
+_httpDisconnect(http_t *http) /* I - HTTP connection */
{
#ifdef HAVE_SSL
if (http->tls)
http_shutdown_ssl(http);
#endif /* HAVE_SSL */
-#ifdef WIN32
- closesocket(http->fd);
-#else
- close(http->fd);
-#endif /* WIN32 */
+ httpAddrClose(NULL, http->fd);
http->fd = -1;
}
*/
int /* O - -1 on error, 0 on success */
-httpEncryption(http_t *http, /* I - Connection to server */
+httpEncryption(http_t *http, /* I - HTTP connection */
http_encryption_t e) /* I - New encryption preference */
{
DEBUG_printf(("httpEncryption(http=%p, e=%d)", http, e));
*/
int /* O - Error code (errno) value */
-httpError(http_t *http) /* I - Connection to server */
+httpError(http_t *http) /* I - HTTP connection */
{
if (http)
return (http->error);
}
+/*
+ * 'httpFieldValue()' - Return the HTTP field enumeration value for a field
+ * name.
+ */
+
+http_field_t /* O - Field index */
+httpFieldValue(const char *name) /* I - String name */
+{
+ int i; /* Looping var */
+
+
+ for (i = 0; i < HTTP_FIELD_MAX; i ++)
+ if (!_cups_strcasecmp(name, http_fields[i]))
+ return ((http_field_t)i);
+
+ return (HTTP_FIELD_UNKNOWN);
+}
+
+
/*
* 'httpFlush()' - Flush data from a HTTP connection.
*/
void
-httpFlush(http_t *http) /* I - Connection to server */
+httpFlush(http_t *http) /* I - HTTP connection */
{
char buffer[8192]; /* Junk buffer */
int blocking; /* To block or not to block */
DEBUG_printf(("httpFlush(http=%p), state=%s", http,
- http_state_string(http->state)));
+ httpStateString(http->state)));
/*
* Nothing to do if we are in the "waiting" state...
http_shutdown_ssl(http);
#endif /* HAVE_SSL */
-#ifdef WIN32
- closesocket(http->fd);
-#else
- close(http->fd);
-#endif /* WIN32 */
+ httpAddrClose(NULL, http->fd);
http->fd = -1;
}
*/
int /* O - Bytes written or -1 on error */
-httpFlushWrite(http_t *http) /* I - Connection to server */
+httpFlushWrite(http_t *http) /* I - HTTP connection */
{
int bytes; /* Bytes written */
*/
int /* O - Status of call (0 = success) */
-httpGet(http_t *http, /* I - Connection to server */
+httpGet(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI to get */
{
return (http_send(http, HTTP_STATE_GET, uri));
}
+/*
+ * 'httpGetActivity()' - Get the most recent activity for a connection.
+ *
+ * The return value is the UNIX time of the last read or write.
+ *
+ * @since CUPS 2.0@
+ */
+
+time_t /* O - Time of last read or write */
+httpGetActivity(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->activity : 0);
+}
+
+
/*
* 'httpGetAuthString()' - Get the current authorization string.
*
*/
char * /* O - Authorization string */
-httpGetAuthString(http_t *http) /* I - Connection to server */
+httpGetAuthString(http_t *http) /* I - HTTP connection */
{
if (http)
return (http->authstring);
*/
int /* O - 1 if blocking, 0 if non-blocking */
-httpGetBlocking(http_t *http) /* I - Connection to server */
+httpGetBlocking(http_t *http) /* I - HTTP connection */
{
return (http ? http->blocking : 0);
}
}
+/*
+ * 'httpGetEncryption()' - Get the current encryption mode of a connection.
+ *
+ * This function returns the encryption mode for the connection. Use the
+ * @link httpIsEncrypted@ function to determine whether a TLS session has
+ * been established.
+ *
+ * @since CUPS 2.0@
+ */
+
+http_encryption_t /* O - Current encryption mode */
+httpGetEncryption(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->encryption : HTTP_ENCRYPTION_IF_REQUESTED);
+}
+
+
/*
* 'httpGetExpect()' - Get the value of the Expect header, if any.
*
*/
int /* O - File descriptor or -1 if none */
-httpGetFd(http_t *http) /* I - Connection to server */
+httpGetFd(http_t *http) /* I - HTTP connection */
{
return (http ? http->fd : -1);
}
*/
const char * /* O - Field value */
-httpGetField(http_t *http, /* I - Connection to server */
+httpGetField(http_t *http, /* I - HTTP connection */
http_field_t field) /* I - Field to get */
{
if (!http || field <= HTTP_FIELD_UNKNOWN || field >= HTTP_FIELD_MAX)
}
+/*
+ * 'httpGetKeepAlive()' - Get the current Keep-Alive state of the connection.
+ *
+ * @since CUPS 2.0@
+ */
+
+http_keepalive_t /* O - Keep-Alive state */
+httpGetKeepAlive(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->keep_alive : HTTP_KEEPALIVE_OFF);
+}
+
+
/*
* 'httpGetLength()' - Get the amount of data remaining from the
* content-length or transfer-encoding fields.
*/
int /* O - Content length */
-httpGetLength(http_t *http) /* I - Connection to server */
+httpGetLength(http_t *http) /* I - HTTP connection */
{
/*
* Get the read content length and return the 32-bit value.
*/
off_t /* O - Content length */
-httpGetLength2(http_t *http) /* I - Connection to server */
+httpGetLength2(http_t *http) /* I - HTTP connection */
{
off_t remaining; /* Remaining length */
DEBUG_printf(("2httpGetLength2(http=%p), state=%s", http,
- http_state_string(http->state)));
+ httpStateString(http->state)));
if (!http)
return (-1);
}
+/*
+ * 'httpGetPending()' - Get the number of bytes that are buffered for writing.
+ *
+ * @since CUPS 2.0@
+ */
+
+size_t /* O - Number of bytes buffered */
+httpGetPending(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->wused : 0);
+}
+
+
+/*
+ * 'httpGetReady()' - Get the number of bytes that can be read without blocking.
+ *
+ * @since CUPS 2.0@
+ */
+
+size_t /* O - Number of bytes available */
+httpGetReady(http_t *http) /* I - HTTP connection */
+{
+ if (!http)
+ return (0);
+ else if (http->used > 0)
+ return (http->used);
+#ifdef HAVE_SSL
+ else if (http->tls)
+ {
+ size_t ready; /* Ready bytes */
+
+# ifdef HAVE_LIBSSL
+ if ((ready = SSL_pending((SSL *)(http->tls))) > 0)
+ return (ready);
+# elif defined(HAVE_GNUTLS)
+ if ((ready = gnutls_record_check_pending(http->tls)) > 0)
+ return (ready);
+# elif defined(HAVE_CDSASSL)
+ if (!SSLGetBufferedReadSize(http->tls, &ready) && ready > 0)
+ return (ready);
+# endif /* HAVE_LIBSSL */
+ }
+#endif /* HAVE_SSL */
+
+ return (0);
+}
+
+
+/*
+ * 'httpGetRemaining()' - Get the number of remaining bytes in the message
+ * body or current chunk.
+ *
+ * The @link httpIsChunked@ function can be used to determine whether the
+ * message body is chunked or fixed-length.
+ *
+ * @since CUPS 2.0@
+ */
+
+size_t /* O - Remaining bytes */
+httpGetRemaining(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->data_remaining : 0);
+}
+
+
/*
* 'httpGets()' - Get a line of text from a HTTP connection.
*/
char * /* O - Line or NULL */
httpGets(char *line, /* I - Line to read into */
int length, /* I - Max length of buffer */
- http_t *http) /* I - Connection to server */
+ http_t *http) /* I - HTTP connection */
{
char *lineptr, /* Pointer into line */
*lineend, /* End of line */
*/
http_state_t /* O - HTTP state */
-httpGetState(http_t *http) /* I - Connection to server */
+httpGetState(http_t *http) /* I - HTTP connection */
{
return (http ? http->state : HTTP_STATE_ERROR);
}
*/
http_status_t /* O - HTTP status */
-httpGetStatus(http_t *http) /* I - Connection to server */
+httpGetStatus(http_t *http) /* I - HTTP connection */
{
return (http ? http->status : HTTP_STATUS_ERROR);
}
*/
char * /* O - Value or NULL */
-httpGetSubField(http_t *http, /* I - Connection to server */
+httpGetSubField(http_t *http, /* I - HTTP connection */
http_field_t field, /* I - Field index */
const char *name, /* I - Name of sub-field */
char *value) /* O - Value string */
*/
char * /* O - Value or NULL */
-httpGetSubField2(http_t *http, /* I - Connection to server */
+httpGetSubField2(http_t *http, /* I - HTTP connection */
http_field_t field, /* I - Field index */
const char *name, /* I - Name of sub-field */
char *value, /* O - Value string */
*/
http_version_t /* O - Version number */
-httpGetVersion(http_t *http) /* I - Connection to server */
+httpGetVersion(http_t *http) /* I - HTTP connection */
{
return (http ? http->version : HTTP_VERSION_1_0);
}
*/
int /* O - Status of call (0 = success) */
-httpHead(http_t *http, /* I - Connection to server */
+httpHead(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI for head */
{
DEBUG_printf(("httpHead(http=%p, uri=\"%s\")", http, uri));
}
+/*
+ * 'httpIsChunked()' - Report whether a message body is chunked.
+ *
+ * This function returns non-zero if the message body is composed of
+ * variable-length chunks.
+ *
+ * @since CUPS 2.0@
+ */
+
+int /* O - 1 if chunked, 0 if not */
+httpIsChunked(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->data_encoding == HTTP_ENCODING_CHUNKED : 0);
+}
+
+
+/*
+ * 'httpIsEncrypted()' - Report whether a connection is encrypted.
+ *
+ * This function returns non-zero if the connection is currently encrypted.
+ *
+ * @since CUPS 2.0@
+ */
+
+int /* O - 1 if encrypted, 0 if not */
+httpIsEncrypted(http_t *http) /* I - HTTP connection */
+{
+ return (http ? http->tls != NULL : 0);
+}
+
+
/*
* 'httpOptions()' - Send an OPTIONS request to the server.
*/
int /* O - Status of call (0 = success) */
-httpOptions(http_t *http, /* I - Connection to server */
+httpOptions(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI for options */
{
return (http_send(http, HTTP_STATE_OPTIONS, uri));
*/
ssize_t /* O - Number of bytes copied */
-httpPeek(http_t *http, /* I - Connection to server */
+httpPeek(http_t *http, /* I - HTTP connection */
char *buffer, /* I - Buffer for data */
size_t length) /* I - Maximum number of bytes */
{
http->state = HTTP_STATE_STATUS;
DEBUG_printf(("1httpPeek: 0-length chunk, set state to %s.",
- http_state_string(http->state)));
+ httpStateString(http->state)));
/*
* Prevent future reads for this request...
*/
int /* O - Status of call (0 = success) */
-httpPost(http_t *http, /* I - Connection to server */
+httpPost(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI for post */
{
return (http_send(http, HTTP_STATE_POST, uri));
*/
int /* O - Number of bytes written */
-httpPrintf(http_t *http, /* I - Connection to server */
+httpPrintf(http_t *http, /* I - HTTP connection */
const char *format, /* I - printf-style format string */
...) /* I - Additional args as needed */
{
*/
int /* O - Status of call (0 = success) */
-httpPut(http_t *http, /* I - Connection to server */
+httpPut(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI to put */
{
DEBUG_printf(("httpPut(http=%p, uri=\"%s\")", http, uri));
*/
int /* O - Number of bytes read */
-httpRead(http_t *http, /* I - Connection to server */
+httpRead(http_t *http, /* I - HTTP connection */
char *buffer, /* I - Buffer for data */
int length) /* I - Maximum number of bytes */
{
*/
ssize_t /* O - Number of bytes read */
-httpRead2(http_t *http, /* I - Connection to server */
+httpRead2(http_t *http, /* I - HTTP connection */
char *buffer, /* I - Buffer for data */
size_t length) /* I - Maximum number of bytes */
{
http->state = HTTP_STATE_STATUS;
DEBUG_printf(("1httpRead2: End of content, set state to %s.",
- http_state_string(http->state)));
+ httpStateString(http->state)));
}
return (bytes);
ssize_t /* O - Number of bytes read or -1 on error */
_httpReadGNUTLS(
- gnutls_transport_ptr ptr, /* I - Connection to server */
+ gnutls_transport_ptr ptr, /* I - HTTP connection */
void *data, /* I - Buffer */
size_t length) /* I - Number of bytes to read */
{
else if (http->state != HTTP_STATE_WAITING)
{
DEBUG_printf(("1httpReadRequest: Bad state %s, returning HTTP_STATE_ERROR.",
- http_state_string(http->state)));
+ httpStateString(http->state)));
return (HTTP_STATE_ERROR);
}
if (!*req_uri)
{
DEBUG_puts("1httpReadRequest: No request URI.");
+ _cupsSetError(IPP_STATUS_ERROR_INTERNAL, _("No request URI."), 1);
return (HTTP_STATE_ERROR);
}
if (!*req_version)
{
DEBUG_puts("1httpReadRequest: No request protocol version.");
+ _cupsSetError(IPP_STATUS_ERROR_INTERNAL, _("No request protocol version."), 1);
return (HTTP_STATE_ERROR);
}
else
{
DEBUG_printf(("1httpReadRequest: Unknown method \"%s\".", req_method));
+ _cupsSetError(IPP_STATUS_ERROR_INTERNAL, _("Unknown request method."), 1);
return (HTTP_STATE_UNKNOWN_METHOD);
}
DEBUG_printf(("1httpReadRequest: Set state to %s.",
- http_state_string(http->state)));
+ httpStateString(http->state)));
if (!strcmp(req_version, "HTTP/1.0"))
{
else
{
DEBUG_printf(("1httpReadRequest: Unknown version \"%s\".", req_version));
+ _cupsSetError(IPP_STATUS_ERROR_INTERNAL, _("Unknown request version."), 1);
return (HTTP_STATE_UNKNOWN_VERSION);
}
*/
int /* O - 0 on success, non-zero on failure */
-httpReconnect(http_t *http) /* I - Connection to server */
+httpReconnect(http_t *http) /* I - HTTP connection */
{
DEBUG_printf(("httpReconnect(http=%p)", http));
*/
int /* O - 0 on success, non-zero on failure */
-httpReconnect2(http_t *http, /* I - Connection to server */
+httpReconnect2(http_t *http, /* I - HTTP connection */
int msec, /* I - Timeout in milliseconds */
int *cancel) /* I - Pointer to "cancel" variable */
{
{
DEBUG_printf(("2httpReconnect2: Closing socket %d...", http->fd));
-#ifdef WIN32
- closesocket(http->fd);
-#else
- close(http->fd);
-#endif /* WIN32 */
+ httpAddrClose(NULL, http->fd);
http->fd = -1;
}
if (http_setup_ssl(http) != 0)
{
-# ifdef WIN32
- closesocket(http->fd);
-# else
- close(http->fd);
-# endif /* WIN32 */
+ httpAddrClose(NULL, http->fd);
return (-1);
}
*/
void
-httpSetAuthString(http_t *http, /* I - Connection to server */
+httpSetAuthString(http_t *http, /* I - HTTP connection */
const char *scheme, /* I - Auth scheme (NULL to clear it) */
const char *data) /* I - Auth data (NULL for none) */
{
*/
int /* O - Status of call (0 = success) */
-httpSetCredentials(http_t *http, /* I - Connection to server */
+httpSetCredentials(http_t *http, /* I - HTTP connection */
cups_array_t *credentials) /* I - Array of credentials */
{
if (!http || cupsArrayCount(credentials) < 1)
*/
void
-httpSetDefaultField(http_t *http, /* I - Connection to server */
+httpSetDefaultField(http_t *http, /* I - HTTP connection */
http_field_t field, /* I - Field index */
const char *value)/* I - Value */
{
*/
void
-httpSetExpect(http_t *http, /* I - Connection to server */
+httpSetExpect(http_t *http, /* I - HTTP connection */
http_status_t expect) /* I - HTTP status to expect
(@code HTTP_STATUS_CONTINUE@) */
{
*/
void
-httpSetField(http_t *http, /* I - Connection to server */
+httpSetField(http_t *http, /* I - HTTP connection */
http_field_t field, /* I - Field index */
const char *value) /* I - Value */
{
}
+/*
+ * 'httpSetKeepAlive()' - Set the current Keep-Alive state of a connection.
+ *
+ * @since CUPS 2.0@
+ */
+
+void
+httpSetKeepAlive(
+ http_t *http, /* I - HTTP connection */
+ http_keepalive_t keep_alive) /* I - New Keep-Alive value */
+{
+ if (http)
+ http->keep_alive = keep_alive;
+}
+
+
/*
* 'httpSetLength()' - Set the content-length and content-encoding.
*
*/
void
-httpSetLength(http_t *http, /* I - Connection to server */
+httpSetLength(http_t *http, /* I - HTTP connection */
size_t length) /* I - Length (0 for chunked) */
{
DEBUG_printf(("httpSetLength(http=%p, length=" CUPS_LLFMT ")", http,
void
httpSetTimeout(
- http_t *http, /* I - Connection to server */
+ http_t *http, /* I - HTTP connection */
double timeout, /* I - Number of seconds for timeout,
must be greater than 0 */
http_timeout_cb_t cb, /* I - Callback function or NULL */
}
+/*
+ * 'httpShutdown()' - Shutdown one side of an HTTP connection.
+ *
+ * @since CUPS 2.0@
+ */
+
+void
+httpShutdown(http_t *http) /* I - HTTP connection */
+{
+ if (!http || http->fd < 0)
+ return;
+
+ if (http->tls)
+ http_shutdown_ssl(http);
+
+ shutdown(http->fd, SHUT_RD);
+}
+
+
/*
* 'httpTrace()' - Send an TRACE request to the server.
*/
int /* O - Status of call (0 = success) */
-httpTrace(http_t *http, /* I - Connection to server */
+httpTrace(http_t *http, /* I - HTTP connection */
const char *uri) /* I - URI for trace */
{
return (http_send(http, HTTP_STATE_TRACE, uri));
*/
int /* O - 1 to continue, 0 to stop */
-_httpUpdate(http_t *http, /* I - Connection to server */
+_httpUpdate(http_t *http, /* I - HTTP connection */
http_status_t *status) /* O - Current HTTP status */
{
char line[32768], /* Line from connection... */
DEBUG_printf(("_httpUpdate(http=%p, status=%p), state=%s", http, status,
- http_state_string(http->state)));
+ httpStateString(http->state)));
/*
* Grab a single line from the connection...
{
if (http_setup_ssl(http) != 0)
{
-# ifdef WIN32
- closesocket(http->fd);
-# else
- close(http->fd);
-# endif /* WIN32 */
+ httpAddrClose(NULL, http->fd);
*status = http->status = HTTP_STATUS_ERROR;
return (0);
http->state ++;
DEBUG_printf(("1_httpUpdate: Set state to %s.",
- http_state_string(http->state)));
+ httpStateString(http->state)));
case HTTP_STATE_POST_SEND :
case HTTP_STATE_HEAD :
httpSetCookie(http, value);
}
- else if ((field = http_field(line)) != HTTP_FIELD_UNKNOWN)
+ else if ((field = httpFieldValue(line)) != HTTP_FIELD_UNKNOWN)
httpSetField(http, field, value);
#ifdef DEBUG
else
*/
http_status_t /* O - HTTP status */
-httpUpdate(http_t *http) /* I - Connection to server */
+httpUpdate(http_t *http) /* I - HTTP connection */
{
http_status_t status; /* Request status */
DEBUG_printf(("httpUpdate(http=%p), state=%s", http,
- http_state_string(http->state)));
+ httpStateString(http->state)));
/*
* Flush pending data, if any...
*/
int /* O - 1 if data is available, 0 otherwise */
-_httpWait(http_t *http, /* I - Connection to server */
+_httpWait(http_t *http, /* I - HTTP connection */
int msec, /* I - Milliseconds to wait */
int usessl) /* I - Use SSL context? */
{
*/
int /* O - 1 if data is available, 0 otherwise */
-httpWait(http_t *http, /* I - Connection to server */
+httpWait(http_t *http, /* I - HTTP connection */
int msec) /* I - Milliseconds to wait */
{
/*
*/
int /* O - Number of bytes written */
-httpWrite(http_t *http, /* I - Connection to server */
+httpWrite(http_t *http, /* I - HTTP connection */
const char *buffer, /* I - Buffer for data */
int length) /* I - Number of bytes to write */
{
*/
ssize_t /* O - Number of bytes written */
-httpWrite2(http_t *http, /* I - Connection to server */
+httpWrite2(http_t *http, /* I - HTTP connection */
const char *buffer, /* I - Buffer for data */
size_t length) /* I - Number of bytes to write */
{
http->state = HTTP_STATE_STATUS;
DEBUG_printf(("2httpWrite2: Changed state to %s.",
- http_state_string(http->state)));
+ httpStateString(http->state)));
}
DEBUG_printf(("1httpWrite2: Returning " CUPS_LLFMT ".", CUPS_LLCAST bytes));
ssize_t /* O - Number of bytes written or -1 on error */
_httpWriteGNUTLS(
- gnutls_transport_ptr ptr, /* I - Connection to server */
+ gnutls_transport_ptr ptr, /* I - HTTP connection */
const void *data, /* I - Data buffer */
size_t length) /* I - Number of bytes to write */
{
if (status >= HTTP_STATUS_BAD_REQUEST && http->keep_alive)
{
- http->keep_alive = 0;
+ http->keep_alive = HTTP_KEEPALIVE_OFF;
httpSetField(http, HTTP_FIELD_KEEP_ALIVE, "");
}
}
#ifdef HAVE_SSL
- if (status == HTTP_STATUS_UPGRADE_REQUIRED)
+ if (status == HTTP_STATUS_UPGRADE_REQUIRED ||
+ status == HTTP_STATUS_SWITCHING_PROTOCOLS)
{
if (!http->fields[HTTP_FIELD_CONNECTION][0])
httpSetField(http, HTTP_FIELD_CONNECTION, "Upgrade");
if (!http->fields[HTTP_FIELD_UPGRADE][0])
httpSetField(http, HTTP_FIELD_UPGRADE, "TLS/1.2,TLS/1.1,TLS/1.0");
+
+ if (!http->fields[HTTP_FIELD_CONTENT_LENGTH][0])
+ httpSetField(http, HTTP_FIELD_CONTENT_LENGTH, "0");
}
#endif /* HAVE_SSL */
if (http->cookie)
{
- if (httpPrintf(http, "Set-Cookie: %s path=/%s\r\n", http->cookie,
- http->tls ? " secure" : "") < 1)
+ if (httpPrintf(http, "Set-Cookie: %s path=/ httponly%s\r\n",
+ http->cookie, http->tls ? " secure" : "") < 1)
{
http->status = HTTP_STATUS_ERROR;
return (-1);
return (-1);
}
- if (status == HTTP_STATUS_CONTINUE)
+ if (status == HTTP_STATUS_CONTINUE ||
+ status == HTTP_STATUS_SWITCHING_PROTOCOLS)
{
/*
* Restore the old data_encoding and data_length values...
http->state == HTTP_STATE_STATUS)
{
DEBUG_printf(("1httpWriteResponse: Resetting state to HTTP_STATE_WAITING, "
- "was %s.", http_state_string(http->state)));
+ "was %s.", httpStateString(http->state)));
http->state = HTTP_STATE_WAITING;
}
else
#endif /* DEBUG */
-/*
- * 'http_field()' - Return the field index for a field name.
- */
-
-static http_field_t /* O - Field index */
-http_field(const char *name) /* I - String name */
-{
- int i; /* Looping var */
-
-
- for (i = 0; i < HTTP_FIELD_MAX; i ++)
- if (_cups_strcasecmp(name, http_fields[i]) == 0)
- return ((http_field_t)i);
-
- return (HTTP_FIELD_UNKNOWN);
-}
-
-
/*
* 'http_read()' - Read a buffer from a HTTP connection.
*
*/
static ssize_t /* O - Number of bytes read or -1 on error */
-http_read(http_t *http, /* I - Connection to server */
+http_read(http_t *http, /* I - HTTP connection */
char *buffer, /* I - Buffer */
size_t length) /* I - Maximum bytes to read */
{
*/
static ssize_t /* O - Number of bytes read or -1 on error */
-http_read_buffered(http_t *http, /* I - Connection to server */
+http_read_buffered(http_t *http, /* I - HTTP connection */
char *buffer, /* I - Buffer */
size_t length) /* I - Maximum bytes to read */
{
*/
static ssize_t /* O - Number of bytes read or -1 on error */
-http_read_chunk(http_t *http, /* I - Connection to server */
+http_read_chunk(http_t *http, /* I - HTTP connection */
char *buffer, /* I - Buffer */
size_t length) /* I - Maximum bytes to read */
{
*/
static int /* O - Bytes read */
-http_read_ssl(http_t *http, /* I - Connection to server */
+http_read_ssl(http_t *http, /* I - HTTP connection */
char *buf, /* I - Buffer to store data */
int len) /* I - Length of buffer */
{
*/
static int /* O - 0 on success, non-zero on error */
-http_send(http_t *http, /* I - Connection to server */
+http_send(http_t *http, /* I - HTTP connection */
http_state_t request, /* I - Request code */
const char *uri) /* I - URI */
{
*/
static int /* O - Status of connection */
-http_set_credentials(http_t *http) /* I - Connection to server */
+http_set_credentials(http_t *http) /* I - HTTP connection */
{
_cups_globals_t *cg = _cupsGlobals(); /* Pointer to library globals */
OSStatus error = 0; /* Error code */
DEBUG_printf(("http_set_length(http=%p) mode=%d state=%s", http, http->mode,
- http_state_string(http->state)));
+ httpStateString(http->state)));
if ((remaining = httpGetLength2(http)) >= 0)
{
*/
static void
-http_set_wait(http_t *http) /* I - Connection to server */
+http_set_wait(http_t *http) /* I - HTTP connection */
{
if (http->blocking)
{
*/
static int /* O - 0 on success, -1 on failure */
-http_setup_ssl(http_t *http) /* I - Connection to server */
+http_setup_ssl(http_t *http) /* I - HTTP connection */
{
char hostname[256], /* Hostname */
*hostptr; /* Pointer into hostname */
*/
static void
-http_shutdown_ssl(http_t *http) /* I - Connection to server */
+http_shutdown_ssl(http_t *http) /* I - HTTP connection */
{
# ifdef HAVE_LIBSSL
SSL_CTX *context; /* Context for encryption */
#endif /* HAVE_SSL */
-#ifdef DEBUG
-/*
- * 'http_state_string()' - Return the string associated with a given HTTP state.
- */
-
-static const char * /* O - State string */
-http_state_string(http_state_t state) /* I - HTTP state */
-{
- static char buffer[255]; /* Unknown value buffer */
- static const char * const states[] = /* State strings */
- {
- "HTTP_STATE_ERROR",
- "HTTP_STATE_WAITING",
- "HTTP_STATE_OPTIONS",
- "HTTP_STATE_GET",
- "HTTP_STATE_GET_SEND",
- "HTTP_STATE_HEAD",
- "HTTP_STATE_POST",
- "HTTP_STATE_POST_RECV",
- "HTTP_STATE_POST_SEND",
- "HTTP_STATE_PUT",
- "HTTP_STATE_PUT_RECV",
- "HTTP_STATE_DELETE",
- "HTTP_STATE_TRACE",
- "HTTP_STATE_CONNECT",
- "HTTP_STATE_STATUS",
- "HTTP_STATE_UNKNOWN_METHOD",
- "HTTP_STATE_UNKNOWN_VERSION"
- };
-
- if (state >= HTTP_STATE_ERROR && state <= HTTP_STATE_UNKNOWN_VERSION)
- return (states[state - HTTP_STATE_ERROR]);
-
- snprintf(buffer, sizeof(buffer), "??? %d ???", (int)state);
- return (buffer);
-}
-#endif /* DEBUG */
-
-
#ifdef HAVE_SSL
/*
* 'http_upgrade()' - Force upgrade to TLS encryption.
*/
static int /* O - Status of connection */
-http_upgrade(http_t *http) /* I - Connection to server */
+http_upgrade(http_t *http) /* I - HTTP connection */
{
int ret; /* Return value */
http_t myhttp; /* Local copy of HTTP data */
DEBUG_puts("8http_upgrade: Server does not support HTTP upgrade!");
-# ifdef WIN32
- closesocket(http->fd);
-# else
- close(http->fd);
-# endif
+ httpAddrClose(NULL, http->fd);
http->fd = -1;
*/
static ssize_t /* O - Number of bytes written */
-http_write(http_t *http, /* I - Connection to server */
+http_write(http_t *http, /* I - HTTP connection */
const char *buffer, /* I - Buffer for data */
size_t length) /* I - Number of bytes to write */
{
*/
static ssize_t /* O - Number bytes written */
-http_write_chunk(http_t *http, /* I - Connection to server */
+http_write_chunk(http_t *http, /* I - HTTP connection */
const char *buffer, /* I - Buffer to write */
size_t length) /* I - Length of buffer */
{
*/
static int /* O - Bytes written */
-http_write_ssl(http_t *http, /* I - Connection to server */
+http_write_ssl(http_t *http, /* I - HTTP connection */
const char *buf, /* I - Buffer holding data */
int len) /* I - Length of buffer */
{