| /* |
| This file is part of libmicrohttpd |
| Copyright (C) 2007-2018 Daniel Pittman and Christian Grothoff |
| |
| This library is free software; you can redistribute it and/or |
| modify it under the terms of the GNU Lesser General Public |
| License as published by the Free Software Foundation; either |
| version 2.1 of the License, or (at your option) any later version. |
| |
| This library is distributed in the hope that it will be useful, |
| but WITHOUT ANY WARRANTY; without even the implied warranty of |
| MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
| Lesser General Public License for more details. |
| |
| You should have received a copy of the GNU Lesser General Public |
| License along with this library; if not, write to the Free Software |
| Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
| */ |
| |
| /** |
| * @file lib/response_for_upgrade.c |
| * @brief implementation of MHD_response_for_upgrade() |
| * @author Christian Grothoff |
| */ |
| #include "internal.h" |
| |
| |
| /** |
| * Create a response object that can be used for 101 UPGRADE |
| * responses, for example to implement WebSockets. After sending the |
| * response, control over the data stream is given to the callback (which |
| * can then, for example, start some bi-directional communication). |
| * If the response is queued for multiple connections, the callback |
| * will be called for each connection. The callback |
| * will ONLY be called after the response header was successfully passed |
| * to the OS; if there are communication errors before, the usual MHD |
| * connection error handling code will be performed. |
| * |
| * MHD will automatically set the correct HTTP status |
| * code (#MHD_HTTP_SWITCHING_PROTOCOLS). |
| * Setting correct HTTP headers for the upgrade must be done |
| * manually (this way, it is possible to implement most existing |
| * WebSocket versions using this API; in fact, this API might be useful |
| * for any protocol switch, not just WebSockets). Note that |
| * draft-ietf-hybi-thewebsocketprotocol-00 cannot be implemented this |
| * way as the header "HTTP/1.1 101 WebSocket Protocol Handshake" |
| * cannot be generated; instead, MHD will always produce "HTTP/1.1 101 |
| * Switching Protocols" (if the response code 101 is used). |
| * |
| * As usual, the response object can be extended with header |
| * information and then be used any number of times (as long as the |
| * header information is not connection-specific). |
| * |
| * @param upgrade_handler function to call with the "upgraded" socket |
| * @param upgrade_handler_cls closure for @a upgrade_handler |
| * @return NULL on error (i.e. invalid arguments, out of memory) |
| */ |
| struct MHD_Response * |
| MHD_response_for_upgrade (MHD_UpgradeHandler upgrade_handler, |
| void *upgrade_handler_cls) |
| { |
| #ifdef UPGRADE_SUPPORT |
| struct MHD_Response *response; |
| |
| mhd_assert (NULL != upgrade_handler); |
| response = MHD_calloc_ (1, |
| sizeof (struct MHD_Response)); |
| if (NULL == response) |
| return NULL; |
| if (! MHD_mutex_init_ (&response->mutex)) |
| { |
| free (response); |
| return NULL; |
| } |
| response->upgrade_handler = upgrade_handler; |
| response->upgrade_handler_cls = upgrade_handler_cls; |
| response->status_code = MHD_HTTP_SWITCHING_PROTOCOLS; |
| response->total_size = MHD_SIZE_UNKNOWN; |
| response->reference_count = 1; |
| if (MHD_NO == |
| MHD_response_add_header (response, |
| MHD_HTTP_HEADER_CONNECTION, |
| "Upgrade")) |
| { |
| MHD_response_queue_for_destroy (response); |
| return NULL; |
| } |
| return response; |
| #else |
| return NULL; |
| #endif |
| } |
| |
| |
| /* end of response_for_upgrade.c */ |