{"record":{"id":"fec2675011859537","repo":"embassy-rs/embassy","slug":"pin-is-outside-the-pio-s-gpiobase-window","errorCode":null,"errorMessage":"pin {} is outside the PIO's GPIOBASE window {}..{}; use Config::set_input_sync_bypass or call this after StateMachine::set_config","messagePattern":"pin (.+?) is outside the PIO's GPIOBASE window (.+?)\\.\\.(.+?); use Config::set_input_sync_bypass or call this after StateMachine::set_config","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"embassy-rp/src/pio/mod.rs","lineNumber":320,"sourceCode":"    }\n\n    /// Set the pin's input sync bypass.\n    ///\n    /// Prefer [`Config::set_input_sync_bypass`]: `input_sync_bypass` is indexed\n    /// relative to the PIO's `GPIOBASE`, which is only established by\n    /// [`StateMachine::set_config`]. If calling this directly (e.g. to clear a\n    /// bypass), do so after configuring the state machine.\n    ///\n    /// Panics if the pin is outside the PIO's current `GPIOBASE` window.\n    pub fn set_input_sync_bypass(&mut self, bypass: bool) {\n        #[cfg(feature = \"rp2040\")]\n        let offset = 0u8;\n        #[cfg(feature = \"_rp235x\")]\n        let offset = if PIO::PIO.gpiobase().read().gpiobase() { 16 } else { 0 };\n\n        let rel = match self.pin().checked_sub(offset) {\n            Some(rel) if rel < 32 => rel,\n            _ => panic!(\n                \"pin {} is outside the PIO's GPIOBASE window {}..{}; use Config::set_input_sync_bypass or call this after StateMachine::set_config\",\n                self.pin(),\n                offset,\n                offset + 32\n            ),\n        };\n        let mask = 1u32 << rel;\n        if bypass {\n            PIO::PIO.input_sync_bypass().write_set(|w| *w = mask);\n        } else {\n            PIO::PIO.input_sync_bypass().write_clear(|w| *w = mask);\n        }\n    }\n\n    /// Set the pin's input sync bypass.\n    pub fn set_input_inversion(&mut self, invert: bool) {\n        self.pin.gpio().ctrl().modify(|w| {\n            w.set_inover(if invert {","sourceCodeStart":302,"sourceCodeEnd":338,"githubUrl":"https://github.com/embassy-rs/embassy/blob/463a07b963419a1bfe61d5d597c44acb810afb8b/embassy-rp/src/pio/mod.rs#L302-L338","documentation":"`set_input_sync_bypass` on a PIO pin group panics when the requested pin cannot be expressed in the PIO block's current GPIOBASE-relative window. On RP235x, PIO2 can be routed to pins 16-47, so pins are addressed relative to the block's GPIOBASE (0 or 16); a pin outside the 32-pin window starting at that base cannot be referenced.","triggerScenarios":"Calling `set_input_sync_bypass` with a pin number below the block's GPIOBASE or at/above base+32 — typically configuring bypass for a pin >=16 (or <16) on RP235x while the PIO's gpiobase routing places it outside the window, or calling before `StateMachine::set_config` has latched the routing.","commonSituations":"RP235x projects moving a PIO block to the high pin bank (16-47) while bypass/pin code still references low pin numbers; code copied from RP2040 (where offset is always 0) that uses pins >=16.","solutions":["Move the pin into the PIO's current GPIOBASE window (offset..offset+32) as the panic message indicates","Call set_input_sync_bypass after StateMachine::set_config so the GPIOBASE routing is latched","Use the Config-level pin assignment (e.g. set the pin in the PIO config) instead of raw bypass manipulation","On RP235x, choose pins that match the block's routing (low bank for base 0, pins 16-47 for base 16)"],"exampleFix":"// before\nsm.set_input_sync_bypass(pin_10); // pin outside current window\n// after\nlet sm = pio.sm0.set_config(&config); // latch routing first\nsm.set_input_sync_bypass(pin_10);","handlingStrategy":"validation","validationCode":"fn pin_in_window(pin: u8, offset: u8) -> bool { pin.checked_sub(offset).map_or(false, |r| r < 32) }\n// check before calling: pin_in_window(pin, gpio_base_offset)","typeGuard":"fn in_pio_window(pin: u8, offset: u8) -> Option<u8> {\n    pin.checked_sub(offset).filter(|&r| r < 32)\n}","tryCatchPattern":null,"preventionTips":["On RP235x, keep track of each PIO block's GPIOBASE routing before touching pin registers","Call set_config before pin-window operations","Wire peripherals to pins that match the block's bank (0-31 vs 16-47)"],"tags":["pio","embedded","gpio","rust"],"backgroundTag":"value-out-of-range","analyzedSha":"463a07b963419a1bfe61d5d597c44acb810afb8b","analyzedAt":"2026-09-10T13:38:26.660Z","contentChangedAt":"2026-09-10T13:38:26.660Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}