Skip to content

Two-wire I2S synchronous serial interface, compatible with I2S specification.

License

Notifications You must be signed in to change notification settings

efabless/EF_I2S

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

EF_I2S

Two-wire I2S synchronous serial interface, compatible with I2S specification.

  • Receiver only
  • 32x32 Receive FIFO
  • Sample Size selection
  • Left channel, Right channel only or Stereo
  • Programmable prescaler
  • Supports both the classical I2S and the Left-aligned formats
  • Programmable sample size
  • Zero/Sign extension for the samples

The wrapped IP

APB, AHBL, and Wishbone wrappers, generated by the BusWrap bus_wrap.py utility, are provided. All wrappers provide the same programmer's interface as outlined in the following sections.

Wrapped IP System Integration

Based on your use case, use one of the provided wrappers or create a wrapper for your system bus type. For an example of how to integrate the APB wrapper:

EF_I2S_APB INST (
       `TB_APB_SLAVE_CONN,
       .ws(ws),
       .sck(sck),
       .sdi(sdi)
);

NOTE: `TB_APB_SLAVE_CONN is a convenient macro provided by BusWrap.

Implementation example

The following table is the result for implementing the EF_I2S IP with different wrappers using Sky130 PDK and OpenLane2 flow.

Module Number of cells Max. freq
EF_I2S 2433 116
EF_I2S_APB 2716 142
EF_I2S_AHBL 2799 135
EF_I2S_WB 2941 136

The Programmer's Interface

Registers

Name Offset Reset Value Access Mode Description
RXDATA 0000 0x00000000 r The received sample
PR 0004 0x00000000 w The Prescaler register; used to determine the sck signal frequency . $Prescaler = clk_freq/(2 x sck_freq) - 1$.
AVGT 0008 0x00000000 w The Average threshold
ZCRT 000c 0x00000000 w The ZCR threshold
CTRL 0010 0x00000000 w Control Register; 0:Enable, 1:FIFO Enable.
CFG 0014 0x00000201 w Configuration Register, 0-1: Channels to read, '01': right, '10': left, '11': Both (stereo) 2: Sign Extend 3: Left Justify 4-8: Sample Size (0-31)
RX_FIFO_LEVEL fe00 0x00000000 r RX_FIFO Level Register
RX_FIFO_THRESHOLD fe04 0x00000000 w RX_FIFO Level Threshold Register
RX_FIFO_FLUSH fe08 0x00000000 w RX_FIFO Flush Register
IM ff00 0x00000000 w Interrupt Mask Register; write 1/0 to enable/disable interrupts; check the interrupt flags table for more details
RIS ff08 0x00000000 w Raw Interrupt Status; reflects the current interrupts status;check the interrupt flags table for more details
MIS ff04 0x00000000 w Masked Interrupt Status; On a read, this register gives the current masked status value of the corresponding interrupt. A write has no effect; check the interrupt flags table for more details
IC ff0c 0x00000000 w Interrupt Clear Register; On a write of 1, the corresponding interrupt (both raw interrupt and masked interrupt, if enabled) is cleared; check the interrupt flags table for more details

RXDATA Register [Offset: 0x0, mode: r]

The received sample

PR Register [Offset: 0x4, mode: w]

The Prescaler register; used to determine the sck signal frequency . $Prescaler = clk_freq/(2 x sck_freq) - 1$.

AVGT Register [Offset: 0x8, mode: w]

The Average threshold

ZCRT Register [Offset: 0xc, mode: w]

The ZCR threshold

CTRL Register [Offset: 0x10, mode: w]

Control Register; 0:Enable, 1:FIFO Enable.

bit field name width description
0 en 1 Enable
1 fifo_en 1 Fifo Enable
2 avg_en 1 Averaging enable
3 zcr_en 1 ZCR enable

CFG Register [Offset: 0x14, mode: w]

Configuration Register, 0-1: Channels to read, '01': right, '10': left, '11': Both (stereo) 2: Sign Extend 3: Left Justify 4-8: Sample Size (0-31)

bit field name width description
0 channels 2 Channels to read, '01': right, '10': left, '11': Both (stereo)
2 sign_extend 1 Sign Extend
3 left_justified 1 Left justified flag
4 sample_size 6 Sample size
10 AVGSEL 1 Select the number of samples to average
11 ZCRSEL 1 Select the number of samples to calculate the ZCR

RX_FIFO_LEVEL Register [Offset: 0xfe00, mode: r]

RX_FIFO Level Register

bit field name width description
0 level 4 FIFO data level

RX_FIFO_THRESHOLD Register [Offset: 0xfe04, mode: w]

RX_FIFO Level Threshold Register

bit field name width description
0 threshold 4 FIFO level threshold value

RX_FIFO_FLUSH Register [Offset: 0xfe08, mode: w]

RX_FIFO Flush Register

bit field name width description
0 flush 1 FIFO flush

Interrupt Flags

The wrapped IP provides four registers to deal with interrupts: IM, RIS, MIS and IC. These registers exist for all wrapper types generated by the BusWrap bus_wrap.py utility.

Each register has a group of bits for the interrupt sources/flags.

  • IM: is used to enable/disable interrupt sources.

  • RIS: has the current interrupt status (interrupt flags) whether they are enabled or disabled.

  • MIS: is the result of masking (ANDing) RIS by IM.

  • IC: is used to clear an interrupt flag.

The following are the bit definitions for the interrupt registers:

Bit Flag Width Description
0 FIFOE 1 Receive FIFO is Empty
1 FIFOA 1 FIFO level is above the set level threshold
2 FIFOF 1 Receive FIFO is Full.
3 AVGF 1 The avg is above the threshold.
4 ZCRF 1 The ZCR is above the threshold.
5 VADF 1 The Voice Activity Detector flag; active when both ZCR & AVG flags are active.

The Interface

Module Parameters

Parameter Description Default Value
DW FIFO data width 32
AW FIFO Address width; Depth=2^AW 4

Ports

Port Direction Width Description
ws output 1 Word select (logic high on WS indicates right-channel audio)
sck output 1 The data clock
sdi input 1 The input serial data
fifo_en input 1 FIFO enable
fifo_rd input 1 Read from FIFO signal
fifo_level_threshold input AW FIFO Threshold
fifo_flush input 1 FIFO Flush
fifo_full output 1 FIFO is full flag
fifo_empty output 1 FIFO is empty flag
fifo_level output AW The current FIFO level
fifo_level_above output 1 FIFO level is above threshold flag
fifo_rdata output 32 Data read from FIFO
sign_extend input 1 Flag to show if input data is sign extended
left_justified input 1 Flag to show if input data is left justified
sample_size input 6 The sample size of input data
sck_prescaler input 8 The clock prescaler
avg_threshold input 32 The samples average threshold
avg_flag output 1 Flag raised when the samples average is above a threshold
avg_en input 1 Enable average feature
avg_sel input 1 0 - 32 Samples, 1 - 64 Samples
zcr_threshold input 32 The samples ZCR threshold
zcr_flag output 1 Flag raised when the samples ZCR is above a threshold
zcr_en input 1 Enable average feature
zcr_sel input 1 0 - 32 Samples, 1 - 64 Samples
vad_flag output 1 The VAD flag
channels input 2 Channels used (left, right, or stereo)
en input 1 Enable signal

F/W Usage Guidelines:

  1. Set the prescaler value in the PR register where sck_freq = (clk_freq / (prescaler+1))/2. Note that for the controller to function correctly, the prescaler needs to be greater than 1.
  2. Check the I2S device data sheet to know the sample size sent and configure the sample_size field in the CFG reg accordingly.
  3. Check the I2S device data sheet to know if the samples sent are in left justified or i2s mode and configure the left_justified field in the CFG reg.
  4. Configure the channels field in CFG by specifying which channel you want to capture or both channels (stereo)
  5. If you want the sample to be sign extended by the controller, enable sign_extended field in CFG register
  6. After configuring the controller, enable it along with the FIFO to capture the samples by setting en and fifo_en fields in the CTRL register.
  7. If you want to use the averaging feature in the controller, you can set the avg_en field and set the average threshold AVGT register. The average flag AVGF will be fired when the average of the samples sent are above this threshold. Note that the averaging mode works only when the sign extension mode is on.

Installation:

You can either clone repo or use IPM which is an open-source IPs Package Manager

  • To clone repo: git clone https://github.com/efabless/EF_I2S
  • To download via IPM , follow installation guides here then run ipm install EF_I2S

Run cocotb UVM Testbench:

In IP directory run:

cd verify/uvm-python/
To run testbench for design with APB

To run all tests:

make run_all_tests BUS_TYPE=APB

To run a certain test:

make run_<test_name> BUS_TYPE=APB

To run all tests with a tag:

make run_all_tests TAG=<new_tag> BUS_TYPE=APB
To run testbench for design with APB

To run all tests:

make run_all_tests BUS_TYPE=AHB

To run a certain test:

make run_<test_name> BUS_TYPE=AHB

To run all tests with a tag:

make run_all_tests TAG=<new_tag> BUS_TYPE=AHB