aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md27
-rw-r--r--plugins/framing_fixedlength.c36
-rw-r--r--plugins/framing_fixedlength.md9
-rw-r--r--plugins/makefile5
-rw-r--r--websocksy.c4
-rw-r--r--websocksy.h1
6 files changed, 77 insertions, 5 deletions
diff --git a/README.md b/README.md
index 369f44d..83f1656 100644
--- a/README.md
+++ b/README.md
@@ -3,7 +3,8 @@
`websocksy` is a highly configurable [WebSocket (RFC6455)](https://tools.ietf.org/html/rfc6455) to 'normal' networking transport (TCP/UDP/Unix sockets) bridge.
It is written in C and supports pluggable modules for bridge peer selection modules (for dynamic bridging) and stream framing.
-It can be used to connect a wide variety of existing applications directly to a website, or to implement new functionality in a way that maintains compatibility between traditional network transports and WebSockets.
+It can be used to connect a wide variety of existing applications directly to a website, or to implement new functionality in a way that maintains compatibility
+between traditional network transports and WebSockets.
## Table of contents
@@ -15,6 +16,7 @@ It can be used to connect a wide variety of existing applications directly to a
* [Command line arguments](#command-line-arguments)
* [Configuration file](#configuration-file)
* [Default backend](#default-backend)
+ * [Plugins](#plugins)
* [Building](#building)
* [Development](#development)
* [Peer discovery backend API](#peer-discovery-backend-api)
@@ -104,7 +106,7 @@ at the time.
* `-p <port>`: Set the listen port for incoming WebSocket connections (Default: `8001`)
* `-l <host>`: Set the host for listening for incoming WebSocket connections (Default: `::`)
-* `-k <seconds>`: Set the inactivity timeout for sending WebSocket keep-alive pings
+* `-k <seconds>`: Set the inactivity timeout for sending WebSocket keep-alive pings (Default: `30`)
* `-b <backend>`: Select external backend
* `-c <option>=<value>`: Pass configuration option to backend
@@ -135,7 +137,15 @@ The integrated default backend takes the following configuration arguments:
* `framing`: The name of a framing function to be used (`auto` is used when none is specified)
* `protocol`: The subprotocol to negotiate with the WebSocket peer. If not set, only the empty protocol set is accepted, which
fails clients indicating an explicitly supported subprotocol. The special value `*` matches the first available protocol.
-* `framing-config`: Arguments to the framing function
+* `framing-config`: Configuration data for the framing function
+
+## Plugins
+
+This repository comes with some plugins already included, in addition to the built-in backend and framing functions.
+Documentation for these resides in the `plugins/` directory.
+
+ * [backend\_file](plugins/backend_file.md)
+ * [framing\_fixedlength](plugins/framing_fixedlength.md)
# Building
@@ -174,6 +184,15 @@ From the backend shared object, `websocksy` tries to resolve the following symbo
will be `free`'d by the core.
* `cleanup` (`void cleanup()`): Release all allocated memory. Called in preparation to core shutdown.
+The [`file` backend](plugins/backend_file.c) is provided as a reference backend implementation.
+
## Peer stream framing API
-TBD
+At startup, `websocksy` tries to load all shared objects in the plugin path (`plugins/` by default) that have a file
+name ending in `.so` and not starting with `backend_` (which is reserved for backend plugins, of which only one may be
+loaded at run time). Plugins may declare their own initializer functions using e.g. the compiler's `__attribute__((constructor))`
+syntax or the linker. To register a framing function with the framing function library, the initializer function should call the
+function `core_register_framing(char* name, ws_framing func)`, exported by the core.
+
+An example plugin providing the [`fixedlength` framing function](plugins/framing_fixedlength.c) is provided in the repository.
+Additions to the `websocksy` plugin library are welcome!
diff --git a/plugins/framing_fixedlength.c b/plugins/framing_fixedlength.c
new file mode 100644
index 0000000..1a66df4
--- /dev/null
+++ b/plugins/framing_fixedlength.c
@@ -0,0 +1,36 @@
+#include <stdio.h>
+
+#include "../websocksy.h"
+
+static int64_t framing_fixedlen(uint8_t* data, size_t length, size_t last_read, ws_operation* opcode, void** framing_data, const char* config){
+ size_t* frame_size = framing_data ? (size_t*) (*framing_data) : NULL;
+
+ if(data && !frame_size){
+ frame_size = calloc(1, sizeof(size_t));
+ if(!frame_size){
+ fprintf(stderr, "Failed to allocate memory\n");
+ return -1;
+ }
+
+ *frame_size = strtoul(config, NULL, 0);
+ *framing_data = frame_size;
+ }
+ else if(!data && frame_size){
+ free(*framing_data);
+ *framing_data = NULL;
+ }
+
+ if(!(*frame_size)){
+ return length;
+ }
+
+ if(length >= *frame_size){
+ return *frame_size;
+ }
+
+ return 0;
+}
+
+static void __attribute__((constructor)) init(){
+ core_register_framing("fixedlength", framing_fixedlen);
+}
diff --git a/plugins/framing_fixedlength.md b/plugins/framing_fixedlength.md
new file mode 100644
index 0000000..bd095c4
--- /dev/null
+++ b/plugins/framing_fixedlength.md
@@ -0,0 +1,9 @@
+# The `fixedlength` framing function
+
+The `fixedlength` peer stream framing function segments the peer stream into binary frames
+at fixed byte boundaries (for example, aggregating and then sending 32-byte fragments from the
+peer stream).
+
+## Configuration
+
+The framing configuration string is simply the length of the segments to transmit in bytes.
diff --git a/plugins/makefile b/plugins/makefile
index 1a6ef36..feab4cd 100644
--- a/plugins/makefile
+++ b/plugins/makefile
@@ -1,5 +1,5 @@
.PHONY: all clean
-PLUGINS = backend_file.so
+PLUGINS = backend_file.so framing_fixedlength.so
CFLAGS += -fPIC -g -I../
LDFLAGS += -shared
@@ -7,6 +7,9 @@ LDFLAGS += -shared
%.so :: %.c %.h
$(CC) $(CFLAGS) $(LDLIBS) $< -o $@ $(LDFLAGS)
+%.so :: %.c
+ $(CC) $(CFLAGS) $(LDLIBS) $< -o $@ $(LDFLAGS)
+
all: $(PLUGINS)
clean:
diff --git a/websocksy.c b/websocksy.c
index 8b37cec..5c29f8c 100644
--- a/websocksy.c
+++ b/websocksy.c
@@ -194,6 +194,10 @@ ws_framing core_framing(char* name){
return plugin_framing(name);
}
+int core_register_framing(char* name, ws_framing func){
+ return plugin_register_framing(name, func);
+}
+
/* Signal handler, attached to SIGINT */
static void signal_handler(int signum){
shutdown_requested = 1;
diff --git a/websocksy.h b/websocksy.h
index 6524977..a97784b 100644
--- a/websocksy.h
+++ b/websocksy.h
@@ -200,6 +200,7 @@ typedef struct /*_ws_backend*/ {
/* Core API */
ws_framing core_framing(char* name);
+int core_register_framing(char* name, ws_framing func);
/* Internal helper functions */
char* xstr_lower(char* in);