Previous: , Up: microhttpd-responses   [Contents][Index]


8.6 Creating a response for protocol upgrades

With RFC 2817 a mechanism to switch protocols within HTTP was introduced. Here, a client sends a request with a “Connection: Upgrade” header. The server responds with a “101 Switching Protocols” response header, after which the two parties begin to speak a different (non-HTTP) protocol over the TCP connection.

This mechanism is used for upgrading HTTP 1.1 connections to HTTP2 or HTTPS, as well as for implementing WebSockets. Which protocol upgrade is performed is negotiated between server and client in additional headers, in particular the “Upgrade” header.

MHD supports switching protocols using this mechanism only if the MHD_ALLOW_SUSPEND_RESUME flag has been set when starting the daemon. If this flag has been set, applications can upgrade a connection by queueing a response (using the MHD_HTTP_SWITCHING_PROTOCOLS status code) which must have been created with the following function:

Function: enum MHD_Result MHD_create_response_for_upgrade (MHD_UpgradeHandler upgrade_handler, void *upgrade_handler_cls)

Create a response suitable for switching protocols. Returns MHD_YES on success. upgrade_handler must not be NULL.

When creating this type of response, the “Connection: Upgrade” header will be set automatically for you. MHD requires that you additionally set an “Upgrade:” header. The “Upgrade” header must simply exist, the specific value is completely up to the application.

The upgrade_handler argument to the above has the following type:

Function Pointer: void *MHD_UpgradeHandler (void *cls, struct MHD_Connection *connection, const char *extra_in, size_t extra_in_size, MHD_socket sock, struct MHD_UpgradeResponseHandle *urh)

This function will be called once MHD has transmitted the header of the response to the connection that is being upgraded. At this point, the application is expected to take over the socket sock and speak the non-HTTP protocol to which the connection was upgraded. MHD will no longer use the socket; this includes handling timeouts. The application must call MHD_upgrade_action with an upgrade action of MHD_UPGRADE_ACTION_CLOSE when it is done processing the connection to close the socket. The application must not call MHD_stop_daemon on the respective daemon as long as it is still handling the connection. The arguments given to the upgrade_handler have the following meaning:

cls

matches the upgrade_handler_cls that was given to MHD_create_response_for_upgrade

connection

identifies the connection that is being upgraded;

con_cls

last value left in ‘*con_cls‘ in the ‘MHD_AccessHandlerCallback‘

extra_in

buffer of bytes MHD read “by accident” from the socket already. This can happen if the client eagerly transmits more than just the HTTP request. The application should treat these as if it had read them from the socket.

extra_in_size

number of bytes in extra_in

sock

the socket which the application can now use directly for some bi-directional communication with the client. The application can henceforth use recv() and send() or read() and write() system calls on the socket. However, ioctl() and setsockopt() functions will not work as expected when using HTTPS. Such operations may be supported in the future via MHD_upgrade_action. Most importantly, the application must never call close() on this socket. Closing the socket must be done using MHD_upgrade_action. However, while close is forbidden, the application may call shutdown() on the socket.

urh

argument for calls to MHD_upgrade_action. Applications must eventually use this function to perform the close() action on the socket.

Function: enum MHD_Result MHD_upgrade_action (struct MHD_UpgradeResponseHandle *urh, enum MHD_UpgradeAction action, ...)

Perform special operations related to upgraded connections.

urh

identifies the upgraded connection to perform an action on

action

specifies the action to perform; further arguments to the function depend on the specifics of the action.

Enumeration: MHD_UpgradeAction

Set of actions to be performed on upgraded connections. Passed as an argument to MHD_upgrade_action().

MHD_UPGRADE_ACTION_CLOSE

Closes the connection. Must be called once the application is done with the client. Takes no additional arguments.

MHD_UPGRADE_ACTION_CORK_ON

Enable corking on the underlying socket.

MHD_UPGRADE_ACTION_CORK_OFF

Disable corking on the underlying socket.


Previous: , Up: microhttpd-responses   [Contents][Index]