From 14b0247716fe19a9bb2b028e86553a83dc76e8e5 Mon Sep 17 00:00:00 2001 From: mwojcik Date: Wed, 9 Feb 2022 17:23:33 +0800 Subject: [PATCH] pca954x: fix to work on cold boot --- libboard_zynq/src/i2c/mod.rs | 30 ++++++++++++++---------------- libboard_zynq/src/i2c/regs.rs | 2 +- 2 files changed, 15 insertions(+), 17 deletions(-) diff --git a/libboard_zynq/src/i2c/mod.rs b/libboard_zynq/src/i2c/mod.rs index 9ac8a33..f68221d 100644 --- a/libboard_zynq/src/i2c/mod.rs +++ b/libboard_zynq/src/i2c/mod.rs @@ -144,27 +144,26 @@ impl I2c { } #[cfg(feature = "target_kasli_soc")] - fn pca_autodetect(&mut self) -> Result { + pub fn pca_autodetect(&mut self) -> Result { // start with resetting the PCA954X - self.i2cswr_oe(false); - self.i2cswr_o(false); - self.delay_us(10); // reset time is just 500ns - self.i2cswr_oe(true); - self.i2cswr_o(true); - self.delay_us(10); - let pca954x_addr = 0x71; + /*self.i2cswr_oe(false); + self.unit_delay(); + self.i2cswr_oe(true);*/ + + let pca954x_read_addr = (0x71 << 1) | 0x01; self.start()?; // read the config register - if !self.write(pca954x_addr)? { + if !self.write(pca954x_read_addr)? { return Err("PCA954X failed to ack read address"); } - let config = self.read(true)?; + let config = self.read(false)?; + let pca = match config { 0x00 => PCA954X::PCA9548, 0x08 => PCA954X::PCA9547, - _ => { return Err("Unknown PCA954X type."); } + _ => { return Err("Unknown response for PCA954X autodetect")}, }; self.stop()?; Ok(pca) @@ -196,14 +195,13 @@ impl I2c { return Err("SCL is stuck low"); } // postcondition: SCL and SDA high + #[cfg(feature = "target_kasli_soc")] { + self.unit_delay(); self.pca_type = self.pca_autodetect()?; } - #[cfg(not(feature = "target_kasli_soc"))] - { - self.pca_type = PCA954X::PCA9548; - } + Ok(()) } @@ -287,7 +285,7 @@ impl I2c { if self.sda_i() { data |= 1 << bit } self.scl_oe(true); } - // Send ack/nack + // Send ack/nack (true = nack, false = ack) self.sda_oe(ack); self.unit_delay(); self.scl_oe(false); diff --git a/libboard_zynq/src/i2c/regs.rs b/libboard_zynq/src/i2c/regs.rs index 01d26ae..7d566fd 100644 --- a/libboard_zynq/src/i2c/regs.rs +++ b/libboard_zynq/src/i2c/regs.rs @@ -76,7 +76,7 @@ register_bit!(gpio_output_mask_lower, i2cswr_o, 1); #[cfg(feature = "target_kasli_soc")] register_bits!(gpio_output_mask_lower, - mask, u16, 16, 31); + mask, u16, 16, 31); register!(gpio_input, /// DATA_1_RO: