diff --git a/web/js/nbd.js b/web/js/nbd.js
new file mode 100644
index 0000000..1de4d3b
--- /dev/null
+++ b/web/js/nbd.js
@@ -0,0 +1,355 @@
+/* Copyright 2018 IBM Corp.
+ *
+ * Author: Jeremy Kerr <jk@ozlabs.org>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License.  You may obtain a copy
+ * of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ */
+
+/* handshake flags */
+const NBD_FLAG_FIXED_NEWSTYLE = 0x1;
+const NBD_FLAG_NO_ZEROES = 0x2;
+
+/* transmission flags */
+const NBD_FLAG_HAS_FLAGS = 0x1;
+const NBD_FLAG_READ_ONLY = 0x2;
+
+/* option negotiation */
+const NBD_OPT_EXPORT_NAME = 0x1;
+const NBD_REP_FLAG_ERROR = 0x1 << 31;
+const NBD_REP_ERR_UNSUP = NBD_REP_FLAG_ERROR | 1;
+
+/* command definitions */
+const NBD_CMD_READ = 0;
+const NBD_CMD_WRITE = 1;
+const NBD_CMD_DISC = 2;
+const NBD_CMD_FLUSH = 3;
+const NBD_CMD_TRIM = 4;
+
+/* errno */
+const EPERM = 1;
+const EIO = 5;
+const ENOMEM = 12;
+const EINVAL = 22;
+const ENOSPC = 28;
+const EOVERFLOW = 75;
+const ESHUTDOWN = 108;
+
+/* internal object state */
+const NBD_STATE_UNKNOWN = 1;
+const NBD_STATE_OPEN = 2;
+const NBD_STATE_WAIT_CFLAGS = 3;
+const NBD_STATE_WAIT_OPTION = 4;
+const NBD_STATE_TRANSMISSION = 5;
+
+function NBDServer(endpoint, file)
+{
+    this.file = file;
+    this.endpoint = endpoint;
+    this.ws = null;
+    this.state = NBD_STATE_UNKNOWN;
+    this.msgbuf = null;
+
+    this.start = function()
+    {
+        this.state = NBD_STATE_OPEN;
+        this.ws = new WebSocket(this.endpoint);
+        this.ws.binaryType = 'arraybuffer';
+        this.ws.onmessage = this._on_ws_message.bind(this);
+        this.ws.onopen = this._on_ws_open.bind(this);
+    }
+
+    this.stop = function()
+    {
+        this.ws.close();
+        this.state = NBD_STATE_UNKNOWN;
+    }
+
+    this._log = function(msg)
+    {
+        if (this.onlog)
+            this.onlog(msg);
+    }
+
+    /* websocket event handlers */
+    this._on_ws_open = function(ev)
+    {
+        this.client = {
+            flags: 0,
+        };
+        this._negotiate();
+    }
+
+    this._on_ws_message = function(ev)
+    {
+        var data = ev.data;
+
+        if (this.msgbuf == null) {
+            this.msgbuf = data;
+        } else {
+            var tmp = new Uint8Array(this.msgbuf.byteLength + data.byteLength);
+            tmp.set(new Uint8Array(this.msgbuf), 0);
+            tmp.set(new Uint8Array(data), this.msgbuf.byteLength);
+            this.msgbuf = tmp.buffer;
+        }
+
+        for (;;) {
+            var handler = this.recv_handlers[this.state];
+            if (!handler) {
+                this._log("no handler for state " + this.state);
+                this.stop();
+                break;
+            }
+
+            var consumed = handler(this.msgbuf);
+            if (consumed < 0) {
+                this._log("handler[state=" + this.state +
+                        "] returned error " + consumed);
+                this.stop();
+                break;
+            }
+
+            if (consumed == 0)
+                break;
+
+            if (consumed > 0) {
+                if (consumed == this.msgbuf.byteLength) {
+                    this.msgbuf = null;
+                    break;
+                }
+                this.msgbuf = this.msgbuf.slice(consumed);
+            }
+        }
+    }
+
+    this._negotiate = function()
+    {
+        var buf = new ArrayBuffer(18);
+        var data = new DataView(buf, 0, 18);
+
+        /* NBD magic: NBDMAGIC */
+        data.setUint32(0,  0x4e42444d);
+        data.setUint32(4,  0x41474943);
+
+        /* newstyle negotiation: IHAVEOPT */
+        data.setUint32(8,  0x49484156);
+        data.setUint32(12, 0x454F5054);
+
+        /* flags: fixed newstyle negotiation, no padding */
+        data.setUint16(16, NBD_FLAG_FIXED_NEWSTYLE | NBD_FLAG_NO_ZEROES);
+
+        this.state = NBD_STATE_WAIT_CFLAGS;
+        this.ws.send(buf);
+    }
+
+    /* handlers */
+    this._handle_cflags = function(buf)
+    {
+        if (buf.byteLength < 4)
+            return 0;
+
+        var data = new DataView(buf, 0, 4);
+        this.client.flags = data.getUint32(0);
+
+        this._log("client flags received: 0x" +
+                this.client.flags.toString(16));
+
+        this.state = NBD_STATE_WAIT_OPTION;
+        return 4;
+    }
+
+    this._handle_option = function(buf)
+    {
+        if (buf.byteLength < 16)
+            return 0;
+
+        var data = new DataView(buf, 0, 16);
+        if (data.getUint32(0) != 0x49484156 ||
+                data.getUint32(4) != 0x454F5054) {
+            this._log("invalid option magic");
+            return -1;
+        }
+
+        var opt = data.getUint32(8);
+        var len = data.getUint32(12);
+
+        this._log("client option received: 0x" + opt.toString(16));
+
+        if (buf.byteLength < 16 + len)
+            return 0;
+
+        switch (opt) {
+        case NBD_OPT_EXPORT_NAME:
+            this._log("negotiation complete, starting transmission mode");
+            var n = 10;
+            if (!(this.client.flags & NBD_FLAG_NO_ZEROES))
+                n += 124;
+            var resp = new ArrayBuffer(n);
+            var view = new DataView(resp, 0, 10);
+            /* export size. todo: 64 bits? */
+            view.setUint32(0, 0);
+            view.setUint32(4, this.file.size & 0xffffffff);
+            /* transmission flags: read-only */
+            view.setUint16(8, NBD_FLAG_HAS_FLAGS | NBD_FLAG_READ_ONLY);
+            this.ws.send(resp);
+
+            this.state = NBD_STATE_TRANSMISSION;
+            break;
+
+        default:
+            /* reject other options */
+            var resp = new ArrayBuffer(20);
+            var view = new DataView(resp, 0, 20);
+            view.setUint32(0, 0x0003e889);
+            view.setUint32(4, 0x045565a9);
+            view.setUint32(8, opt);
+            view.setUint32(12, NBD_REP_ERR_UNSUP);
+            view.setUint32(16, 0);
+            this.ws.send(resp);
+        }
+
+        return 16 + len;
+    }
+
+    this._create_cmd_response = function(req, rc, data = null)
+    {
+        var len = 16;
+        if (data)
+            len += data.byteLength;
+        var resp = new ArrayBuffer(len);
+        var view = new DataView(resp, 0, 16);
+        view.setUint32(0, 0x67446698);
+        view.setUint32(4, rc);
+        view.setUint32(8, req.handle_msB);
+        view.setUint32(12, req.handle_lsB);
+        if (data)
+            new Uint8Array(resp, 16).set(new Uint8Array(data));
+        return resp;
+    }
+
+    this._handle_cmd = function(buf)
+    {
+        if (buf.byteLength < 28)
+            return 0;
+
+        var view = new DataView(buf, 0, 28);
+
+        if (view.getUint32(0) != 0x25609513) {
+            this._log("invalid request magic");
+            return -1;
+        }
+
+        var req = {
+            flags: view.getUint16(4),
+            type: view.getUint16(6),
+            handle_msB: view.getUint32(8),
+            handle_lsB: view.getUint32(12),
+            offset_msB: view.getUint32(16),
+            offset_lsB: view.getUint32(20),
+            length: view.getUint32(24),
+        };
+
+        /* we don't support writes, so nothing needs the data at present */
+        /* req.data = buf.slice(28); */
+
+        var err = 0;
+	var consumed = 28;
+
+        /* the command handlers return 0 on success, and send their
+         * own response. Otherwise, a non-zero error code will be
+         * used as a simple error response
+         */
+        switch (req.type) {
+        case NBD_CMD_READ:
+            err = this._handle_cmd_read(req);
+            break;
+
+        case NBD_CMD_DISC:
+            err = this._handle_cmd_disconnect(req);
+            break;
+
+        case NBD_CMD_WRITE:
+	    /* we also need length bytes of data to consume a write
+	     * request */
+	    if (buf.byteLength < 28 + req.length)
+		    return 0;
+	    consumed += req.length;
+	    err = EPERM;
+	    break;
+
+        case NBD_CMD_TRIM:
+            err = EPERM;
+            break;
+        
+        default:
+            this._log("invalid command 0x" + req.type.toString(16));
+            err = EINVAL;
+        }
+
+        if (err) {
+            var resp = this._create_cmd_response(req, err);
+            this.ws.send(resp);
+        }
+
+        return consumed;
+    }
+
+    this._handle_cmd_read = function(req)
+    {
+        if (req.offset_msB)
+            return ENOSPC;
+
+        if (req.offset_lsB + req.length > file.size)
+            return ENOSPC;
+
+        this._log("read: 0x" + req.length.toString(16) +
+                " bytes, offset 0x" + req.offset_lsB.toString(16));
+
+        var blob = this.file.slice(req.offset_lsB,
+                req.offset_lsB + req.length);
+        var reader = new FileReader();
+
+        reader.onload = (function(ev) {
+            var reader = ev.target;
+            if (reader.readyState != FileReader.DONE)
+                return;
+            var resp = this._create_cmd_response(req, 0, reader.result);
+            this.ws.send(resp);
+        }).bind(this);
+
+        reader.onerror = (function(ev) {
+            var reader = ev.target;
+            this._log("error reading file: " + reader.error);
+            var resp = this._create_cmd_response(req, EIO);
+            this.ws.send(resp);
+        }).bind(this);
+
+        reader.readAsArrayBuffer(blob);
+
+        return 0;
+    }
+
+    this._handle_cmd_disconnect = function(req)
+    {
+            this._log("disconnect received");
+            this.stop();
+            return 0;
+    }
+
+    this.recv_handlers = Object.freeze({
+        [NBD_STATE_WAIT_CFLAGS]: this._handle_cflags.bind(this),
+        [NBD_STATE_WAIT_OPTION]: this._handle_option.bind(this),
+        [NBD_STATE_TRANSMISSION]: this._handle_cmd.bind(this),
+    });
+}
+
+
