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.
.....2
Hi everyone.....
I m using CC2540 on custom board and working on custom bluetooth 4.0 project. At the first screenshot yellow channel of scope shows destination wave to measure pulse-space width. This wave coming from anolog circuit to P0_7of CC2540. The blue cannel shows catching of any external interrupt(rising&falling). For the first screenshot, the time slot (that has variable value, not fixed) beetwen cursors(value is 189.4 us) is expected value. So, external interrupt on P0_7 is working truely. At the second screenshot, this time, blue cannel showing P0_7 logic-0 state(it means if the P0_7 is logic-0 then toggle) after the capturing any edge. So, after the edge capture, checking the P0_7 state working truely(also, logic-1 state checked).
What i want to?.. I want to measure pulse-space width with 16-bit timer(TIMER1) and save to variable. If the measured pulse-space width with the timer1 is in the destination time slot, then the data array which is coming from analog circuit will place to uint8 array after the evaluation. The code fragments like this;
-For external interrupt init;
P0DIR =(0x07); //P0.7-P0.3 as input- P0.1,P0.2, P0.0 as output/leds-buzzer
P0SEL =(0x80); //P0.7 as peripheral others gpio
PICTL |=0x00; //Port0, inputs 7 to 0 rising edge
P0IEN |=0x80; //P0.7 interrupt enable
IEN1 |=0x20; //Port0 interrupt enable
-For ISR,
#pragma vector=P0INT_VECTOR
__interrupt void P0_isr(void)
{
P0IFG=0x00;
P0IF = 0;
//Need INT0 to trigger on any edge,so xor LSB
PICTL ^=0x01;
_ _ _
//Save Timer/Counter1 into variable to compare
delay = T1CNTL;
delay|= (T1CNTH<<8);
//Check whatever pulse or space
if (P0 & 0x80)
{
P0_2=~(P0_2);
event = 0;
}
else
{
P0_1=~(P0_1);
event = 2;
}
//Set to event to select correct state
if(delay > UD_MIN && delay < UD_MAX)
{
event += 4;
}
else if(delay < KD_MIN || delay > KD_MAX)
{
//There is no correct event occur because of noise or erroneous
//so, reset state to initial state
Reset();
}
_ _ _
//Clear Timer/Counter1 to calculate one other pulse-space time
T1CNTH=0;
T1CNTL=0;
}
-For Timer1 Init;
T1CC0L = 0;
T1CC0H = 0;
T1CTL = (T1CTL & ~(T1CTL_MODE | T1CTL_DIV)) | T1CTL_MODE_FREERUN | T1CTL_DIV_32;
-For 32Mhz Clock;
SLEEPCMD |= OSC32K_CALDIS;
// Change the system clock source to HS XOSC and set the clock speed to 32 MHz.
CLKCONCMD = (CLKCONCMD & ~(CLKCON_CLKSPD | CLKCON_OSC)) | CLKCON_CLKSPD_32M;
// Wait until system clock source has changed to HS XOSC (CLKCONSTA.OSC = 0).
while(CLKCONSTA & CLKCON_OSC);
*****AS Result;
I did not read timer1 value truely. So i need to help. Timer1 working free run mode and time division is 32.
Thanks For All......
Hi Daron,
If you use the </> button on the forum text editor you can paste the code in with formatting.
To your question - I don't know if I really understand what you are going to do. But it looks like you are not using the capture mode of the timer.
We don't have any published examples of this (I think) but below is a small function I made once that uses the T1 capture mode and DMA to store pulse lengths. DMA stores the T1 capture register 0x62A6 to &timercapture. You could change timerCapture to be an array. Also please note that the comments for the DMA initialization is wrong.
In the example it is used to calculate a frequency based on time difference after a number of pulses, but you could use the DMAIRQ to read out the latest values in an ISR if you want. That would be more robust than IO ISR and reading T1.
#include "freqCapture.h" #include "hal_dma.h" volatile uint16 timerCapture; volatile double frequency = 0; volatile double ticksAvg; volatile double firstCap; volatile double lastCap; void timerCaptureArmDMA() { halDMADesc_t *ch; ch = HAL_DMA_GET_DESC1234( T1CAP_DMA_CH ); // Abort any pending DMA operations (in case of a soft reset). HAL_DMA_ABORT_CH( T1CAP_DMA_CH ); // The start address of the destination. HAL_DMA_SET_DEST( ch, &timerCapture ); // Using the length field to determine how many bytes to transfer. HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN ); // One byte is transferred each time. HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_WORD ); // The bytes are transferred 1-by-1 on Tx Complete trigger. HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE ); HAL_DMA_SET_TRIG_SRC( ch, HAL_DMA_TRIG_T1_CH0 ); // The source address is incremented by 1 byte after each transfer. HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_0 ); // The destination address is constant - the T1 Compare 1. HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_0 ); //HAL_DMA_DSTINC_1 // The DMA transfer done is serviced by ISR in order to maintain full thruput. HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_DISABLE ); // Xfer all 8 bits of a byte xfer. HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS ); // DMA has highest priority for memory access. HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH); HAL_DMA_SET_LEN( ch, NUM_CAPTURES); HAL_DMA_SET_SOURCE(ch, 0x62A6); HAL_DMA_ARM_CH( T1CAP_DMA_CH ); HAL_DMA_CLEAR_IRQ( T1CAP_DMA_CH ); } void initFreqCapture() { P0DIR &= ~(1<<2); P0SEL |= (1<<2); P2DIR |= 0x2 << 6; uint8 cnt = 1; } double freqCapture() { // Intialize timer T1CTL = 0; T1CNTL = 0; T1CCTL0 = 0; // Reset Ch0 mode so we don't get spurious '0' DMA-copies on next iteration. T1STAT = ~(1 << 0); // Set up DMA to copy from T1CC0 to someplace. timerCaptureArmDMA(); DMAIRQ = ~(1<<2); // Set timer1 input capture T1CCTL0 = (0x01 << 0) | (1 << 6); // Capture type, IM=0 T1CTL = 1; while( 0 == (T1STAT & 1) ); firstCap = T1CC0L; // Get the first one directly. //Wait for X edges while( ( DMAIRQ & (1<<2) ) == 0); // Turn off timer T1CTL = 0; T1CNTL = 0; T1CCTL0 = 0; // Reset Ch0 mode so we don't get spurious '0' DMA-copies on next iteration. T1STAT = ~(1 << 0); // Calculate frequency lastCap = timerCapture; ticksAvg = (lastCap-firstCap)/NUM_CAPTURES; frequency = 32 / ticksAvg; asm("nop"); return frequency; }
I hope that helps. Unfortunately there are a few hard-coded values in there instead of defines, but you seem to have the hang of this.
Best regards,
Aslak