How to use cfa_bsc_Configure

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
Anonymous
Not applicable

I am trying to make non-default I2C configuration.

I found cfa_bsc_Configure API in cfa.h file but it does not give detailed information.

void cfa_bsc_Configure(UINT8 newConfig);

// To configure the I2C serial interface. The configuration values include:

//          - Clock Rate

//          - Clock divider

//          - Delay disable

//          - Deglitch disable

- Clock Rate

I can find defines for them(CFA_BSC_CTL_SCL_400KHZ ~ CFA_BSC_CTL_SCL_1000KHZ)

- Clock divider

I can find defines for it(CFA_BSC_CTL_DV_CLK_BY_4)

- Delay diable

I cannot find any defines for it.

- Deglitch disable

I cannot find any defines for it.

Please let me know how to use newConfig input parameter.

Thanks

0 Likes
1 Solution
Anonymous
Not applicable

Finally we can correctly read 0x1E register value(0x02) using cfa_bsc_OpExtended API.

(And it looks like other registers are read correctly.)

It seems that main cause was slave address conflict.

(AS3955's default address : 0xA0, EEPROM slave address : 0xA0)

We referenced the following thread.

https://community.broadcom.com/thread/1460

Thank you jakewtorres and mwf_mmfae .

View solution in original post

0 Likes
9 Replies
MichaelF_56
Moderator
Moderator
Moderator
250 sign-ins 25 comments on blog 10 comments on blog

Have you seen the I2C sample that we provide in the WICED Smart Hardware Interfaces document?

Similar to the I2C Temp Sensor Sample in the SDK (/WICED-Smart-SDK/Apps/i2c_temperature_sensor), this example shows how to initialize I2C in the master role (Master is all we support), and how to write, read and use the combo write-then-read transaction using the driver API available in the WICED SDK (driver is described within WICED-Smart-SDK/Wiced-Smart/cfa/cfa.h, but not documented much beyond what is already provided in previous discussions and HTML API docs in the SDK).

You may want to start by getting one of these examples working, then slowly make customizations to one of these sample apps.

0 Likes
Anonymous
Not applicable

We have 2 devices on the I2C bus using cfa_bsc_OpExtended.

- LIS2DH12TR(MEMS sensor) : read and write OK(Register values are read and written correctly.)

- AS3955-ATDM-I4(NFC tag) : cfa_bsc_OpExtended returns CFA_BSC_STATUS_SUCCESS for read and write,

  but the actual values are not what we expected.

For example, register 0x1E has Major version value of 0x02(We checked it using devkit from AMS).

When we read the register 0x1E using cfa_bsc_OpExtended, it reads 0x00.

So, we checked SDA, SCL signals for both our board and AMS's devkit.

Our board signal(Yellow : SCL, Green : SDA)

20736_as3955_i2c.png

(Too short data signal : red circle)

AMS's devkit signal(Yellow : SCL, Green : SDA)

asm_devkit_i2c.png

We tried to simulate I2C signal pattern for AMS's devkit using Arduino Uno's GPIO function.

And we could read a correct value for the register 0x1E.

Is there any way to give some break between I2C unit operation(read, write, start, stop, restart)?

0 Likes
JacobT_81
Employee
Employee
250 replies posted 100 replies posted 50 replies posted

Hi hojun

I just want to clarify, you did establish i2c communication with your sensor? "And we could read a correct value for the register 0x1E."

The way in which you can break up your i2c operations into individual bytes is by passing NULL values into cfa_bsc_OpExtended and only filling up a single byte with data. 

Jacob

0 Likes
Anonymous
Not applicable

>> I just want to clarify, you did establish i2c communication with your sensor? "And we could read a correct value for the register 0x1E."

This is for picture3. "And we could read a correct value for the register 0x1E on Arduino Uno."

So we thought that if we can make similar signal pattern for AMS's devkit using cfa_bsc_OpExtended, we can read correct register values for AS3955.

And when we found cfa_bsc_Configure API, we thought that we can try cfa_bsc_Configure with different configuration.

Picutre1.

- Our board

20736_as3955.png

Picture2.

- AMS's devkit

ams_devkit_as3955.png

Picture3.

- Arduino Uno

arduino_as3955.png

We tried to simulate I2C signal pattern for AMS's devkit using Arduino Uno's GPIO function.

And we could read a correct value for the register 0x1E on Arduino Uno.

Picture4.

- Register values for AS3955

as3955_i2c_register.png

0 Likes
JacobT_81
Employee
Employee
250 replies posted 100 replies posted 50 replies posted

Do you have the ability to use a decoded logic analyzer? That will make a drastic difference in trying to debug this.

According to your sensor's data sheet, you don't need to break up each i2c byte like your other MCUs are doing. Continuous clocking is fine.

1. Can you post the exact code that produced the scope you posted above?

There is something strange going on here, because if you study the scope, it looks like your sensor is actually responding with 0x02 you expect. However, there are too many clocks before the chip responds, so the ends up displaying 0x00.

2. Please attempt something to give us some clues:

Take your received data pointer and copy 16 bits of it. Apply a right shift of 5, cast it as an 8 bit integer and print it out. Tell me if that produces your 0x02.

You may be getting the data just in the wrong byte frame. Have you altered any i2c settings? What value pull ups do you have on the i2c lines?

Again, a logic analyzer will greatly ease the debugging process on this one.

Jacob

0 Likes
Anonymous
Not applicable

>> Do you have the ability to use a decoded logic analyzer?
We don't have a logic analyzer.

>> 1. Can you post the exact code that produced the scope you posted above?
This is the AS3955 related partial code for our board.

(I added some comments for reducing long explanation.)

Part of our main source code start(currently reading 0x1E register every 1 second for testing)
-----------------------------------------------------------------------


#define B736_PORT(pin)          (pin/16)

#define B736_PORT_PIN(pin)      (pin%16)

// AS3599_Datasheet_EN_V1.pdf, p. 15,

// About 300us(Checked on AMS's devkit)


void b736_ActivateAs3955(void)
{
  int i;

  gpio_setPinOutput(B736_PORT(GPIO_PIN_P8), B736_PORT_PIN(GPIO_PIN_P8), 0);


  for (i = 0; i < 300; i++)
  {
    gpio_setPinOutput(B736_PORT(GPIO_PIN_P8), B736_PORT_PIN(GPIO_PIN_P8), 0);
  }
}

void b736_DeactivateAs3955(void)
{
  gpio_setPinOutput(B736_PORT(GPIO_PIN_P8), B736_PORT_PIN(GPIO_PIN_P8), 1);
}

// Below is executed every 1 second.
//UINT8 data[1] = {0};  // --> cfa_bsc_OpExtended returns CFA_BSC_STATUS_SUCCESS but it still reads 0x00. (data[0] = 0x00)
UINT8 data[2] = {0, 0}; // --> cfa_bsc_OpExtended returns CFA_BSC_STATUS_SUCCESS but it still reads 0x00. (data[0] = 0x00, data[1] = 0x00)

// Device adress : 0xA0,
if (as3955_readReg(0x50 << 1, AS3955_VER_MAJOR, data, sizeof(data)) != 0)
{
  ble_trace0("as3955_readReg failed");
}
else
{
  ble_trace2("Major : 0x%x, 0x%x", data[0], data[1]);
}
-----------------------------------------------------------------------
Part of our main source code end.


AS3955 driver code start
-----------------------------------------------------------------------

#define AS3955_VER_MAJOR      (0x1E)

UINT8 as3955_readReg(UINT8 deviceAddr, UINT8 reg, UINT8 *data, UINT8 bytesToRead)
{
  CFA_BSC_STATUS read_status;
  UINT8 addr[1] = {0x20 | reg}; // AS3599_Datasheet_EN_V1.pdf, p. 69, for reading a single register.

  //ble_trace1("Addr : 0x%x", addr[0]);
 
  // AS3599_Datasheet_EN_V1.pdf, p. 15,
  // About 300us(Checked on AMS's devkit)
  b736_ActivateAs3955();

  read_status = cfa_bsc_OpExtended(data, bytesToRead, addr, sizeof(addr), deviceAddr, CFA_BSC_OP_READ);
  b736_DeactivateAs3955();
  if (read_status == CFA_BSC_STATUS_SUCCESS)
  {
    return 0;
  }

  return 1;
}
-----------------------------------------------------------------------

AS3955 driver code end

>>2. Please attempt something to give us some clues:
>>Take your received data pointer and copy 16 bits of it
It still reads 0x00, 0x00. (Please refer to Part of our main source code "// Below is executed every 1 second")

>>You may be getting the data just in the wrong byte frame. Have you altered any i2c settings?
Do you mean cfa_bsc_Configure API?

cfa_bsc_Configure seems to have insufficient documentation.

So we tried this for the parameter newConfig.

(Clock_constant | 0x00, Clock_constant | 0x01, ..., Clock_constant | 0x0F)

It still reads 0x00.

>>What value pull ups do you have on the i2c lines?

No resistors are connected.

(LIS2DH12TR correctly read/write registers on the same I2C lines. So I'm not sure this is the main cause. )

I2C signal test using P0 and P3

We did some experiment like Aruino Uno's case.

We made I2C signal patterns using P0 and P3 on our board.

(We cut the lines from pin number 21(SCL), 22(SDA)  of BCM20736S).

GPIO_PIN_P0 : SCL

GPIO_PIN_P3 : SDA

We can read 0x02 from the register 0x1E of AS3955 using GPIO_PIN_P0, GPIO_PIN_P3.

We are doing some tests, if we get any progress, we'll let you know.

0 Likes
Anonymous
Not applicable

We have some questions.

1. What is the I2C slave address of Internal EEPROM?

(Is the address is 0xA0?)

2. If the I2C slave address of EEPROM, is there any way to change the I2C address of EEPROM?

Our AS3955's the I2C address is also 0xA0.

(So we thought that the two device have address conflict)

0 Likes
Anonymous
Not applicable

Finally we can correctly read 0x1E register value(0x02) using cfa_bsc_OpExtended API.

(And it looks like other registers are read correctly.)

It seems that main cause was slave address conflict.

(AS3955's default address : 0xA0, EEPROM slave address : 0xA0)

We referenced the following thread.

https://community.broadcom.com/thread/1460

Thank you jakewtorres and mwf_mmfae .

0 Likes

Thanks for updating the thread with the resolution hojun

0 Likes