Re: [PATCH 2/2] i2c: designware: slave should do WRITE_REQUESTED before WRITE_RECEIVED
On 11/4/20 12:17 PM, michael...@vatics.com wrote: Hi Wolfram, dev->status can be used to record the current state, especially Designware I2C controller has no interrupts to identify a write-request. This patch Just double-checking: the designware HW does not raise an interrupt when its own address + RW bit has been received? Not exactly. There're an interrupt state name "RD_REQ" but no one named like "WR_REQ". For read-request, the slave will get a RD_REQ interrupt. For write-request, the slave won't be interrupted until data arrived to trigger interrupt "RX_FULL". I tried to use GPIO to simulate an I2C master. I only sent its own address + W bit without any data and then I got only a STOP_DET interrupt. If I sent its own address + W bit + one byte data and then I got one RX_FULL and a STOP_DET. It seems the controller doesn't interrupt when RW bit is W, but R does. What do you think, Jarkko? Yes, the datasheet has a flowchart for slave mode and it shows for a write only RX_FULL interrupt followed by read from IC_DATA_CMD to retrieve received byte. Which I believe won't occur if there is no incoming data byte and only STOP_DET happens as you have observed. The flowchart however doesn't include the STOP_DET flow. Jarkko
RE: [PATCH 2/2] i2c: designware: slave should do WRITE_REQUESTED before WRITE_RECEIVED
Hi Wolfram, > Thanks for the detailed explanation! Okay, then what you do looks > correct to me (from a high level perspective without really knowing the > HW): when RX is full, you first send the state WRITE_REQUESTED when > there is no other transfer on-going. Then you send WRITE_RECEIVED > immediately. I think this is the way to do it. Bingo!! Thanks for your understanding. I think I should have a habit of writing comments... X-P Best regards, Michael Wu
Re: [PATCH 2/2] i2c: designware: slave should do WRITE_REQUESTED before WRITE_RECEIVED
> Not exactly. There're an interrupt state name "RD_REQ" but no one named > like "WR_REQ". > > For read-request, the slave will get a RD_REQ interrupt. > For write-request, the slave won't be interrupted until data arrived to > trigger interrupt "RX_FULL". > > I tried to use GPIO to simulate an I2C master. I only sent its own > address + W bit without any data and then I got only a STOP_DET interrupt. > If I sent its own address + W bit + one byte data and then I got one > RX_FULL and a STOP_DET. > > It seems the controller doesn't interrupt when RW bit is W, but R does. Thanks for the detailed explanation! Okay, then what you do looks correct to me (from a high level perspective without really knowing the HW): when RX is full, you first send the state WRITE_REQUESTED when there is no other transfer on-going. Then you send WRITE_RECEIVED immediately. I think this is the way to do it. signature.asc Description: PGP signature
RE: [PATCH 2/2] i2c: designware: slave should do WRITE_REQUESTED before WRITE_RECEIVED
Hi Wolfram, > > dev->status can be used to record the current state, especially Designware > > I2C controller has no interrupts to identify a write-request. This patch > > Just double-checking: the designware HW does not raise an interrupt when > its own address + RW bit has been received? Not exactly. There're an interrupt state name "RD_REQ" but no one named like "WR_REQ". For read-request, the slave will get a RD_REQ interrupt. For write-request, the slave won't be interrupted until data arrived to trigger interrupt "RX_FULL". I tried to use GPIO to simulate an I2C master. I only sent its own address + W bit without any data and then I got only a STOP_DET interrupt. If I sent its own address + W bit + one byte data and then I got one RX_FULL and a STOP_DET. It seems the controller doesn't interrupt when RW bit is W, but R does. What do you think, Jarkko? Sincerely, Michael Wu
Re: [PATCH 2/2] i2c: designware: slave should do WRITE_REQUESTED before WRITE_RECEIVED
Hi Michael, > Documentation/i2c/slave-interface.rst says that I2C_SLAVE_WRITE_REQUESTED, > which is mandatory, should be sent while the data did not arrive yet. It > means in a write-request I2C_SLAVE_WRITE_REQUESTED should be reported > before any I2C_SLAVE_WRITE_RECEIVED. Correct. > dev->status can be used to record the current state, especially Designware > I2C controller has no interrupts to identify a write-request. This patch Just double-checking: the designware HW does not raise an interrupt when its own address + RW bit has been received? Kind regards, Wolfram signature.asc Description: PGP signature
Re: [PATCH 2/2] i2c: designware: slave should do WRITE_REQUESTED before WRITE_RECEIVED
On 10/30/20 10:04 AM, Michael Wu wrote: Sometimes we would get the following flow when doing an i2cset: 0x1 STATUS SLAVE_ACTIVITY=0x1 : RAW_INTR_STAT=0x514 : INTR_STAT=0x4 I2C_SLAVE_WRITE_RECEIVED 0x1 STATUS SLAVE_ACTIVITY=0x0 : RAW_INTR_STAT=0x714 : INTR_STAT=0x204 I2C_SLAVE_WRITE_REQUESTED I2C_SLAVE_WRITE_RECEIVED Documentation/i2c/slave-interface.rst says that I2C_SLAVE_WRITE_REQUESTED, which is mandatory, should be sent while the data did not arrive yet. It means in a write-request I2C_SLAVE_WRITE_REQUESTED should be reported before any I2C_SLAVE_WRITE_RECEIVED. By the way, I2C_SLAVE_STOP didn't be reported in the above case because DW_IC_INTR_STAT was not 0x200. dev->status can be used to record the current state, especially Designware I2C controller has no interrupts to identify a write-request. This patch makes not only I2C_SLAVE_WRITE_REQUESTED been reported first when IC_INTR_RX_FULL is rising and dev->status isn't STATUS_WRITE_IN_PROGRESS but also I2C_SLAVE_STOP been reported when a STOP condition is received. Signed-off-by: Michael Wu --- drivers/i2c/busses/i2c-designware-slave.c | 45 +-- 1 file changed, 18 insertions(+), 27 deletions(-) Acked-by: Jarkko Nikula