diff --git a/Dockerfile b/Dockerfile index 73d3243..3458fa8 100644 --- a/Dockerfile +++ b/Dockerfile @@ -21,8 +21,7 @@ RUN make O=imx7 ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- imx_v6_v7_defconfig # Enable uinput RUN sed -i 's/# CONFIG_INPUT_UINPUT is not set/CONFIG_INPUT_UINPUT=y/' imx7/.config -ARG parallel=8 -RUN make O=imx7 ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- -j$parallel +RUN make O=imx7 ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- -j $(nproc) # Copy the output files RUN cp imx7/arch/arm/boot/zImage /opt && \ @@ -59,10 +58,10 @@ ADD make_rootfs.sh /opt RUN ./make_rootfs.sh /opt/rootfs.ext4 # Step3: Qemu! -FROM debian:bookworm AS qemu +FROM debian:bookworm AS qemu-base RUN apt-get update && \ - apt-get install -y qemu-system-arm + apt-get install --no-install-recommends -y qemu-system-arm qemu-utils ssh netcat-openbsd RUN mkdir -p /opt/root @@ -70,18 +69,73 @@ COPY --from=linux-build /opt/zImage /opt COPY --from=linux-build /opt/imx7d-rm.dtb /opt COPY --from=rootfs /opt/rootfs.qcow2 /opt/root +ADD bin /opt/bin +ENV PATH=/opt/bin:$PATH + +# First boot, disable xochitl, sync time, and save state +RUN run_vm.sh -serial null -daemonize && \ + ssh -o StrictHostKeyChecking=no root@localhost 'systemctl stop rm-sync && systemctl mask rm-sync' && \ + ssh -o StrictHostKeyChecking=no root@localhost 'systemctl mask xochitl' && \ + ssh -o StrictHostKeyChecking=no root@localhost 'while ! timedatectl status | grep "synchronized: yes"; do sleep 1; done' && \ + save_vm.sh + +# Mount to presist rootfs VOLUME /opt/root + +# SSH access EXPOSE 22/tcp +# Qemu monitor TCP port +EXPOSE 5555/tcp +# For rm2fb EXPOSE 8888/tcp -CMD qemu-system-arm \ - -machine mcimx7d-sabre \ - -cpu cortex-a9 \ - -smp 2 \ - -m 2048 \ - -kernel /opt/zImage \ - -dtb /opt/imx7d-rm.dtb \ - -drive if=sd,file=/opt/root/rootfs.qcow2,format=qcow2,index=2 \ - -append "console=ttymxc0 rootfstype=ext4 root=/dev/mmcblk1p2 rw rootwait init=/sbin/init" \ - -nic user,hostfwd=tcp::22-:22,hostfwd=tcp::8888-:8888 \ - -nographic +CMD run_vm.sh -nographic + +FROM qemu-base AS qemu-toltec + +RUN run_vm.sh -serial null -daemonize && \ + ssh -o StrictHostKeyChecking=no root@localhost 'wget http://toltec-dev.org/bootstrap && bash bootstrap' && \ + save_vm.sh + +# Step 4: Build rm2fb-client and forwarder +FROM ghcr.io/toltec-dev/base:v3.1 as rm2fb-client + +RUN apt-get update && \ + apt-get install -y git + +RUN mkdir -p /opt && \ + git clone https://github.com/timower/rM2-stuff.git -b dev /opt/rm2-stuff +WORKDIR /opt/rm2-stuff + +RUN cmake --preset release-toltec && \ + cmake --build build/release-toltec --target rm2fb_client rm2fb-forward + +# Step 5: Build rm2fb-emu for the debian host... +FROM debian:bookworm AS rm2fb-host + +RUN apt-get update && \ + apt-get install -y git clang cmake ninja-build libsdl2-dev libevdev-dev + +RUN mkdir -p /opt && \ + git clone https://github.com/timower/rM2-stuff.git -b dev /opt/rm2-stuff +WORKDIR /opt/rm2-stuff + +RUN cmake --preset dev-host && cmake --build build/host --target rm2fb-emu + +# Step 6: Integrate +FROM qemu-toltec AS qemu-rm2fb + +RUN mkdir -p /opt/rm2fb + +COPY --from=rm2fb-client /opt/rm2-stuff/build/release-toltec/libs/rm2fb/librm2fb_client.so /opt/rm2fb +COPY --from=rm2fb-client /opt/rm2-stuff/build/release-toltec/tools/rm2fb-forward/rm2fb-forward /opt/rm2fb +COPY --from=rm2fb-host /opt/rm2-stuff/build/host/tools/rm2fb-emu/rm2fb-emu /opt/bin + +RUN run_vm.sh -serial null -daemonize && \ + scp -o StrictHostKeyChecking=no /opt/rm2fb/* root@localhost: && \ + save_vm.sh + +RUN apt-get update && \ + apt-get install -y libevdev2 libsdl2-2.0-0 + +CMD run_xochitl.sh diff --git a/Readme.md b/Readme.md index 49947ac..10e20ae 100644 --- a/Readme.md +++ b/Readme.md @@ -20,10 +20,38 @@ reMarkable login: ssh root@localhost -p 2222 ``` +Targets +------- + +### qemu-base + +Use `docker build --target qemu-base` to build a basic qemu image. + +### qemu-toltec + +The `qemu-toltec` target will install [toltec](https://toltec-dev.org/) in +the image. + +### qemu-rm2fb + +The `qemu-rm2fb` target (which is the default) will include a framebuffer +emulator from [rm2-stuff](https://github.com/timower/rM2-stuff/tree/dev). + +X11 forwarding can be used to view the framebuffer: +``` +docker run --rm \ + -v /tmp/.X11-unix:/tmp/.X11-unix \ + -v $HOME/.Xauthority:/root/.Xauthority \ + --env DISPLAY \ + -h (hostnamectl hostname) \ + -p 2222:22 \ + -it rm-docker:plain +``` + TODO ---- - * Add rm2fb from [rm2-stuff](https://github.com/timower/rM2-stuff/tree/dev) + - [ ] Add github actions References ---------- diff --git a/bin/run_vm.sh b/bin/run_vm.sh new file mode 100755 index 0000000..ae314ba --- /dev/null +++ b/bin/run_vm.sh @@ -0,0 +1,26 @@ +#!/bin/sh + +set -eu + +LOAD_STATE="" + +if qemu-img snapshot -l /opt/root/rootfs.qcow2 | grep main > /dev/null +then + LOAD_STATE="-loadvm main" +fi + +echo "Staring..." +qemu-system-arm \ + -machine mcimx7d-sabre \ + -cpu cortex-a9 \ + -smp 2 \ + -m 2048 \ + -kernel /opt/zImage \ + -dtb /opt/imx7d-rm.dtb \ + -drive if=sd,file=/opt/root/rootfs.qcow2,format=qcow2,index=2 \ + -append "console=ttymxc0 rootfstype=ext4 root=/dev/mmcblk1p2 rw rootwait init=/sbin/init" \ + -nic user,hostfwd=tcp::22-:22,hostfwd=tcp::8888-:8888 \ + -monitor tcp::5555,server=on,wait=off \ + -parallel null -display none \ + $LOAD_STATE \ + "$@" diff --git a/bin/run_xochitl.sh b/bin/run_xochitl.sh new file mode 100755 index 0000000..911a618 --- /dev/null +++ b/bin/run_xochitl.sh @@ -0,0 +1,22 @@ +#!/bin/sh + +set -eux + +# Start the VM +run_vm.sh -serial null -daemonize + +# Make sure it's up +ssh -o StrictHostKeyChecking=no root@localhost 'true' + +# Launch the TCP forwarding server +ssh -o StrictHostKeyChecking=no root@localhost './rm2fb-forward' & + +# Make sure the server is running by waiting a bit :( +sleep 5 + +# Connect using the FB emulator +rm2fb-emu 127.0.0.1 8888 & + +# Start xochitl +ssh -o StrictHostKeyChecking=no root@localhost 'LD_PRELOAD=/home/root/librm2fb_client.so /usr/bin/xochitl' + diff --git a/bin/save_vm.sh b/bin/save_vm.sh new file mode 100755 index 0000000..5eded37 --- /dev/null +++ b/bin/save_vm.sh @@ -0,0 +1,6 @@ +#!/bin/sh + +set -e + +echo 'savevm main' | nc -N 127.0.0.1 5555 +echo 'quit' | nc -N 127.0.0.1 5555