--- /dev/null
+#include <stdio.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+#include <opencbm.h>
+
+const unsigned int BUFSIZE=16;
+
+int main(int argc, char **argv)
+{
+ unsigned char devnr;
+ CBM_FILE cbm;
+ char buffer[BUFSIZE];
+ ssize_t numbytes;
+ ssize_t totalbytes=0;
+
+ if(argc != 2)
+ return 1;
+
+ devnr=atoi(argv[1]);
+
+ setbuf(stdout, NULL);
+
+ cbm_driver_open(&cbm,0);
+ cbm_lock(cbm);
+ cbm_listen(cbm, devnr, 0);
+ while((numbytes=read(0, buffer, BUFSIZE)) > 0)
+ {
+ totalbytes+=numbytes;
+ cbm_raw_write(cbm, buffer, numbytes);
+ printf("Wrote %6ld bytes\r", totalbytes);
+ }
+
+ printf("\r\n");
+ cbm_unlisten(cbm);
+ cbm_unlock(cbm);
+ cbm_driver_close(cbm);
+
+
+}
--- /dev/null
+#include <iostream>
+#include <string>
+#include <vector>
+
+#include <Magick++.h>
+
+const unsigned int MAX_WIDTH=480;
+
+int usage(const char* name)
+{
+ std::cerr << "Usage: " << name << " IMAGE" << std::endl << "MPS801 datastream gets written to stdout" << std::endl;
+ return 1;
+}
+
+int main(int argc, char **argv)
+{
+ if(argc != 2)
+ return usage(argv[0]);
+
+ auto img = Magick::Image(argv[1]);
+
+ if(img.columns() > MAX_WIDTH)
+ {
+ std::cerr << "Cropping width to " << MAX_WIDTH << "px" << std::endl;
+ img.crop(Magick::Geometry(MAX_WIDTH, img.rows(), 0, 0));
+ }
+
+ if(img.totalColors() > 2)
+ {
+ std::cerr << "Converting to bi-level image." << std::endl;
+ img.type(Magick::BilevelType);
+ }
+
+ std::vector<std::vector<uint8_t>> mps;
+ mps.insert(mps.begin(), { 0x08 });
+
+ img.modifyImage();
+ auto columns = img.columns();
+ auto rows = img.columns();
+
+ auto pixels = img.getPixels(0, 0, columns, rows);
+
+ for(size_t row=0; row < rows; row+=7)
+ {
+ std::vector<uint8_t> line(columns, 0x80);
+ for(auto subrow=0; subrow < 7; subrow++)
+ {
+ if(row+subrow >= rows)
+ break;
+ for(size_t column=0; column < columns; column++)
+ {
+ auto pixel = pixels + (row+subrow)*columns + column;
+ if((pixel->red)==0)
+ line[column] |= 1<<subrow;
+ }
+ }
+ mps.push_back(line);
+ mps.push_back({0x15, 0x0D, 0x08});
+ }
+
+ for(auto line : mps)
+ for(auto byte: line)
+ std::cout << byte;
+}