This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Programming an Atmel ATtiny88 using C5535 SPI

I'm trying to program an Atmel ATtiny88 using an SPI channel of a C5535. This requires sending the following "Program Enable" sequence over the SPI bus:

  1. Hold the clock low
  2. Hold chip select (ATtiny RESET pin) low for 20 ms
  3. Clock 4 bytes of data: 0xAC 0x53 0x00 0x00
  4. When clocking the third byte, a 0x53 should be read back on SPI_RX
  5. Drive chip select high

However, I don't see any way for to hold the chip select low for 20 ms, and before writing the four bytes. I figured I could bit-bang these signals. Using the CSPx and CKPx bits in the SPIDCRx register, I can drive the SPI_CSx (chip select) and clock (SPI_CLK) lines either high or low, but I don't see a way to do the same for SPI_TX, or read the value on SPI_RX. Is there a way to do the above programming sequence on the SPI bus?

Also, the SPI bus allows simultaneous reading and writing of data. However, the SPI_write() CSL library function only allows writing. Does the CSL library provide a way to read back data while writing?

  • Hi,

    Please note that writing to SPICMD2 immediately initiates a slave access; therefore you should only write to CSNUM when you are ready to initiate a slave access. One way delay in data transfer after CS is asserted is to use data delay. The SPI module automatically delays the first clock edge with respect to the activation of the SPI_CSn pin by half a SPI_CLK cycle plus a system clock cycle. You can program the SPI module to insert additional clock delay cycles using the data delay bits (DDn) of SPIDCR1 and SPIDCR2 to determine the number of clock delay cycles to insert. The data delay can be specified from zero to three clock cycles (DDn = 00b - 11b).

    But looking at the your requirements that is, to hold the chip select low for 20 ms before writing the four bytes, its looks difficult to acheive through programming concept.

    On CSL support to simultaneous reading & writing, in my understanding there is no support for this.

    Hope this answers your question.

    Regards

     Vasanth

  • Vasanth,

    I finally got this to work using the following set-up:

    1. Set the SPI clock to the slowest possible clock rate by writing 0xFFFE to SPICDR (0xFFFF doesn't work). Although the datasheet says the maximum value is 0x3FFF, It appears all 16 bits are operational. The CSL function SPI_config() doesn't let you set the upper two bits; I had to write to SPICDR directly in my code.
    2. Setting the "data delay" to the maximum (DD1=3 in SPIDCR1)
    3. Slowing the system clock way down from 100 MHz to 10 MHz

    This set-up gave me about 22 ms delay, and allowed me to put the ATtiny88 into programming mode. This is a bit of a hack, but we need a way to field upgrade the ATtiny88 firmware, even if it is slow due to the ridiculously slow SPI clock. Do you know why the datasheet specifies SPICDR bits 0-13, when in fact all 16 bits of this register are operational?

  • I figured out a much simpler way to to program an Atmel ATtiny88 without having to change the clock speed, allowing me to program at a higher SPI clock rate (125 kHz instead of about 200 Hz). I have 4 SPI devices, one on each of the 4 chip selects (SPI_CSx), and all of my SPI devices have active low chip selects. The problem is generating a 20 ms delay from the time the chips select goes low, until the time of the first clock pulse. To program an ATtiny on SPI_CS0:
    1. Set CSP0 in SPIDCR1 to 1, which drives SPI_CS0 low.
    2. Wait 20 ms.
    3. Configure SPI channel 3 for an SPI operation. 
    4. Set CSP3 in SPIDCR2 to 1, which drives SPI_CS3 low.
    5. Write SPI bytes to configure ATtiny programming mode, which drives SPI_CS3 high before clocking data. 
    6. Since only SPI_CS0 is the only low chip select, data will actually be written to/read from the ATtiny on SPI_CS0 (instead of SPI_CS3).
    7. Set CSP0 in SPIDCR1 to 0, which drives SPI_CS0 high.
    8. Set CSP3 in SPIDCR2 to 0, which drives SPI_CS3 high.
    Hopefully this info will be of help to someone trying to do something similar.