diff --git a/fastclient/Makefile b/fastclient/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..032ab9a9bdf3ac3c7f82eed6d3da2afd0eadb7a8
--- /dev/null
+++ b/fastclient/Makefile
@@ -0,0 +1,11 @@
+flash: flash.o
+	g++ -lzmq -o $@ $<
+
+snow: snow.o
+	g++ -lzmq -o $@ $<
+
+client: client.o
+	g++ -lzmq -o $@ $<
+
+%.o: %.c
+	g++ -W -Wall -Wextra -pedantic -std=c++11 -c -o $@ $<
diff --git a/fastclient/client.c b/fastclient/client.c
new file mode 100644
index 0000000000000000000000000000000000000000..4432d3f9b82116752aa79af4a487f4d61c0bf857
--- /dev/null
+++ b/fastclient/client.c
@@ -0,0 +1,94 @@
+// Hello World client
+#include <zmq.h>
+#include <string.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <stdlib.h>
+
+#include <vector>
+
+#define WIDTH 480
+#define HEIGHT 70
+
+#define CMD_PIXEL 0
+#define CMD_BLIT 1
+
+struct msgSetPixel {
+  uint8_t cmd;
+  uint32_t x;
+  uint32_t y;
+  uint8_t on;
+} __attribute__ ((packed));
+
+struct msgBlit {
+  uint8_t cmd;
+  uint32_t x;
+  uint32_t y;
+  uint32_t w;
+  uint32_t h;
+  uint8_t data[0];
+} __attribute__ ((packed));
+
+int main (void) {
+  void *context = zmq_ctx_new ();
+  void *requester;
+
+  requester = zmq_socket (context, ZMQ_REQ);
+  zmq_connect(requester, "tcp://mensadisplay:5556");
+  // zmq_connect(requester, "tcp://192.168.178.147:5570");
+  // zmq_connect(requester, "tcp://localhost:5556");
+
+  int x = 0;
+
+  msgBlit *onLine = reinterpret_cast<msgBlit *>(malloc(sizeof(msgBlit) + 70));
+  onLine->cmd = CMD_BLIT;
+  onLine->y = 0;
+  onLine->w = 1;
+  onLine->h = HEIGHT;
+  for(int i = 0; i < 70; ++i) onLine->data[i] = 255;
+
+  msgBlit *offLine = reinterpret_cast<msgBlit *>(malloc(sizeof(msgBlit) + 70));
+  offLine->cmd = CMD_BLIT;
+  offLine->y = 0;
+  offLine->w = 1;
+  offLine->h = HEIGHT;
+  for(int i = 0; i < 70; ++i) offLine->data[i] = 0;
+
+  while(1) {
+    zmq_msg_t msg;
+//    for(int i = 0; i < HEIGHT; ++i) {
+//      zmq_msg_init_size(&msg, sizeof(msgSetPixel));
+//      msgSetPixel set = { CMD_PIXEL, static_cast<uint32_t>((x + 1) % 480), static_cast<uint32_t>(i), 1 };
+//      memcpy(zmq_msg_data(&msg), &set, sizeof(set));
+//      zmq_msg_send(&msg, requester, ZMQ_SNDMORE);
+//    }
+//
+//    for(int i = HEIGHT; i < HEIGHT * 2; ++i) {
+//      zmq_msg_init_size(&msg, sizeof(msgSetPixel));
+//      msgSetPixel set = { CMD_PIXEL, static_cast<uint32_t>(x % 480), static_cast<uint32_t>(i - HEIGHT), 0 };
+//      memcpy(zmq_msg_data(&msg), &set, sizeof(set));
+//      zmq_msg_send(&msg, requester, ZMQ_SNDMORE);
+//    }
+
+    zmq_msg_init_size(&msg, sizeof(msgBlit) + 70);
+    onLine->x = (x + 1) % 480;
+    memcpy(zmq_msg_data(&msg), onLine, sizeof(msgBlit) + 70);
+    zmq_msg_send(&msg, requester, ZMQ_SNDMORE);
+
+    zmq_msg_init_size(&msg, sizeof(msgBlit) + 70);
+    offLine->x = x % 480;
+    memcpy(zmq_msg_data(&msg), offLine, sizeof(msgBlit) + 70);
+    zmq_msg_send(&msg, requester, ZMQ_SNDMORE);
+
+    zmq_msg_init_size(&msg, 0);
+    zmq_msg_send(&msg, requester, 0);
+    zmq_recv(requester, NULL, 0, 0);
+
+    x = (x + 1) % 480;
+  }
+
+  zmq_close(requester);
+
+  zmq_ctx_destroy(context);
+  return 0;
+}
diff --git a/fastclient/flash.c b/fastclient/flash.c
new file mode 100644
index 0000000000000000000000000000000000000000..1c4d4b9b11edae8b49969006c20e61c8c5c86dc1
--- /dev/null
+++ b/fastclient/flash.c
@@ -0,0 +1,85 @@
+// Hello World client
+#include <zmq.h>
+#include <string.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <stdlib.h>
+
+#include <vector>
+#include <math.h>
+
+#define WIDTH 480
+#define HEIGHT 70
+
+#define CMD_PIXEL 0
+#define CMD_BLIT 1
+
+struct msgSetPixel {
+  uint8_t cmd;
+  uint32_t x;
+  uint32_t y;
+  uint8_t on;
+} __attribute__ ((packed));
+
+struct msgBlit {
+  uint8_t cmd;
+  uint32_t x;
+  uint32_t y;
+  uint32_t w;
+  uint32_t h;
+  uint8_t data[0];
+} __attribute__ ((packed));
+
+int main (void) {
+  void *context = zmq_ctx_new ();
+  void *requester;
+
+  requester = zmq_socket (context, ZMQ_REQ);
+  zmq_connect(requester, "tcp://mensadisplay:5556");
+  // zmq_connect(requester, "tcp://192.168.178.147:5570");
+  // zmq_connect(requester, "tcp://localhost:5556");
+
+  msgBlit *snow = reinterpret_cast<msgBlit *>(malloc(sizeof(msgBlit) + WIDTH * HEIGHT));
+  snow->cmd = CMD_BLIT;
+  snow->x = 0;
+  snow->y = 0;
+  snow->w = WIDTH;
+  snow->h = HEIGHT;
+
+  int on = 0;
+
+  while(1) {
+    zmq_msg_t msg;
+    zmq_msg_init_size(&msg, sizeof(msgBlit) + WIDTH * HEIGHT);
+    int d = 0;
+
+    switch(on) {
+      case 0: d = 0; break;
+      case 1: d = 0; break;
+      case 2: d = 0; break;
+      case 3: d = 0; break;
+      case 4: d = 1; break;
+      case 5: d = 1; break;
+      case 6: d = 0; break;
+      case 7: d = 1; break;
+    }
+
+    for(int i = 0; i < WIDTH * HEIGHT; ++i) {
+      snow->data[i] = d;
+    }
+
+    on = (on + 1) % 8;
+
+    memcpy(zmq_msg_data(&msg), snow, sizeof(msgBlit) + WIDTH * HEIGHT);
+    zmq_msg_send(&msg, requester, ZMQ_SNDMORE);
+
+    zmq_msg_init_size(&msg, 0);
+    zmq_msg_send(&msg, requester, 0);
+    zmq_recv(requester, NULL, 0, 0);
+  }
+
+  zmq_close(requester);
+
+  zmq_ctx_destroy(context);
+  return 0;
+}
diff --git a/fastclient/snow.c b/fastclient/snow.c
new file mode 100644
index 0000000000000000000000000000000000000000..55a97fffe1396fdd79dbe94a84c324ec9b56d849
--- /dev/null
+++ b/fastclient/snow.c
@@ -0,0 +1,93 @@
+// Hello World client
+#include <zmq.h>
+#include <string.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <stdlib.h>
+
+#include <vector>
+#include <math.h>
+
+#define WIDTH 480
+#define HEIGHT 70
+
+#define CMD_PIXEL 0
+#define CMD_BLIT 1
+
+struct msgSetPixel {
+  uint8_t cmd;
+  uint32_t x;
+  uint32_t y;
+  uint8_t on;
+} __attribute__ ((packed));
+
+struct msgBlit {
+  uint8_t cmd;
+  uint32_t x;
+  uint32_t y;
+  uint32_t w;
+  uint32_t h;
+  uint8_t data[0];
+} __attribute__ ((packed));
+
+int main (void) {
+  void *context = zmq_ctx_new ();
+  void *requester;
+
+  requester = zmq_socket (context, ZMQ_REQ);
+  zmq_connect(requester, "tcp://mensadisplay:5556");
+  // zmq_connect(requester, "tcp://192.168.178.147:5570");
+  // zmq_connect(requester, "tcp://localhost:5556");
+
+  msgBlit *snow = reinterpret_cast<msgBlit *>(malloc(sizeof(msgBlit) + WIDTH * HEIGHT));
+  snow->cmd = CMD_BLIT;
+  snow->x = 0;
+  snow->y = 0;
+  snow->w = WIDTH;
+  snow->h = HEIGHT;
+
+  float f[HEIGHT / 7] = { 0 };
+  float dir[HEIGHT / 7] = { 0 };
+  float sharpness[HEIGHT / 7] = { 0 };
+
+  for(int i = 0; i < HEIGHT / 7; ++i) {
+    dir[i] = 0.2;
+    sharpness[i] = 2;
+  }
+
+  while(1) {
+    zmq_msg_t msg;
+    zmq_msg_init_size(&msg, sizeof(msgBlit) + WIDTH * HEIGHT);
+    for(int i = 0; i < WIDTH * HEIGHT; ++i) {
+      int x = i % WIDTH;
+      int y = i / WIDTH;
+
+      int thresh = 32768 + sharpness[y / 7] * sin(f[y / 7] + 1.0 * x / 60) * 32768;
+
+      snow->data[i] = (rand() % 65536) > thresh;
+    }
+
+    for(int i = 0; i < HEIGHT / 7; ++i) {
+      f[i] += dir[i];
+    }
+
+    if(!(rand() % 100)) {
+      dir[rand() % (HEIGHT / 7)] *= -1;
+    }
+    if(!(rand() % 100)) {
+      sharpness[rand() % (HEIGHT / 7)] = 1 + rand() % 3;
+    }
+
+    memcpy(zmq_msg_data(&msg), snow, sizeof(msgBlit) + WIDTH * HEIGHT);
+    zmq_msg_send(&msg, requester, ZMQ_SNDMORE);
+
+    zmq_msg_init_size(&msg, 0);
+    zmq_msg_send(&msg, requester, 0);
+    zmq_recv(requester, NULL, 0, 0);
+  }
+
+  zmq_close(requester);
+
+  zmq_ctx_destroy(context);
+  return 0;
+}