Skip to content

Latest commit

 

History

History
213 lines (161 loc) · 6.96 KB

File metadata and controls

213 lines (161 loc) · 6.96 KB

LodgeNet Input Interface

Reads Nintendo LodgeNet hotel gaming controllers via proprietary serial protocols over an RJ11 connector. Supports N64, GameCube, and SNES controller variants with automatic detection and hot-swap between types.

Protocol

Two protocol families, auto-detected and swapped dynamically:

MCU Protocol (N64 / GameCube)

  • Bus: 3-wire serial (Clock, Data, VCC) over RJ11
  • Method: PIO state machine (lodgenet_mcu_program)
  • Polling: ~60Hz (MCU_POLL_INTERVAL_US = 16000us)
  • Data: Hello pulse sequence, then 80 bits clocked MSB-first (10 bytes)
  • Detection: Byte 1 bit 7 = MCU present, bit 6 = GC (set) vs N64 (clear)
  • Stability: Requires 15 consecutive good reads before outputting (prevents connection flash)

SR Protocol (SNES)

  • Bus: Dual-clock shift register (CLK1 + CLK2 + Data) over RJ11
  • Method: PIO state machine (lodgenet_sr_program)
  • Polling: ~131Hz (SR_POLL_INTERVAL_US = 7620us)
  • Data: 16 data bits + 1 presence bit
  • Presence: Data line LOW after shift = controller present

Auto-Detection

The driver cycles between protocols when communication fails:

  • MCU fails 5 times consecutively -> switch to SR protocol
  • SR fails 5 times consecutively -> switch to MCU protocol
  • PIO program is unloaded and reloaded on each switch (single SM shared)

Location: src/native/host/lodgenet/

Supported Controllers

Device Protocol Detection
LodgeNet N64 controller MCU Byte 1 bit 6 clear
LodgeNet GameCube controller MCU Byte 1 bit 6 set
LodgeNet SNES controller SR Presence bit in SR read

Hot-swap between all three types without reboot.

LodgeNet Connector

The LodgeNet system uses a 6-pin RJ11-style connector. Connector diagram via Nielk1:

 +-+-+-+-+-+-+-+       GAME        TV                MTI
 | | | | | | | |   1   DATA(in)    CLK(out)          IR(in)
 | 1 2 3 4 5 6 |   2   CLK(out)    MTI(in)           GND
 |             |   3   12V         N/C               DATA(in)
 |             |   4   CLK2(out)   DATA(out)         N/C
 +---+---+---+-+   5   GND         GND               MTI(out)
     +---+         6   IR          IR(out)           CLK(in)

Only 4 lines from the GAME port are needed:

RJ11 Pin Signal Description
1 DATA Controller data output (active-low, pull-up)
2 CLK Host clock output (idle HIGH)
3 12V Power input (use 5V from Pico VBUS instead)
4 CLK2 Second clock (SNES SR protocol only)
5 GND Ground

GPIO Pinout

Default pins (overridable per-app):

GPIO Function Default
LODGENET_PIN_DATA Data input (pull-up) 7
LODGENET_PIN_CLOCK CLK1 output (idle HIGH) 5
LODGENET_PIN_CLOCK2 CLK2 output (SR only) 5
LODGENET_PIN_VCC VCC output (powers controller) 4

Custom pin initialization via lodgenet_host_init_pins().

Button Mapping -- N64 LodgeNet

LodgeNet N64 JP_BUTTON_* Notes
A B1
B B3
C-Down B2
C-Left B4
C-Up L3
C-Right R3
Z R1 Shared MCU mapping
L L2 Shared MCU mapping
R R2 Shared MCU mapping
Start S2
D-pad DU/DD/DL/DR Decoded from encoded SOCD d-pad
Reset (All 4 encoded) A4 Misc 5
Menu (U+D encoded) A1 Home button
Star (L+R encoded) R4
Select (U+D+R encoded) S1 Back button
Order (U+L+R encoded) A2 Capture button
Hash (U+D+L encoded) L4

Encoded D-pad and Virtual Buttons

The MCU protocol encodes the d-pad and LodgeNet system buttons using SOCD (Simultaneous Opposing Cardinal Directions) combinations in the low nibble of byte 0. Physical d-pad directions that are impossible on a real d-pad encode virtual buttons:

Encoded Value Meaning
0x0F Reset
0x0C Menu (U+D)
0x03 *
0x0D Select (U+D+R)
0x0B Order
0x0E #

The driver tracks last_dpad to separate real d-pad state from encoded virtual button presses.

Button Mapping -- GameCube LodgeNet

LodgeNet GC JP_BUTTON_* Notes
A B2
B B1
X B4
Y B3
Z R1 Shared MCU mapping
L L2 Shared MCU mapping
R R2 Shared MCU mapping
Start S2
D-pad DU/DD/DL/DR Decoded from encoded d-pad
Main Stick ANALOG_LX/LY Y inverted: 255 - raw
C-Stick ANALOG_RX/RY Y inverted: 255 - raw
L Trigger ANALOG_L2 0-255 analog
R Trigger ANALOG_R2 0-255 analog
Reset (All 4 encoded) A4 Misc 5
Menu (U+D encoded) A1 Home button
Star (L+R encoded) R4
Select (U+D+R encoded) S1 Back button
Order (U+L+R encoded) A2 Capture button
Hash (U+D+L encoded) L4

Layout reported as LAYOUT_GAMECUBE.

Button Mapping -- SNES LodgeNet

LodgeNet SNES JP_BUTTON_* Notes
B B1
A B2
Y B3
X B4
L L1
R R1
Select S1
Start S2
D-pad Up DU Filtered by SOCD detection
D-pad Down DD Filtered by SOCD detection
D-pad Left DL Filtered by SOCD detection
D-pad Right DR Filtered by SOCD detection
Menu A1 Home button
Order A2 Capture button
Minus (U+D SOCD) A3
Plus (L+R SOCD) A4

Layout reported as LAYOUT_NINTENDO_4FACE. SOCD filtering prevents simultaneous opposing directions from being output as d-pad; instead they produce the Minus and Plus virtual buttons.

Analog Axes

N64 LodgeNet

N64 stick is read as signed 8-bit and scaled from +/-80 to full range (same scaling as N64 host):

scaled = (raw * 127) / 80
output = scaled + 128

Y-axis inverted: stick_ly = 255 - (scaled_y + 128).

No right stick or triggers -- ANALOG_RX/RY at center (128), ANALOG_L2/R2 at 0.

GameCube LodgeNet

Full analog: main stick, C-stick (both Y-inverted), L/R triggers (0-255).

SNES LodgeNet

Purely digital -- all analog axes at center (128).

Connection Detection

  • MCU: Valid read requires byte 1 bit 7 set (MCU present) and no forced-fail flag
  • SR: Presence bit after the 16 data bits (LOW = present)
  • Disconnect after 5 consecutive failed reads, then protocol switch
  • On connect/disconnect, state is logged and cleared input submitted

Feedback

No rumble or LED feedback -- LodgeNet controllers are passive devices.

Configuration

  • Device address: 0xF0 (fixed, single port)
  • Transport type: INPUT_TRANSPORT_NATIVE
  • Input source: INPUT_SOURCE_NATIVE_LODGENET
  • PIO: PIO0, single SM shared between MCU and SR programs (swapped on protocol change)

Apps Using This Input