Signal polarity: All differential buses are same polarity entering each board, but BCLK signal goes through inverter before entering microphone SCK The shutdown signal exiting Teensy board (ribbon cable pin 20) is distributed with the same polarity to all intermediate and microphone boards, where received low = 3.3 V regulator off This signal exits an inverter, so the corresponding Teensy pin (teensy pin 14) is driven high to power off the external system The reset signal exiting Teensy board (ribbon cable pin 1) is inverted at each intermediate board, then inverted again at each microphone board, where received low = reset counters This signal exits an inverter, so the corresponding Teensy pin (teensy pin 32) is driven high to reset the counters (when external 3.3V power is on, because the intermediate inverters use 3.3V for their signaling) Teensy pin HIGH Main PCB out LOW Int. PCB out HIGH Mic. IC pin LOW = reset counters All microphones set to left channel (output when WCLK low) I2S timing SCK WS Out 0 1 rise 1 R30 read 1 1 fall fall R31 set 0 0 rise 0 R31 read 1 0 fall 0 L0 set 0 0 rise 0 L0 read 1 0 fall 0 L1 set 0 0 rise 0 L1 read 1 0 fall 0 L2 set BCLK signal goes through inverter to allow counters to advance on falling edge of SCK Transmission starts when cnt=0b01111111 -> 0b1000000 Transmission ends when cnt=0b10010100 or local Reset low (teensy pin 32 high) Counter increases on rising edge of BCLK BCLK SCK Cnt WS=Cnt[5] OP Tx Cnt(next) Tx(next) 1 0 01111110 1 Off 01101001 Off fall rise ` 1 ` 0 1 ` 1 rise fall 01111111 1 01101010 ` 1 0 ` 1 fall rise ` 1 R30 read 0 1 ` 1 rise fall 10000000 fall R31 set On 01101011 ` 1 0 ` 0 ` fall rise ` 0 R31 read 0 1 ` 0 rise fall 10000001 0 L0 set 01101100 1 0 ` 0 fall rise ` 0 L0 read 0 1 ` 0 rise fall 10000010 0 L1 set 01101101 1 0 ` 0 fall rise ` 0 L1 read 0 1 ` 0 rise fall 10000011 0 L2 set 01101110 ....... 1 0 ` 0 fall rise ` 0 L16 read 0 1 ` 0 rise fall 10010010 0 L17 set 01111101 1 0 ` 0 fall rise ` 0 L17 read 0 1 ` 0 rise fall 10010011 0 L18 set 01111110 1 0 ` 0 fall rise ` 0 L18 read 0 1 ` 0 rise fall 10010100 0 L19 set Off 01111111 1 0 ` 0 ` fall rise ` 0 L19 read 0 1 ` 0 rise fall 10010101 0 L20 set 10000000 On 1 0 ` 0 ` fall rise ` 0 L20 read 0 1 ` 0 rise fall 10010110 0 L21 set 10000001 1 0 ` 0 fall rise ` 0 L21 read 0 1 ` 0 rise fall 10010111 0 L22 set 10000010 The preload jumpers should be set to achieve the following counter values, for microphones transmitting in order 0,1,2...B; or for an extra bit at beginning decrement by 1 Mic Cnt Cnt2Bin2 0 127 126 01111110 1 106 105 01101001 2 85 84 01010100 3 64 63 00111111 4 43 42 00101010 5 22 21 00010101 6 1 0 00000000 7 236 235 11101011 8 215 214 11010110 9 194 193 11000001 A 173 172 10101100 B 152 151 10010111 Transmission starts when cnt turns 128, ends when cnt=148, with 1 free bit before next transmission to avoid bus contention. After the last transmission (B), there are 4 free bits during which a reset event may be performed. It is desirable to reset to a state before transmission starts so the next rising edge will initiate transmission. The reset signal will need to end before the BCLK rising edge, as illustrated: BCLK SCK Cnt WS=Cnt[5] OP Tx Cnt(next) Tx(next) Reset (local polarity) rise fall ???????? ? ? ???????? ? 1 1 0 ` ? ? ? ` fall rise 01111111 1 Off 01101010 Off fall 0 1 ` 1 rise fall 01111111 1 ` 01101010 ` 0 1 0 ` 1 ..... 1 0 ` 1 (rise-) fall rise 01111111 1 R30 read ` 01101010 ` rise 0 1 ` 1 (rise+) rise fall 10000000 fall R31 set On 01101011 ` 1 1 0 ` 0 ` fall rise ` 0 R31 read 0 1 ` 0 rise fall 10000001 0 L0 set 01101100 1 0 ` 0 fall rise ` 0 L0 read From the view of the teensy board: A reset event may start (teensy pin 32 pulled high) at any point, and should end (teensy pin 32 pulled low) slightly before or after the falling edge of BCLK Following the reset event, on the next rising edge of BCLK, mic board 0 will start to transmit. On the next falling edge of BCLK the right channel LSB (dummy bit, which may be 0 or 1 as the microphone is tri-stated) is to be read. On subsequent 19 falling edges, bits 0-18 (where 0 represents MSB) of microphone data are read (the last bit should be 0 for these microphones, and there are 18 bits of audio data). On the next BCLK rising edge, mic board 0 stops transmitting and the bus is free on the subsequent falling edge (should read 0). There have been a total of 21 BCLK rising edges at this point. On the next BCLK rising edge, mic board 1 starts transmitting, repeating above sequence. Eventually, mic board B will stop transmitting on a BCLK rising edge. There have been 252 BCLK rising edges at this point. The bus is free on subsequent falling edge (should read 0). Since the next 4 rising edges will be free, we expect to read another 4 falling edges as 0. The process then repeats with mic board 0 starting to transmit on the next BCLK rising edge. 1 audio sample per microphone is acquired in 256 BCLK periods. Acquisition at 10 KHz sample rate therefore requires a BCLK of 2.56 MHz. Microphone supported minimum is 2.048 MHz (or 8 KHz sample rate) and maximum 4.096 MHz (16 KHz sample rate). With 2 bytes per sample, 10 KHz SR on 96 microphones gives 1.92 MByte/s. 8 KHz gives 1.536 MB/s, 16 KHz gives 3.072 MB/s. The Teensy FlexIO module takes 480 MHz clock from PLL3_sw, then through configurable dividers of 2 and 8, to give a starting clock of 30 MHz. This should be divided by (8 to 14) x to be within the specs for the microphone (2.048 to 4.096) MHz, giving (2.14 to 3.75) MHz. Dividing by 12 x gives a BCLK of 2.5 MHz, near to that for 10 KHz sample rate (actually 9.766 KHz). Also if dividers are configured for a 240 MHz starting clock, then dividing by 94 x gives 2.55 MHz (9.973 KHz SR), or 120 MHz / 46 x = 2.61 MHz (10.190 KHz SR). The timer period should be set to half of the divider value minus 1. Let's start with the 2.5 MHz BCLK, then the timer compare register should be set to 5 (after 6 rising edges of the starting clock, it will toggle the edge of output BCLK, for a total division by 12). The bit shift register to read 21 bits should be set to 21*2-1=41, since this counts both rising and falling edges of BCLK. However for simplicity initially it will be adequate to read 32 bits (the full shift register) by setting the counter to 32*2-1=63. With timer in 8-bit baud counter mode, this requires a setting of (63)(5)=0x3F05 for the timer compare register TIMCMP. Configure SHIFTCTL to receive data on falling edge of BCLK. Read data periodically from SHIFTBUF. Microphone bus data pins Bus Teensy pin Native FlexIO2 pin FlexIO3 pin BCLK 8 B1_00 16 16 a 41 AD_B1_05 5 b 40 AD_B1_04 4 c 39 AD_B1_13 13 d 38 AD_B1_12 12 e 37 B1_03 19 19 f 36 B1_02 18 18 g 35 B1_12 28 28 h 34 B1_13 29 29 There are 8 32-bit shift registers available in each module so this should all be doable using FlexIO3 only, however FlexIO2 may also be used if needed. To configure all pins for FlexIO3: IOMUXC_SW_MUX_CTL_PAD_GPIO_B1_00 = 9; // BCLK - HW pin 8 to FlexIO3.16 IOMUXC_SW_MUX_CTL_PAD_GPIO_AD_B1_05 = 9;// Bus a HW pin 41 to FlexIO3.05 IOMUXC_SW_MUX_CTL_PAD_GPIO_AD_B1_04 = 9;// Bus b HW pin 40 to FlexIO3.04 IOMUXC_SW_MUX_CTL_PAD_GPIO_AD_B1_13 = 9;// Bus c HW pin 39 to FlexIO3.13 IOMUXC_SW_MUX_CTL_PAD_GPIO_AD_B1_12 = 9;// Bus d HW pin 38 to FlexIO3.12 IOMUXC_SW_MUX_CTL_PAD_GPIO_B1_03 = 9; // Bus e HW pin 37 to FlexIO3.19 IOMUXC_SW_MUX_CTL_PAD_GPIO_B1_02 = 9; // Bus f HW pin 36 to FlexIO3.18 IOMUXC_SW_MUX_CTL_PAD_GPIO_B1_12 = 9; // Bus g HW pin 35 to FlexIO3.28 IOMUXC_SW_MUX_CTL_PAD_GPIO_B1_13 = 9; // Bus h HW pin 34 to FlexIO3.29 SHIFTCTL setup TIMSEL - the timer used to generate BCLK TIMPOL - 1 to shift on falling edge of timer PINCFG - 0 (no output) PINSEL - 4 to 29 as in above list SMOD - 1 for receive mode Result: 0x01800501 to use timer 1 with pin f5 0x01800401 to use timer 1 with pin f4 ... 0x01801D01 to use timer 1 with pin f29 SHIFTCFG setup PWIDTH - 0 to shift 1 bit at a time Result: 0x0 (no need to write) Check SHIFTSTAT bits 7-0 to find when data is ready to be read, flag is cleared when SHIFTBUF register is read. "SHIFTBUF should only be read when the status flag is set" per manual Simple mode (for now) Use timer 1 to output continuous BCLK and control shift register TIMCTL setup TRGSEL - 0 (not used) TRGSRC - 1 (not used) PINCFG - 0b11 output on pin PINSEL - 16 to select HW pin 8 TIMOD - 1 8-bit baud counter Result: 0x00401001 TIMCFG setup All 0 (no need to write) TIMCMP 0x3F05 (described above) Complicated mode (for later) Use timer 0 to output continuous BCLK run in 16-bit counter mode with TIMCMP=5 for 2.5 MHz BCLK Use timer 1 to count 252 and 4 bits to gate timer 2 Use timer 2 to shift in 21 bits when enabled by timer 1 Measurements BCLK of 2.5 MHz (0.4 us period) Reset line driven low within 50 ns of BCLK falling edge (the delay is likely due to the data synchronization delay from FlexIO module, equal to 1.5 FlexIO clocks or about 50 ns at 30 MHz) Microphone transmit enable every 102.4 us, expected 256*0.4 us = 102.4 us Microphone transmit width 8 us, expected 20*0.4 us = 8 us WCLK period 25.6 us, expected 64*0.4 = 25.6 us Microphone transmit offset 42.4 us between mic 0 and mic 23 start times, then 60.0 us between mic 23 and mic 0 start times Transmission starts when cnt turns 128, ends when cnt=148 mic0 mic23 0 23 Reset, 0 us 105 128 +105 counts, 42 us, mic23 starts transmit 125 148 +20 counts, 50 us, mic23 ends transmit 128 151 +3 counts, 51.2 us, mic0 starts transmit 148 171 +20 counts, 59.2 us, mic0 ends transmit 0 23 +108 counts, back to reset state 105 128 +213 counts, 144.4 us, mic23 starts transmit Expected width=20*0.4=8 us, mic0 to mic23=233*0.4=93.2 us, mic23 to mic0=23*0.4=9.2 us The transmit offset is inconsistent and varies between trials. There appears to be an issue with the reset line being able to synchronize the counters. The reset line coming into the microphone board is as expected. 1 bit width = 2 edges = code 1 2 bit width = 4 edges = code 3 32 bit width = 64 edges = code 63 The circuits all seem to be set up correctly. Could there be an issue with noise on the clock line causing desynchronization over time? If I record values immediately one after another, they are synchronized, but at 1 second intervals, they move around randomly.