Q2687 SPI Problem

Hi ,
In Spi for read and write operation which mode we have to use synchronous or asynchronous?
if i use read and write function call in Synchronous will it work :question:
Thanks and Regards
kiran

I believe asynchronous must be OK…

Now i’m trying to include a SD Card on a project too .

If u have seen on some documentations you need to pull up
2 singnals on your SD Card , marked as NC when you are using
SPI …

SD Card works fine on Q2687 with SPI ! :slight_smile:

I think its a great idea! :smiley: . This is my personal contribution to make a solid SPI Handle.

In my personal experience, i worked with a AT45DB161B 2Mbytes SPI EEProm Memory and i had lots of troubles using Wavecoms SPI functions because there are not well documented. The firmware im using is the latest (R74) and the AT OS is the 6.31.

First of all, you must make a initialitation.

1-To do that, you need to use the "s32 adl_busSubscribe ( adl_busID_e BusId, u32 BlockId, void *BusParam )function.
This step is one of the most important, because you must set the correct setting of your SPI port, if you make some mistakes here you wont be able to make a good comunication. Lets chek the parameters of adl_busSubscribe .

*adl_busID_e BusId => Is the flag that repersents wich port you want to use. For SPI you must use ADL_BUS_ID_SPI .
*u32 BlockId => Is the Handler ID. You can make severals handlers for several ports and treat them in different way.

  • void *BusParam => Heres the big deal, this is the Configuration of the SPI bus. Its a struct with some parameters that will be explained right now.

typedef struct _adl_busSPISettings_t
{
u32 Clk_Speed;
u32 Clk_Mode;

u32     ChipSelect;

u32     ChipSelectPolarity;
u32     LsbFirst;

adl_ioDefs_t GpioChipSelect;

u32     LoadSignal;
u32     DataLinesConf;
 u32     MasterMode;
   u32     BusySignal;

} adl_busSPISettings_t;

*u32 Clk_Speed: Its a frequency divider, the count is
the count is 13Mhs/(Clk_Speed+1).

*u32 Clk_Mode: The clock mode basically defines the normal
level of the clock in rest state and the valid edge. This must
be the same as your device. See your device datasheet,

*u32 ChipSelect: This defines the management of the CS
device. You can levit to wavecom´s OS (i dont recomend it!)
or you can leave the management to the GPIOs apis (i use this one).

*u32 LsbFirst: This defines if you want to send the MSB
bits frst or the LSB.

*adl_ioDefs_t GpioChipSelect: This sets wich pin will be CS. Normally
if you want that Wavecom OS control your CS this is 31 or 25. But
if you want to controll you own line with the GPIO apis, leave it to ‘0’.

*u32 LoadSignal:This is a treacky one, basically, this flag indicate if
you are using the LOAD (CS) or not. Again, i you want to controll
the CS by yourself just put “ADL_BUS_SPI_LOAD_UNUSED”, otherwise
“ADL_BUS_SPI_LOAD_USED”.

*u32 DataLinesConf: Basically, if youre are using a 3 wire device
you must put “ADL_BUS_SPI_DATA_UNIDIR” otherwise “ADL_BUS_SPI_DATA_BIDIR”.

*u32 MasterMode: The easiest! :slight_smile:, master or slave!.

*u32 BusySignal:Some devices uset, others dont.

This is my personal configuration as an example.
const adl_busSPISettings_t MySpiconfig =
{
5,
//ADL_BUS_SPI_CLK_MODE_0,
ADL_BUS_SPI_CLK_MODE_0,
ADL_BUS_SPI_ADDR_CS_NONE,
ADL_BUS_SPI_CS_POL_LOW,
ADL_BUS_SPI_MSB_FIRST,
0,
//ADL_BUS_SPI_FRAME_HANDLING,
ADL_BUS_SPI_LOAD_UNUSED,
ADL_BUS_SPI_DATA_UNIDIR,
ADL_BUS_SPI_MASTER_MODE,
ADL_BUS_SPI_BUSY_UNUSED
};

2-Once you Init your handler, you must set the sizes of the bus with the
“adl_busIOCtl” function. You must set three thing:

*Data size
*Adress size
*Opcode size

Now, i will show u how i did it, because you cant size the way you want.
For example, my memory needs for some operation, 6 bytes of adress
this is 48bits, if you want to size that you´ll recieve a parameter
error. So the right tecnique is not use the Adress and Opcode features that
Wavecoms has and just size to 0 bytes. Data cant be size more than 16bits.

So, i´ll size them as this.

Data size=8bits. //Wavecom will write data in packets of 8bits.
Adress size=0bits. //WEavecom wont write the Adress.Ill doit
Opcode size=0bits. //Wavecom wont write the Opcode.Ill doit

For example if you want to send 1Byte(OPCODE)+6Bytes(ADRESS), you should
send the 7 Bytes one by one with the bus write command and control the CS
with the GPIO`s api (ill show you how more ahead). This is basically the
way i manage my device and its a general porpose to any SPI device.

Again, there is the code.
u32 Datasize=8;
u32 Bussize=0;
u32 Opsize=0;
s32 adl_busIOCtlAnswer=adl_busIOCtl(adl_busSubscribeHandler,ADL_BUS_CMD_SET_ADD_SIZE,&Bussize);
s32 adl_busIOCtlAnswer=adl_busIOCtl(adl_busSubscribeHandler,ADL_BUS_CMD_SET_DATA_SIZE,&Datasize);
s32 adl_busIOCtlAnswer=adl_busIOCtl(adl_busSubscribeHandler,ADL_BUS_CMD_SET_OP_SIZE,&Opsize);

3- Now, we can write or read from a SPI device. Before I start i must explain with higher detail how is my method,
first if i want to write lets say 7 bytes (1 Op+6 Adress) y need to put down the CS line (actually, this depends of the device, in my case is like this) then write in to the bus and then rise the CS to finish the write.
For reading, its a different story, most of SPI devices first recieve the reading command from the Master and then output the data to the bus, this means that the Wavecom first must write the command to the bus, and then read. This is exaclty what read does, but unfortunetly if the Adress is more than 16 (perhaps its a bug) jus dont work. Thats why i controll my CS line by using GPIO´s apis and dont let Wavecoms control it. In conclution, for reading i down the CS line (again, this is for my device, perhaps in other you must reaise the CS, please check your datasheet) then i write the OP and Adress, then withou rise the CS line a make a reading (i read 1 byte at a time and save it into a buffer) and then rise the CS line.
Supossely, all this work should be done by SPI automatelly, but for some reason i dont know (and believe me, ive tested like a million times) i dont work.

This is the code for write and read.
void SPI_Write(u8 *Data,int DataLenghts)
{
pAccessModeSPI.Address=0x00;
pAccessModeSPI.Address=0x00;
s32 adl_busWriteAnswer=adl_busWrite(adl_busSubscribeHandler,&pAccessModeSPI,DataLenghts,Data);
}

void SPI_Read (u8 *Data,int DataLengh)
{
pAccessModeSPI.Opcode=0;
pAccessModeSPI.Address=0;
s32 adl_busReadAnswer=adl_busRead(adl_busSubscribeHandler,&pAccessModeSPI,DataLengh,Data);
}

This is my method, its my personal conribution for you for helping me before, i could explained with more detail but it would be too large. If you need help with your code or some tip send me an email and then ill post for everyone.

Best regards to all!,
Nicolas.

If i remember well BUSY and LOAD signals aren’t available yet,
and also only Master mode is available for SPI.

Ive just finished a project were i have to manage the comunication between my Wavecom and a ATMEL microcontroller as a Slave using SPI with the tree wires mode and i handt have to use LOAD and BUSY signals.

I believe those are used in some rare ocation, so it shouldnt be a problem to worried about.

had or had not?
i’ve also implemented SPI slave on an atmel. even without the chip_select signal.
and i never used the busy and load signals

It hasn have the LOAD and BUSY signals. If you ever want to comunicate with a device that has this signals you must use in the CPU two GPIOS. And yes, it has the slave feature.

in r74 firmware maybe ,
in r73 wasn’t available .