Having dug around a lot on the net, I see that lots of people discourage using frame error to detect the long break.
So I am trying my own code, where a High to Low transition on RB2 triggers an interrupt.
In the interrupt it resets timer1, and then sets a edge flag, it also changes the interrupt edge detection for the next part to trigger an interrupt on low to high.
Then when the interrupt occurs, it reads off the timer1. If it is a low time, then ignore it because it is probably a bit. If it is longer than 128 Cycles in the timer, then it is most likely the 176ms break. In which case it sets a flag for the long break detection, and drops out of the ISR.
My main loop then keeps on polling this flag. As soon as the flag goes high, it is supposed to start reading from the USART.
I have a problem when, If I enable Timer1's T1_SOURCE_INT, it stops my program from ever going into the ISR (Even though I do not even have Interrupts enabled for Timer1)
Any clues.....
Thanks for all your help
/*
* File: DMXRecv.c
* Author: Peter
*
* Created on 09 August 2014, 17:26
*/
/** C O N F I G U R A T I O N B I T S ******************************/
#pragma config OSC = INTIO67, FCMEN = OFF, IESO = OFF // CONFIG1H
#pragma config PWRT = OFF, BOREN = OFF //,BORV = 30 // CONFIG2L
#pragma config WDT = OFF, WDTPS = 32768 // CONFIG2H
#pragma config MCLRE = ON, LPT1OSC = OFF, PBADEN = OFF, CCP2MX = PORTB // CONFIG3H
#pragma config STVREN = ON, LVP = OFF, XINST = OFF // CONFIG4L
#pragma config CP0 = OFF, CP1 = OFF //, CP2 = OFF, CP3 = OFF // CONFIG5L
#pragma config CPB = OFF, CPD = OFF // CONFIG5H
#pragma config WRT0 = OFF, WRT1 = OFF//, WRT2 = OFF, WRT3 = OFF // CONFIG6L
#pragma config WRTB = OFF, WRTC = OFF, WRTD = OFF // CONFIG6H
#pragma config EBTR0 = OFF, EBTR1 = OFF//, EBTR2 = OFF, EBTR3 = OFF // CONFIG7L
#pragma config EBTRB = OFF // CONFIG7H
/** I N C L U D E S **************************************************/
#include <timers.h>
#include <string.h>
#include <usart.h>
#include <pwm.h>
#include <stdio.h>
#include <stdlib.h>
#include <delays.h>
#include "xlcd.h"
#include <portb.h>
/*
*
*/
/** PROTOTYPES *****************************************************/
void setup_usart(void); // setup baud rate etc. of USART
void setup_pwm(void); // setup pwm etc
/* declare statically allocated uinitialized variables *********/
#pragma udata
char RXbuffer[64];
char DataVal = 0;
int slot = 0;
int channel = 1;
int brkfl;
unsigned int t1val;
char at1val;
int lbflag; //THIS FLAG SAYS THERE IS A LONG BREAK, SO START USART
char chanval;
/* Declare executable instructions ****************************/
//#pragma code
// Delays for XLCD.h
void DelayFor18TCY( void ) { Delay1KTCYx(12); }
void DelayPORXLCD( void ) { Delay10KTCYx(100); }
void DelayXLCD( void ) { Delay1KTCYx(11); }
void reset (void) { //This Routine will reset the uC
_asm reset _endasm
}
void high_interrupt (void); /* prototype needed for 'goto' below */
#pragma code HIGH_INTERRUPT_VECTOR = 0x8
void high_ISR (void)
{
_asm
goto high_interrupt
_endasm
}
#pragma code /* allow the linker to locate the remaining code */
#pragma interrupt high_interrupt
void high_interrupt (void) {
putrsXLCD ("Abcd ");
if (INTCON3bits.INT2IF==1) {
putrsXLCD("B ");
if (brkfl==0) { //THIS WAS A HIGH TO LOW
WriteTimer1(0); //RESET THE TIMER
putrsXLCD("C ");
INTCON2bits.INTEDG2=1; //Change to rising edge
PORTB=PORTB; //Clear Mismatch
brkfl=1; //Change the Flag so we know next step
};
if (brkfl==1) { //THIS WAS A LOW TO HIGH
putrsXLCD("P ");
t1val=ReadTimer1();
INTCON2bits.INTEDG2=0; //Change to falling edge detection
PORTB=PORTB; //Clear Mismatch
brkfl=0;
while(BusyXLCD()); //Wait for LCD
itoa(t1val,at1val); // Convert to Ascii
putsXLCD(at1val);
putrsXLCD(" ");
if (t1val>=128) {
//THIS IS A LONG BREAK, SO WE CAN START THE USART
lbflag=1;
//putsXLCD(at1val);
putrsXLCD("D ");
while(1);
};
};
};
INTCON3bits.INT2IF=0; //ByeByeFlag
INTCON3bits.INT1IF =0; //Re-en``able all interrupts
}
void EnableHighInterrupts (void)
{
RCONbits.IPEN = 1; /* enable interrupt priority levels */
INTCONbits.GIEH = 1; /* enable all high priority interrupts */
}
#pragma interrupt low_interrupt
void low_interrupt (void) {
WriteCmdXLCD ((0x80+0x42));
putrsXLCD("HEY A LOW");
// INTCON3bits.INT1IF =0; //Re-enable all interrupts
while(1);
}
void EnableLowInterrupts (void)
{
RCONbits.IPEN = 1; /* enable interrupt priority levels */
INTCONbits.GIEL = 1; /* enable all high priority interrupts */
}
void main(void) {
// set internal oscillator to 16MHz
OSCCON = 0x60; // IRCFx = 110 MAKES CLOCK 4MHZ
OSCTUNEbits.PLLEN = 1; // x4 PLL MAKES CLOCK 16MHZ
LATA=0x00;
LATB=0x00;
LATC=0x00;
TRISA=0x00; // 0=OUT, 1=IN
TRISB=0x00;//&0x04; // O=OUT, 1=IN
TRISB=0xFF;
TRISC=0xFF; // O=OUT, 1=IN
//INITIALISE THE LCD
// while( BusyXLCD() );
OpenXLCD( FOUR_BIT & LINES_5X7);
WriteCmdXLCD( BLINK_OFF & CURSOR_OFF);
WriteCmdXLCD( SHIFT_DISP_LEFT );
// while ( BusyXLCD());
//BANNER
putrsXLCD("DMX Buddy v1.1 ");
OpenTimer1( TIMER_INT_OFF &
T1_8BIT_RW &
T1_SOURCE_INT &
T1_PS_1_8 &
T1_OSC1EN_OFF &
T1_SYNC_EXT_OFF );
PIE1bits.TMR1IE=0;
IPR1bits.TMR1IP=0;
// setup_usart();
//SETUP PORT RB2 FOR HIGH TO LOW FOR BREAK DETECTION
//CAUSES INTERRUPT
brkfl=0;
OpenRB2INT( PORTB_CHANGE_INT_ON & FALLING_EDGE_INT & PORTB_PULLUPS_ON);
// RCONbits.IPEN = 0; // priority
INTCONbits.GIE = 1; // enable interrupt
INTCONbits.RBIE = 1; // interrupt portB on
EnableHighInterrupts;
EnableLowInterrupts;
while(1) { //MAIN LOOP
if (lbflag==1) { //Long Break Detected. Start the USART Receing
lbflag=0;
putrsXLCD("pwpwpwpwpwpwpw");
ReadUSART(); //Clear any errors
/* Receive 512 bytes of data */
for (slot=0; slot<64; slot++)
{
// if (RCSTAbits.FERR == 1) break; // check for framing error
while (!DataRdyUSART()); // wait for data to be available
RXbuffer[slot] = ReadUSART(); // read and copy data to RXbuffer
}
itoa((RXbuffer[5]),chanval);
putsXLCD(at1val);
putrsXLCD("- -");
};
};
}
void setup_usart(void) // Set USART to transmit @ 250KB
{
OpenUSART( USART_TX_INT_OFF & // disable TX interrupt
USART_RX_INT_OFF & // enable RX interrupt
USART_ASYNCH_MODE & // set asynchronous mode
USART_NINE_BIT & // set 9-bit data mode
USART_CONT_RX & // set port continues RX
USART_BRGH_HIGH, 15); // uses high speed formula, 250KBd
BAUDCONbits.BRG16 = 1; // set 16 bit async mode
}