| /* |
| * libwebsockets - small server side websockets and web server implementation |
| * |
| * Copyright (C) 2010 Andy Green <andy@warmcat.com> |
| * |
| * 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: |
| * version 2.1 of the License. |
| * |
| * 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 |
| */ |
| |
| #ifndef __LIBWEBSOCKET_H__ |
| #define __LIBWEBSOCKET_H__ |
| |
| #define CONTEXT_PORT_NO_LISTEN 0 |
| |
| #define LWS_SERVER_OPTION_DEFEAT_CLIENT_MASK 1 |
| |
| enum libwebsocket_callback_reasons { |
| LWS_CALLBACK_ESTABLISHED, |
| LWS_CALLBACK_CLIENT_ESTABLISHED, |
| LWS_CALLBACK_CLOSED, |
| LWS_CALLBACK_RECEIVE, |
| LWS_CALLBACK_CLIENT_RECEIVE, |
| LWS_CALLBACK_CLIENT_RECEIVE_PONG, |
| LWS_CALLBACK_CLIENT_WRITEABLE, |
| LWS_CALLBACK_HTTP, |
| LWS_CALLBACK_BROADCAST |
| }; |
| |
| enum libwebsocket_write_protocol { |
| LWS_WRITE_TEXT, |
| LWS_WRITE_BINARY, |
| LWS_WRITE_HTTP, |
| |
| /* special 04 opcodes */ |
| |
| LWS_WRITE_CLOSE, |
| LWS_WRITE_PING, |
| LWS_WRITE_PONG, |
| |
| /* flags */ |
| |
| LWS_WRITE_NO_FIN = 0x40, |
| /* |
| * client packet payload goes out on wire unmunged |
| * only useful for security tests since normal servers cannot |
| * decode the content if used |
| */ |
| LWS_WRITE_CLIENT_IGNORE_XOR_MASK = 0x80 |
| }; |
| |
| struct libwebsocket; |
| struct libwebsocket_context; |
| |
| /* document the generic callback (it's a fake prototype under this) */ |
| /** |
| * callback() - User server actions |
| * @wsi: Opaque websocket instance pointer |
| * @reason: The reason for the call |
| * @user: Pointer to per-session user data allocated by library |
| * @in: Pointer used for some callback reasons |
| * @len: Length set for some callback reasons |
| * |
| * This callback is the way the user controls what is served. All the |
| * protocol detail is hidden and handled by the library. |
| * |
| * For each connection / session there is user data allocated that is |
| * pointed to by "user". You set the size of this user data area when |
| * the library is initialized with libwebsocket_create_server. |
| * |
| * You get an opportunity to initialize user data when called back with |
| * LWS_CALLBACK_ESTABLISHED reason. |
| * |
| * LWS_CALLBACK_ESTABLISHED: after the server completes a handshake with |
| * an incoming client |
| * |
| * LWS_CALLBACK_CLIENT_ESTABLISHED: after your client connection completed |
| * a handshake with the remote server |
| * |
| * LWS_CALLBACK_CLOSED: when the websocket session ends |
| * |
| * LWS_CALLBACK_BROADCAST: signal to send to client (you would use |
| * libwebsocket_write() taking care about the |
| * special buffer requirements |
| * |
| * LWS_CALLBACK_RECEIVE: data has appeared for this server endpoint from a |
| * remote client, it can be found at *in and is |
| * len bytes long |
| * |
| * LWS_CALLBACK_CLIENT_RECEIVE_PONG: if you elected to see PONG packets, |
| * they appear with this callback reason. PONG |
| * packets only exist in 04+ protocol |
| * |
| * LWS_CALLBACK_CLIENT_RECEIVE: data has appeared from the server for the |
| * client connection, it can be found at *in and |
| * is len bytes long |
| * |
| * LWS_CALLBACK_HTTP: an http request has come from a client that is not |
| * asking to upgrade the connection to a websocket |
| * one. This is a chance to serve http content, |
| * for example, to send a script to the client |
| * which will then open the websockets connection. |
| * @in points to the URI path requested and |
| * libwebsockets_serve_http_file() makes it very |
| * simple to send back a file to the client. |
| * |
| * LWS_CALLBACK_CLIENT_WRITEABLE: if you call |
| * libwebsocket_callback_on_writable() on a connection, you will |
| * get this callback coming when the connection socket is able to |
| * accept another write packet without blocking. If it already |
| * was able to take another packet without blocking, you'll get |
| * this callback at the next call to the service loop function. |
| */ |
| extern int callback(struct libwebsocket *wsi, |
| enum libwebsocket_callback_reasons reason, void *user, |
| void *in, size_t len); |
| |
| /** |
| * struct libwebsocket_protocols - List of protocols and handlers server |
| * supports. |
| * @name: Protocol name that must match the one given in the client |
| * Javascript new WebSocket(url, 'protocol') name |
| * @callback: The service callback used for this protocol. It allows the |
| * service action for an entire protocol to be encapsulated in |
| * the protocol-specific callback |
| * @per_session_data_size: Each new connection using this protocol gets |
| * this much memory allocated on connection establishment and |
| * freed on connection takedown. A pointer to this per-connection |
| * allocation is passed into the callback in the 'user' parameter |
| * @owning_server: the server init call fills in this opaque pointer when |
| * registering this protocol with the server. |
| * @broadcast_socket_port: the server init call fills this in with the |
| * localhost port number used to forward broadcasts for this |
| * protocol |
| * @broadcast_socket_user_fd: the server init call fills this in ... the main() |
| * process context can write to this socket to perform broadcasts |
| * (use the libwebsockets_broadcast() api to do this instead, |
| * it works from any process context) |
| * @protocol_index: which protocol we are starting from zero |
| * |
| * This structure represents one protocol supported by the server. An |
| * array of these structures is passed to libwebsocket_create_server() |
| * allows as many protocols as you like to be handled by one server. |
| */ |
| |
| struct libwebsocket_protocols { |
| const char *name; |
| int (*callback)(struct libwebsocket *wsi, |
| enum libwebsocket_callback_reasons reason, void *user, |
| void *in, size_t len); |
| size_t per_session_data_size; |
| |
| /* |
| * below are filled in on server init and can be left uninitialized, |
| * no need for user to use them directly either |
| */ |
| |
| struct libwebsocket_context *owning_server; |
| int broadcast_socket_port; |
| int broadcast_socket_user_fd; |
| int protocol_index; |
| }; |
| |
| extern struct libwebsocket_context * |
| libwebsocket_create_context(int port, |
| struct libwebsocket_protocols *protocols, |
| const char *ssl_cert_filepath, |
| const char *ssl_private_key_filepath, int gid, int uid, |
| unsigned int options); |
| |
| extern void |
| libwebsocket_context_destroy(struct libwebsocket_context *this); |
| |
| extern int |
| libwebsockets_fork_service_loop(struct libwebsocket_context *this); |
| |
| extern int |
| libwebsocket_service(struct libwebsocket_context *this, int timeout_ms); |
| |
| /* |
| * IMPORTANT NOTICE! |
| * |
| * When sending with websocket protocol (LWS_WRITE_TEXT or LWS_WRITE_BINARY) |
| * the send buffer has to have LWS_SEND_BUFFER_PRE_PADDING bytes valid BEFORE |
| * buf, and LWS_SEND_BUFFER_POST_PADDING bytes valid AFTER (buf + len). |
| * |
| * This allows us to add protocol info before and after the data, and send as |
| * one packet on the network without payload copying, for maximum efficiency. |
| * |
| * So for example you need this kind of code to use libwebsocket_write with a |
| * 128-byte payload |
| * |
| * char buf[LWS_SEND_BUFFER_PRE_PADDING + 128 + LWS_SEND_BUFFER_POST_PADDING]; |
| * |
| * // fill your part of the buffer... for example here it's all zeros |
| * memset(&buf[LWS_SEND_BUFFER_PRE_PADDING], 0, 128); |
| * |
| * libwebsocket_write(wsi, &buf[LWS_SEND_BUFFER_PRE_PADDING], 128); |
| * |
| * When sending LWS_WRITE_HTTP, there is no protocol addition and you can just |
| * use the whole buffer without taking care of the above. |
| */ |
| |
| /* this is the frame nonce plus two header plus 8 length */ |
| |
| #define LWS_SEND_BUFFER_PRE_PADDING (4 + 10) |
| #define LWS_SEND_BUFFER_POST_PADDING 1 |
| |
| extern int |
| libwebsocket_write(struct libwebsocket *wsi, unsigned char *buf, size_t len, |
| enum libwebsocket_write_protocol protocol); |
| |
| extern int |
| libwebsockets_serve_http_file(struct libwebsocket *wsi, const char *file, |
| const char *content_type); |
| |
| /* notice - you need the pre- and post- padding allocation for buf below */ |
| |
| extern int |
| libwebsockets_broadcast(const struct libwebsocket_protocols *protocol, |
| unsigned char *buf, size_t len); |
| |
| extern const struct libwebsocket_protocols * |
| libwebsockets_get_protocol(struct libwebsocket *wsi); |
| |
| extern int |
| libwebsocket_callback_on_writable(struct libwebsocket *wsi); |
| |
| extern int |
| libwebsocket_callback_on_writable_all_protocol( |
| const struct libwebsocket_protocols *protocol); |
| |
| extern int |
| libwebsocket_get_socket_fd(struct libwebsocket *wsi); |
| |
| extern int |
| libwebsocket_rx_flow_control(struct libwebsocket *wsi, int enable); |
| |
| extern size_t |
| libwebsockets_remaining_packet_payload(struct libwebsocket *wsi); |
| |
| extern struct libwebsocket * |
| libwebsocket_client_connect(struct libwebsocket_context *clients, |
| const char *address, |
| int port, |
| int ssl_connection, |
| const char *path, |
| const char *host, |
| const char *origin, |
| const char *protocol); |
| |
| extern const char * |
| libwebsocket_canonical_hostname(struct libwebsocket_context *this); |
| |
| extern void |
| libwebsocket_client_close(struct libwebsocket *wsi); |
| |
| #endif |