<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://sudoroom.org/mediawiki/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Z4ppho</id>
	<title>Sudo Room - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://sudoroom.org/mediawiki/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Z4ppho"/>
	<link rel="alternate" type="text/html" href="https://sudoroom.org/wiki/Special:Contributions/Z4ppho"/>
	<updated>2026-08-29T23:37:21Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.37.2</generator>
	<entry>
		<id>https://sudoroom.org/mediawiki/index.php?title=User:Z4ppho&amp;diff=13325</id>
		<title>User:Z4ppho</title>
		<link rel="alternate" type="text/html" href="https://sudoroom.org/mediawiki/index.php?title=User:Z4ppho&amp;diff=13325"/>
		<updated>2026-08-29T22:38:17Z</updated>

		<summary type="html">&lt;p&gt;Z4ppho: /* Projects at Sudo */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''Raelyn''' (z4ppho) lives in Richmond. In her free time she likes to tinker in her homelab and experiment with AI technologies.&lt;br /&gt;
&lt;br /&gt;
== Projects at Sudo ==&lt;br /&gt;
* [[Oculus Rift DK2 on Linux]]&lt;/div&gt;</summary>
		<author><name>Z4ppho</name></author>
	</entry>
	<entry>
		<id>https://sudoroom.org/mediawiki/index.php?title=Oculus_Rift_DK2_on_Linux&amp;diff=13324</id>
		<title>Oculus Rift DK2 on Linux</title>
		<link rel="alternate" type="text/html" href="https://sudoroom.org/mediawiki/index.php?title=Oculus_Rift_DK2_on_Linux&amp;diff=13324"/>
		<updated>2026-08-29T22:33:04Z</updated>

		<summary type="html">&lt;p&gt;Z4ppho: page made and details added&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;''Project page by [[User:Z4ppho|Raelyn]] — started August 2026. Status: working (orientation tracking); positional tracking open.''&lt;br /&gt;
&lt;br /&gt;
5/13/26 discord user thedesperad0 asked in #free-stuff if anyone wanted a oculus dev kit. user z4ppho took the offer. Nothing official has supported it in years, but every piece needed to run it on a modern Linux desktop exists in the open — it just isn't written down in one place. This page is that place: what the DK2 is, why it looks dead on a modern desktop, and the exact stack that brings it back at its native 75 Hz.&lt;br /&gt;
&lt;br /&gt;
This was done on Fedora 44 / GNOME 50 (Wayland) with an NVIDIA GTX 1060. The same approach should work on any compositor that supports DRM leasing (GNOME 46+, KDE Plasma 6, wlroots-based compositors).&lt;br /&gt;
&lt;br /&gt;
== What's in a DK2 ==&lt;br /&gt;
Per the [https://www.ifixit.com/Teardown/Oculus+Rift+Development+Kit+2+Teardown/27613 iFixit teardown]:&lt;br /&gt;
* '''Display:''' literally the front panel of a Samsung Galaxy Note 3 — a 5.7&amp;quot; 1080×1920 Super AMOLED, driven through a Toshiba TC358779XBG HDMI→MIPI-DSI bridge and an STM32L100 microcontroller. The MCU's firmware overclocks the panel from 60 to 75 Hz and pulses it for low persistence. (The touchscreen controller is still in there, unused.)&lt;br /&gt;
* '''Tracking:''' an InvenSense MPU-6500 IMU (gyro + accelerometer) over USB for orientation, plus an array of IR LEDs read by an external USB camera (Etron eSP570) for position.&lt;br /&gt;
* '''USB:''' a Cypress CY7C65632 hub — the headset shows up as &amp;lt;code&amp;gt;2833:2021&amp;lt;/code&amp;gt; (hub) and &amp;lt;code&amp;gt;2833:0021&amp;lt;/code&amp;gt; (headset); the camera is &amp;lt;code&amp;gt;2833:0201&amp;lt;/code&amp;gt;.&lt;br /&gt;
* '''Connections:''' one HDMI, one USB for the headset, one USB for the camera. It needs a real HDMI port (or a DisplayPort→HDMI adapter that carries a proper EDID).&lt;br /&gt;
&lt;br /&gt;
Because the display path and the tracking path are separate (HDMI vs USB), each can be debugged on its own.&lt;br /&gt;
&lt;br /&gt;
== Why the screen stays black ==&lt;br /&gt;
Plug it in and nothing happens: the desktop never lights the panel, and it doesn't appear in display settings. This is deliberate. The Linux kernel carries a quirk list (&amp;lt;code&amp;gt;drivers/gpu/drm/drm_edid.c&amp;lt;/code&amp;gt;) that marks the Oculus DK1, DK2 and CV1 EDIDs as '''non-desktop''' — a hint that the display is a head-mounted device, so the compositor should ''not'' put a desktop on it. Instead, a VR runtime is expected to '''lease''' the connector from the compositor and drive it directly.&lt;br /&gt;
&lt;br /&gt;
So the job is: get a VR runtime to ask the compositor for a lease.&lt;br /&gt;
&lt;br /&gt;
== The stack ==&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
! Layer !! What we used !! Notes&lt;br /&gt;
|-&lt;br /&gt;
| VR runtime (OpenXR) || [https://monado.freedesktop.org/ Monado] || Packaged in Fedora (&amp;lt;code&amp;gt;monado&amp;lt;/code&amp;gt;). Has a native DK2 path through OpenHMD.&lt;br /&gt;
|-&lt;br /&gt;
| Headset driver || [http://www.openhmd.net/ OpenHMD] '''0.3.0''' || '''Not''' the current git snapshot — see gotchas.&lt;br /&gt;
|-&lt;br /&gt;
| Display handoff || &amp;lt;code&amp;gt;wp_drm_lease_v1&amp;lt;/code&amp;gt; (Wayland DRM lease) || Mutter 50 implements it; Monado's &amp;quot;Wayland direct&amp;quot; mode requests the lease.&lt;br /&gt;
|-&lt;br /&gt;
| GPU || NVIDIA GTX 1060, Vulkan || Monado uses &amp;lt;code&amp;gt;VK_EXT_acquire_drm_display&amp;lt;/code&amp;gt; on the leased connector.&lt;br /&gt;
|-&lt;br /&gt;
| Application || Python, [https://github.com/cmbruns/pyopenxr pyopenxr] + OpenGL || Anything OpenXR works; ours is a &amp;quot;virtual monitors around the room&amp;quot; app.&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== Step by step ==&lt;br /&gt;
&lt;br /&gt;
=== 1. Let your user touch the device ===&lt;br /&gt;
A udev rule so the HID and USB nodes are readable by the &amp;lt;code&amp;gt;video&amp;lt;/code&amp;gt; group:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;text&amp;quot;&amp;gt;&lt;br /&gt;
# /etc/udev/rules.d/70-oculus-dk2.rules&lt;br /&gt;
SUBSYSTEM==&amp;quot;hidraw&amp;quot;, ATTRS{idVendor}==&amp;quot;2833&amp;quot;, MODE=&amp;quot;0660&amp;quot;, GROUP=&amp;quot;video&amp;quot;&lt;br /&gt;
SUBSYSTEM==&amp;quot;usb&amp;quot;,    ATTRS{idVendor}==&amp;quot;2833&amp;quot;, MODE=&amp;quot;0660&amp;quot;, GROUP=&amp;quot;video&amp;quot;&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
Then &amp;lt;code&amp;gt;sudo udevadm control --reload &amp;amp;&amp;amp; sudo udevadm trigger&amp;lt;/code&amp;gt;, and make sure your user is in &amp;lt;code&amp;gt;video&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
'''Gotcha:''' group membership only applies to processes started ''after'' you were added. A terminal, tmux server or user systemd instance that was already running will still lack the group and Monado will report a &amp;quot;Simulated HMD&amp;quot; instead of the real one. Log out and back in, or wrap the launch in &amp;lt;code&amp;gt;sg video -c &amp;quot;...&amp;quot;&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== 2. Install Monado ===&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo dnf install monado openhmd hidapi&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
(Fedora's &amp;lt;code&amp;gt;openhmd&amp;lt;/code&amp;gt; package gets replaced in step 3, but it pulls in the right dependencies.)&lt;br /&gt;
&lt;br /&gt;
=== 3. Build OpenHMD 0.3.0 by hand ===&lt;br /&gt;
The OpenHMD in Fedora (and current git master) uses a new Kalman-filter fusion for positional tracking. With a DK2 it aborts within a minute — &amp;lt;code&amp;gt;Cholesky decomposition failed on P_root&amp;lt;/code&amp;gt; — '''with or without the camera plugged in'''. The last release, 0.3.0, uses the older orientation-only fusion and is rock solid.&lt;br /&gt;
&lt;br /&gt;
Monado links against two symbols newer than 0.3.0 (&amp;lt;code&amp;gt;ohmd_device_set_haptics_on/off&amp;lt;/code&amp;gt;), so add a tiny stub file and compile the library directly — no cmake needed:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
git clone --branch 0.3.0 https://github.com/OpenHMD/OpenHMD.git &amp;amp;&amp;amp; cd OpenHMD&lt;br /&gt;
cat &amp;gt; src/stubs_compat.c &amp;lt;&amp;lt;'C'&lt;br /&gt;
#include &amp;quot;openhmdi.h&amp;quot;&lt;br /&gt;
int ohmd_device_set_haptics_on(ohmd_device* d, float f, float a, float t)  { (void)d;(void)f;(void)a;(void)t; return OHMD_S_UNSUPPORTED; }&lt;br /&gt;
int ohmd_device_set_haptics_off(ohmd_device* d) { (void)d; return OHMD_S_UNSUPPORTED; }&lt;br /&gt;
C&lt;br /&gt;
mkdir -p ~/vr/lib&lt;br /&gt;
gcc -O2 -fPIC -shared -Wl,-soname,libopenhmd.so.0 \&lt;br /&gt;
  -DDRIVER_OCULUS_RIFT -DDRIVER_DUMMY -DDRIVER_EXTERNAL \&lt;br /&gt;
  -Iinclude -Isrc -I/usr/include/hidapi \&lt;br /&gt;
  src/openhmd.c src/fusion.c src/omath.c src/shaders.c src/platform-posix.c src/stubs_compat.c \&lt;br /&gt;
  src/drv_dummy/dummy.c src/drv_external/external.c \&lt;br /&gt;
  src/drv_oculus_rift/rift.c src/drv_oculus_rift/packet.c \&lt;br /&gt;
  -lhidapi-libusb -lm -lpthread -o ~/vr/lib/libopenhmd.so.0&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
Point Monado at it with &amp;lt;code&amp;gt;LD_LIBRARY_PATH=$HOME/vr/lib&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== 4. Start Monado in Wayland direct mode ===&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
XRT_COMPOSITOR_FORCE_WAYLAND_DIRECT=1 XRT_NO_STDIN=1 XRT_LOG=info \&lt;br /&gt;
  sg video -c &amp;quot;LD_LIBRARY_PATH=$HOME/vr/lib monado-service&amp;quot;&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
Watch the log for two lines. The lease:&lt;br /&gt;
&amp;lt;pre&amp;gt;connector HDMI-A-1 (OVR Rift DK2) id: 96&amp;lt;/pre&amp;gt;&lt;br /&gt;
and the tracker:&lt;br /&gt;
&amp;lt;pre&amp;gt;head: Rift (DK2) (OpenHMD)&amp;lt;/pre&amp;gt;&lt;br /&gt;
If it says &amp;lt;code&amp;gt;Simulated HMD&amp;lt;/code&amp;gt;, go back to the group gotcha in step 1. If no connector is offered, your compositor isn't handing out leases (check its version).&lt;br /&gt;
&lt;br /&gt;
'''Gotcha:''' &amp;lt;code&amp;gt;sg&amp;lt;/code&amp;gt; is setuid and strips &amp;lt;code&amp;gt;LD_LIBRARY_PATH&amp;lt;/code&amp;gt; from its own environment — put the variable ''inside'' the quoted command, as above.&lt;br /&gt;
&lt;br /&gt;
=== 5. Run something ===&lt;br /&gt;
Any OpenXR app will now render to the headset at 75 Hz. The smallest test is pyopenxr's &amp;lt;code&amp;gt;hello_xr&amp;lt;/code&amp;gt;-style sample: a blank scene that spins as you turn your head. Ours draws textured quads at (yaw, pitch, distance) around the wearer and refreshes them from log files, a webcam, a video stream and a real Firefox window — a poor person's command center. A single Python process with an EGL offscreen context holds 75 fps with ~3 ms of frame work on a GTX 1060.&lt;br /&gt;
&lt;br /&gt;
== Results ==&lt;br /&gt;
* First light and orientation tracking: about one hour from &amp;quot;plugged in&amp;quot; to &amp;quot;I CAN LOOK AROUND.&amp;quot;&lt;br /&gt;
* Steady 75 fps (the panel's native rate) at 1920×2160 per eye (Monado's maximum, 2× the physical resolution), downsampled for cleaner text.&lt;br /&gt;
* The panel is still a 2014 pentile 1080p: roughly 10 pixels per degree. Text has to be about 1° tall to read. Plan your UI around big, close, few-lined panels — no amount of supersampling adds pixels.&lt;br /&gt;
&lt;br /&gt;
== Open problems ==&lt;br /&gt;
* '''Positional tracking.''' The IR camera opens fine (&amp;lt;code&amp;gt;Opened 1 Rift Sensor cameras&amp;lt;/code&amp;gt;), but the only OpenHMD fusion that uses it is the one that aborts. Fixing the UKF, or porting position-only from the newer code onto the 0.3.0 base, is the next real project.&lt;br /&gt;
* '''Panel upgrade?''' The Note 3 panel can't be swapped on the original board — the STM32 firmware initialises that exact Samsung driver IC. A 5.5&amp;quot; 2560×1440 module with its own HDMI driver board (~$40–90) would fit and keeps tracking intact (separate USB path), but trades 75 Hz low-persistence OLED for 60 Hz full-persistence LCD and needs its own distortion profile. A trade, not an upgrade; not attempted.&lt;br /&gt;
* '''Persistence.''' The units above were started with &amp;lt;code&amp;gt;systemd-run&amp;lt;/code&amp;gt;; write proper unit files so they survive a reboot.&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
* [https://monado.freedesktop.org/ Monado] · [https://github.com/OpenHMD/OpenHMD OpenHMD] · [https://github.com/cmbruns/pyopenxr pyopenxr]&lt;br /&gt;
* Kernel non-desktop quirk: &amp;lt;code&amp;gt;drivers/gpu/drm/drm_edid.c&amp;lt;/code&amp;gt;, search for &amp;lt;code&amp;gt;EDID_QUIRK_NON_DESKTOP&amp;lt;/code&amp;gt;&lt;br /&gt;
* [[User:Z4ppho]]&lt;br /&gt;
&lt;br /&gt;
This project is ongoing and will continue to be updated. &lt;br /&gt;
&lt;br /&gt;
''Written by Raelyn with Riley. from the working notes of the project.  (August 28–29, 2026).''&lt;br /&gt;
&lt;br /&gt;
[[Category:Projects]]&lt;/div&gt;</summary>
		<author><name>Z4ppho</name></author>
	</entry>
	<entry>
		<id>https://sudoroom.org/mediawiki/index.php?title=Sudo_Room:Copyrights&amp;diff=13323</id>
		<title>Sudo Room:Copyrights</title>
		<link rel="alternate" type="text/html" href="https://sudoroom.org/mediawiki/index.php?title=Sudo_Room:Copyrights&amp;diff=13323"/>
		<updated>2026-08-29T22:12:27Z</updated>

		<summary type="html">&lt;p&gt;Z4ppho: embedded link&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;See [https://sudoroom.org/wiki/Sudo_Room:Copyrights this page] for details on the SudoRoom copyright policy.&lt;/div&gt;</summary>
		<author><name>Z4ppho</name></author>
	</entry>
	<entry>
		<id>https://sudoroom.org/mediawiki/index.php?title=Sudo_Room:Copyrights&amp;diff=13322</id>
		<title>Sudo Room:Copyrights</title>
		<link rel="alternate" type="text/html" href="https://sudoroom.org/mediawiki/index.php?title=Sudo_Room:Copyrights&amp;diff=13322"/>
		<updated>2026-08-29T22:03:38Z</updated>

		<summary type="html">&lt;p&gt;Z4ppho: made the page so at least the link in the editor notes go somewhere&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;See this page for details on the SudoRoom copyright policy.&lt;/div&gt;</summary>
		<author><name>Z4ppho</name></author>
	</entry>
	<entry>
		<id>https://sudoroom.org/mediawiki/index.php?title=User:Z4ppho&amp;diff=13321</id>
		<title>User:Z4ppho</title>
		<link rel="alternate" type="text/html" href="https://sudoroom.org/mediawiki/index.php?title=User:Z4ppho&amp;diff=13321"/>
		<updated>2026-08-29T22:00:33Z</updated>

		<summary type="html">&lt;p&gt;Z4ppho: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''Raelyn''' (z4ppho) lives in Richmond. In her free time she likes to tinker in her homelab and experiment with AI technologies.&lt;br /&gt;
&lt;br /&gt;
== Projects at Sudo ==&lt;br /&gt;
''Coming soon.''&lt;/div&gt;</summary>
		<author><name>Z4ppho</name></author>
	</entry>
	<entry>
		<id>https://sudoroom.org/mediawiki/index.php?title=User:Z4ppho&amp;diff=13320</id>
		<title>User:Z4ppho</title>
		<link rel="alternate" type="text/html" href="https://sudoroom.org/mediawiki/index.php?title=User:Z4ppho&amp;diff=13320"/>
		<updated>2026-08-29T21:59:02Z</updated>

		<summary type="html">&lt;p&gt;Z4ppho: Created page with &amp;quot;'''Raelyn''' (z4ppho) lives in Richmond. In her free time she likes to tinker in her homelab and experiment with AI technology.  == Projects at Sudo == ''Coming soon.''&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''Raelyn''' (z4ppho) lives in Richmond. In her free time she likes to tinker in her homelab and experiment with AI technology.&lt;br /&gt;
&lt;br /&gt;
== Projects at Sudo ==&lt;br /&gt;
''Coming soon.''&lt;/div&gt;</summary>
		<author><name>Z4ppho</name></author>
	</entry>
</feed>