ADSP BFin-532: SPORT data-dependent transmit problem
Hi all,
I'm trying to interface BF532 with the Intan RHD2132 amplifiers (listing the amp in case someone has worked with them before). The amplifiers uses SPI: 16-bits commands and data are exchanged through MOSI and MISO when _CS is held low. In between each commands, _CS needs to be pulsed high for >154ns.
I'm using both SPORT channels, and both primary and secondary ports to talk to four amps with the following wiring connections, based on the application note (http://www.analog.com/media/en/technical-documentation/application-notes/EE_304_Blackfin.pdf)
RFS0 connected to TFS0 --> connected to _CS
RFS1 connected to TFS1 --> connected to _CS
DTxPRI and DTxSEC connected to MOSI
DRxPRI and DRxSEC connected to MISO
My SCLK is 80MHz, as a test, I used the following settings:
*pSPORT0_TCLKDIV = 1;
*pSPORT0_TFSDIV = 4;
*pSPORT0_TCR2 = TXSE | 0xf;
*pSPORT0_RCR2 = RXSE | 0xf;
*pSPORT1_TCLKDIV = 1;
*pSPORT1_TFSDIV = 4;
*pSPORT1_TCR2 = TXSE | 0xf;
*pSPORT1_RCR2 = RXSE | 0xf;
*pSPORT0_TCR1 = TCKFE | LATFS | LTFS | TFSR | ITFS | ITCLK | DITFS; // data-independent transmit, active low, late FS
*pSPORT1_TCR1 = TCKFE | LATFS | LTFS | TFSR | ITFS | ITCLK | DITFS; // data-independent transmit, active low, late FS
*pSPORT0_RCR1 = RCKFE | LARFS | LRFS | RFSR; // RFS taken from external TFS
*pSPORT1_RCR1 = RCKFE | LARFS | LRFS | RFSR; // RFS taken from external TFS
I would have the TCLK running at 20MHz. Frame-sync is asserted low for 16 TCLK cycles (800ns), followed by 4 TCLK cycles high (200ns), fulfilling my requirements. This works, as confirmed on the oscilloscope.
But making the TFS data-dependent (by taking out DITFS), and continually pushing contents into SPORTx_TX, I should get the same frame-sync behavior. However this is not the case. With the following code:
--------------------------
int main() {
// turn all SPORT off
*pSPORT0_TCR1 = 0x0000;
*pSPORT0_RCR1 = 0x0000;
*pSPORT1_TCR1 = 0x0000;
*pSPORT1_RCR1 = 0x0000;
*pSPORT0_TCLKDIV = 1;
*pSPORT0_TFSDIV = 4;
*pSPORT0_TCR2 = TXSE | 0xf;
*pSPORT0_RCR2 = RXSE | 0xf;
*pSPORT1_TCLKDIV = 1;
*pSPORT1_TFSDIV = 4;
*pSPORT1_TCR2 = TXSE | 0xf;
*pSPORT1_RCR2 = RXSE | 0xf;
*pSPORT0_TCR1 = TCKFE | LATFS | LTFS | TFSR | ITFS | ITCLK; // data-DEPENDENT transmit
*pSPORT1_TCR1 = TCKFE | LATFS | LTFS | TFSR | ITFS | ITCLK; // data-DEPENDENT transmit
*pSPORT0_RCR1 = RCKFE | LARFS | LRFS | RFSR; // RFS taken from external TFS
*pSPORT1_RCR1 = RCKFE | LARFS | LRFS | RFSR; // RFS taken from external TFS
asm volatile("ssync;");
radio_bidi_asm();
return 0;
}
-----------------------
// In frame_sync_test.asm
#define NEXT_CHANNEL 0x3f00
.global _radio_bidi_asm
_radio_bidi_asm:
p5.l = LO(SPORT0_TCR1);
p5.h = HI(SPORT0_TCR1);
r0.l = TCKFE | LATFS | LTFS | TFSR | ITFS | ITCLK | TSPEN; // data-DEPENDENT transmit
w[p5] = r0;
p5.l = LO(SPORT1_TCR1);
p5.h = HI(SPORT1_TCR1);
w[p5] = r0;
p5.l = LO(SPORT0_RCR1);
p5.h = HI(SPORT0_RCR1);
r0.l = RCKFE | LARFS | LRFS | RFSR | RSPEN;
w[p5] = r0;
p5.l = LO(SPORT1_RCR1);
p5.h = HI(SPORT1_RCR1);
w[p5] = r0;
ssync;
p0.l = LO(SPORT0_RX);
p0.h = HI(SPORT0_RX);
// push one set to TX-fifo
r0 = 0 (z);
w[p0] = r0;
w[p0] = r0;
w[p0 + (SPORT1_TX - SPORT0_RX)] = r0;
w[p0 + (SPORT1_TX - SPORT0_RX)] = r0;
// push another one to TX-fifo
r0 = NEXT_CHANNEL (z);
w[p0] = r0;
w[p0] = r0;
w[p0 + (SPORT1_TX - SPORT0_RX)] = r0;
w[p0 + (SPORT1_TX - SPORT0_RX)] = r0;
jump get_samples;
// there should always be one set of values in transmit FIFO
get_samples:
r7 = NEXT_CHANNEL (z);
wait_samples: // wait until we have finished receiving/transmitting one set of 16-bit words
r3 = w[p0 + (SPORT1_STAT - SPORT0_RX)];
cc = bittst(r3,0);
if !cc jump wait_samples;
// should still be one more set in the FIFO
// queue next channel in transmit FIFO.
w[p0 + (SPORT0_TX - SPORT0_RX)] = r7; // SPORT0 primary TX
w[p0 + (SPORT0_TX - SPORT0_RX)] = r7; // SPORT0 sec TX
w[p0 + (SPORT1_TX - SPORT0_RX)] = r7; // SPORT1 primary TX
w[p0 + (SPORT1_TX - SPORT0_RX)] = r7; // SPORT1 sec TX
// read out the samples just received
r1 = w[p0 + (SPORT1_RX - SPORT0_RX)];
r0 = w[p0 + (SPORT1_RX - SPORT0_RX)];
r1 = w[p0];
r0 = w[p0];
jump wait_samples;
-------------------------------------------
What I get on the oscilloscope is that, frame-sync is ALWAYS low! The signals are the DTxPRI and DTxSEC are what I sent in the code. But since the frame-sync is always low, the amplifier will never execute the commands I send it.
Why is this happening? Since my SCLK is running at 80Mhz, a new set of values is loaded into the transmit FIFO before the current word is finished transmit, so the transmit FIFO is never empty and data is always available for transmission.
What can I do to fix this? Using data-independent frame-sync instead?
Thanks,
Allen
frame_sync
bf532
sport_blackfin
Hi Allen,
When Sport is configured for late and low frame sync mode, the frame sync will remain low for the entire data duration, if there are two data transfers one after the other, frame sync won't toggle and just continue to be low(FSDIV=SLEN or (SLEN+1) is integral multiple of SLEN.
Can you try TFSDIV=SLEN+4 ( 4 high period and SLEN+1 low period) . Also configure the oscilloscope to trigger on edge just to make sure that you capture the change in FS( then you don't have to worry whether FIFO is filled in time).
Thanks,
Sachin
Hi Sachin,
Right, I figured that might be the case after trying different configurations. I wish the manual had made it a bit more clear in terms of corner cases like this.
Thanks,
Allen
This question has been assumed as answered either offline via email or with a multi-part answer. This question has now been closed out. If you have an inquiry related to this topic please post a new question in the applicable product forum.
Thank you,
EZ Admin
Please log in to reply.