CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to CCS Technical Support

ideas on how to interrupt my program

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
madtoilet



Joined: 02 Apr 2008
Posts: 36

View user's profile Send private message

ideas on how to interrupt my program
PostPosted: Tue Apr 29, 2008 1:42 pm     Reply with quote

The following is my code. I've removed the whole checking of the keypad routine because it was quite long.

Anyway, during the my_get_string function, i'd like to be able to interrupt it so that it will break out of that function. This interrupt has to come from my keypad. My keypad which are along ports B and C. I've not used interrupts before. Anyone have any ideas on how i could do this?

Code:
//#include "18f452.h
#include "D:\Program Files\PICC\Devices\LCD.h"
#include "string.h"
#fuses HS,NOWDT,NOPROTECT, NOLVP
#use delay(clock=4mhz)
//#use rs232(baud=4800, bits=8, parity=N, stop=1, xmit=PIN_C6, rcv=PIN_C7,/* stream=GSM,*/ ERRORS)
//int receiver1 = 0;
//int i=0;
#define delay_min delay_ms(120000)


int  screen_number=1;
//int  cursor=0;
void int_LCD(void);
void Check_Keys(void);
void out_LCD(int i);
void key_table(char *array, int columns_value, int row);
void clear(void);
//void arrows(int columns_value);
void out_LCD_string(char *string);
//void menu(void);
void screen(void);
void cursor_position(int position);
void altus_fortis_init(void);
void menu(void);
void stdmode(void);
void my_get_string(void);
void disp_rmc_long(void);
void disp_rmc_lat(void);
void valid_check(void);
void gsm_call(void);
void gsm_power(void);

int  counter = 0;         //keep track of the number enter for aisle
//int  menu_or_clear=0;
//char gpstring[96];
//char input_str[STRING_SIZE];
char aisle_number[]="000";
char array1[]="147";
char array2[]="258";
char array3[]="369";
char array4[]="abc";
char resetmode[]="2. Reset Mode";
char standardmode[]="1. Standard Mode";
char forcemode[]="3. Force Mode";
char poweroff[]="4. Power On/Off ";
char intro[]="Altus Fortis inc.";
char intro2[]="KabTrak Beta";
char intro3[]="Ver. 1.03";
char initial[]="Initializing...";
char reseting[]="Reseting...";
char gsm_on_off[]="GSM Power On/Off";
byte num[] ="4153851526";

/*char zero[]="0";
char one[]="1";
char two[]="2";
char three[]="3";
char four[]="4";
char five[]="5";
char six[]="6";
char seven[]="7";
char eight[]="8";
char nine[]="9";
char up[]="up";
char down[]="down";
char second[]="second";
char enterr[]="enter";*/
//char []="clear";
//char help[]="help";
char error[]="error";
char ok[]="ok";
unsigned char rmc[70];

void main()
{
int   k=0;

   setup_adc_ports(NO_ANALOGS);
   setup_adc(ADC_OFF);
   setup_psp(PSP_DISABLED);
   setup_spi(FALSE);
   setup_wdt(WDT_OFF);
   setup_timer_0(RTCC_INTERNAL);
   setup_timer_1(T1_DISABLED);
   setup_timer_2(T2_DISABLED,0,1);
   setup_oscillator(False);
  // my_get_string();

   delay_ms(100);

   int_LCD();
   delay_ms(100);
   altus_fortis_init();
   delay_ms(30);
   menu();



here:
     Check_Keys();
    delay_ms(75);

goto here;
}



void my_get_string(void) {
#use rs232(baud=4800, bits=8, parity=N, stop=1, xmit=PIN_C6, rcv=PIN_C7, ERRORS)
  char c;
  int i=4;
  int count=0;
  int reprep=45;
  unsigned char temp[68]="$GPR";
  int v;

output_low(PIN_C4);
output_low(PIN_C5);
delay_ms(500);
output_low(PIN_B7);
delay_ms(500);
start:
while(reprep != 0){

c = getc();
if(c == '$')
{
   output_high(PIN_B7);
   output_low(PIN_B7);
   c = getc();
      if(c == 'G'){
        //  output_low(PIN_B7);
          output_high(PIN_B7);
          //output_low(PIN_B7);
          c = getc();
             if (c == 'P'){
                  c = getc();
                  if (c == 'R'){
                     output_high(PIN_B7);
                           while(count < 55){
                              temp[i]= getc();
                              i++;
                              count++;
                              }

        goto ending;

             }
        }
   }
}


goto start;

ending:
temp[i] = 0;
cursor_position(0x81);
//out_lcd_string(temp);
delay_ms(2000);

strcpy(rmc, temp);
delay_ms(200);
disp_rmc_lat();
delay_ms(10);
disp_rmc_long();
delay_ms(500);
valid_check();
reprep--;
}

gsm_call();
}

void disp_rmc_lat(void)
{
int i=0;

int j=16;//27
int h=5;
char temp1[70];
char lattitude[20]="Lat:    ";


strcpy(temp1, rmc);


for(i=0; i< 11; i++){
lattitude[h]= temp1[j];
j++;
h++;

}

lattitude[h] = 0;
cursor_position(0x80);
out_lcd_string(lattitude);

}

void disp_rmc_long(void)
{
int l=5;
int k=28;
int i=0;
char temp1[70];
char longitude[20]="Lon:    ";

strcpy(temp1,rmc);

for(i=0;i < 12; i++){
longitude[l]= temp1[k];
k++;
l++;
}

longitude[l]=0;
cursor_position(0xC0);
out_lcd_string(longitude);


}

void valid_check(void)
{

char temp[70];
char check[2];
char invalid[]="Status: Invalid";
char valid[]="Status: Valid";

strcpy(temp, rmc);

check[0] = temp[14];

if(check[0]=='V'){
cursor_position(0x94);
out_lcd_string(invalid);

}

else if (check[0] == 'A'){
cursor_position(0x94);
out_lcd_string(valid);
}
}


void gsm_call(void)
{
#use rs232(baud=4800, bits=8, parity=N, stop=1, xmit=PIN_C6, rcv=PIN_C7, stream=GSM, ERRORS)
char c;

output_high(PIN_B5);
delay_ms(800);
output_low(PIN_C4);
output_high(PIN_C5);
delay_ms(500);


fprintf(GSM, "AT+CMGF=1\r\n");
delay_ms(2050);
fprintf(GSM,"AT+CMGS=\"%s\"\r\n",num);
delay_ms(2000);
fprintf(GSM, "%s", rmc);
fputc(0x1A,GSM);
delay_ms(3000);
output_low(PIN_B5);
//delay_min;
}

void gsm_power(void)
{
out_lcd_string(gsm_on_off);
output_low(PIN_B6);
delay_ms(10);
output_high(PIN_B6);
delay_ms(2000);
output_low(PIN_B6);

delay_ms(10);
}
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Tue Apr 29, 2008 5:06 pm     Reply with quote

Change the design of your program. Get rid of the my_get_string()
function, and use an interrupt-driven method to receive the messages.

Use #int_rda to get each character. Inside the int_rda routine, look
for your header bytes. When you get them, set a flag which indicates
that you are receiving a message. Then as each byte is received,
put it into a message buffer. When the End of Message byte is received,
set a global flag byte = True. In main(), there will be a loop which
checks this byte. If it's true, then do something with the message
(copy it to another buffer) and set the flag to False.

You should only get one character per pass through the #int_rda
routine. Do not sit in the int_rda routine and call getc() repeatedly. That
will defeat the purpose of the interrupt-driven program design. Also,
make sure you don't start receiving a new message inside the #int_rda
routine until the existing message (if any) has been handled by code in
main(). Check the flag inside the #int_rda routine to test for this.

I found an example of this. See the #int_rda routine in this post.
http://www.ccsinfo.com/forum/viewtopic.php?t=30539
I haven't tested this code.
Douglas Kennedy



Joined: 07 Sep 2003
Posts: 755
Location: Florida

View user's profile Send private message AIM Address

PostPosted: Wed Apr 30, 2008 11:43 am     Reply with quote

You would do well to follow PCM programmers advice. Throwing a fair bit of code at the wall and hoping it will stick is not working well for you. Search the forum and also look at the CCS examples. Get them to work and understand why they work before adding any code of your own. Try especially to understand the examples about interrupt service routines. Start with just a few dozen lines prove each example snippet works in a stand alone program. Only then try to combine them. If the combined functions work then carefully add you own code assuming that if it doesn't work then it was the last couple of lines of your own code that did it. I may be wrong but when you post several dozen lines of code you hoped would stick to the wall then few will want to go into the weeds and find where you lost your way. Most find their own mistakes and those errors that are harder to find have a high chance of already being posted by others that's why searching this board is useful. PCM programmer was gracious enough to provide a link for you in the way of encouragement. The situation that happens the least often is a new to almost everyone type issue. When code is posted that allows the rare issue to be reproduced by others this board lights up.
madtoilet



Joined: 02 Apr 2008
Posts: 36

View user's profile Send private message

PostPosted: Fri May 02, 2008 2:48 pm     Reply with quote

i'm trying to understand how interrupts work. I've used a number of examples from the forums as well as the example from CCS. I've simplified my code down to:

Code:
#include "G:\Senior Project\base2\base2.h"
  #include <string.h>
  #include <stdio.h>
#include <stdlib.h>


#define BUFFER_SIZE 80
BYTE inStr[BUFFER_SIZE];
BYTE next_in = 0;
BYTE next_out = 32;
int index=0;
int1 sentence = FALSE;
BYTE char_rcvd;

#int_rda
void serial_isr() {
   int i=0;

   sentence = TRUE;
   char_rcvd = fgetc(GSM);
   for(i=0; i <5; i++)
     {
         inStr[i] = char_rcvd;
   }
   output_b(char_rcvd);  //shows the received character
   delay_ms(50);  //for troubleshooting purposes
}
void receive_text(void);


void main()
{

   setup_adc_ports(NO_ANALOGS|VSS_VDD);
   setup_adc(ADC_OFF);
   setup_psp(PSP_DISABLED);
   setup_spi(FALSE);
   setup_wdt(WDT_OFF);
   setup_timer_0(RTCC_INTERNAL);
   setup_timer_1(T1_DISABLED);
   setup_timer_2(T2_DISABLED,0,1);
   setup_timer_3(T3_DISABLED|T3_DIV_BY_1);
   setup_comparator(NC_NC_NC_NC);
   setup_vref(FALSE);
   enable_interrupts(int_rda);
   enable_interrupts(global);
   setup_low_volt_detect(FALSE);
   setup_oscillator(False);
output_b(0x00);
output_low(PIN_D1);
delay_ms(500);
output_high(PIN_D1);
delay_ms(2000);
output_low(PIN_D1);
output_low(PIN_D1);
delay_ms(15000);
receive_text();


}

void receive_text(void)
{

char ch;
int count=1;
int count2=10;
int count3=0;
int i=0;
int b;

fprintf(GSM,"AT");
fprintf(GSM,"\r\n");

output_b(0xFF);

//program doesn't seem to be able to arrive at this point
output_b(inStr[0]);
delay_ms(1000);
output_b(inStr[1]);
delay_ms(1000);

output_b(inStr[2]);
delay_ms(1000);

output_b(inStr[3]);
delay_ms(1000);

output_b(inStr[4]);
delay_ms(1000);

}


the AT command is the best way i can get a character to be sent to my serial port. I'm still trying to understand how the interrupt works and how the get it to work with my main program. In this program, if i examine the LED lights during the interrupt, i can see that i get the characters. However, those characters don't get saved into my inStr like i want because when i try to display those on my LEDs i get nothing. Is this because it's taking garbage characters too early or because the program isn't resuming after the interrupt?

the header is as follows.

Code:
#include <18F4550.h>
#device adc=8

#FUSES NOWDT                    //No Watch Dog Timer
#FUSES WDT128                   //Watch Dog Timer uses 1:128 Postscale
#FUSES HS                       //Crystal osc <= 4mhz
#FUSES NOPROTECT                //Code not protected from reading
#FUSES BROWNOUT_NOSL            //Brownout enabled during operation, disabled during SLEEP
#FUSES BROWNOUT                 //Reset when brownout detected
#FUSES BORV46                   //Brownout reset at 4.6V
#FUSES NOPUT                    //No Power Up Timer
#FUSES NOCPD                    //No EE protection
#FUSES STVREN                   //Stack full/underflow will cause reset
#FUSES NODEBUG                  //No Debug mode for ICD
#FUSES NOLVP                      //Low Voltage Programming on B3(PIC16) or B5(PIC18)
#FUSES NOWRT                    //Program memory not write protected
#FUSES NOWRTD                   //Data EEPROM not write protected
#FUSES IESO                     //Internal External Switch Over mode enabled
#FUSES FCMEN                    //Fail-safe clock monitor enabled
#FUSES PBADEN                   //PORTB pins are configured as analog input channels on RESET
#FUSES NOWRTC                   //configuration not registers write protected
#FUSES NOWRTB                   //Boot block not write protected
#FUSES NOEBTR                   //Memory not protected from table reads
#FUSES NOEBTRB                  //Boot block not protected from table reads
#FUSES NOCPB                    //No Boot Block code protection
#FUSES MCLR                     //Master Clear pin enabled
#FUSES LPT1OSC                  //Timer1 configured for low-power operation
#FUSES NOXINST                  //Extended set extension and Indexed Addressing mode disabled (Legacy mode)
#FUSES PLL1                     //No PLL PreScaler

#use delay(clock=4000000)
#use rs232(baud=4800,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=8, stream=GSM, ERRORS)


i know i've been going at this same topic for awhile but i'm still trying to grasp it. I've looked at topics on this and i still haven't quite gotten a good understanding of what's happening.
Douglas Kennedy



Joined: 07 Sep 2003
Posts: 755
Location: Florida

View user's profile Send private message AIM Address

PostPosted: Sat May 03, 2008 12:42 pm     Reply with quote

Quote:
#include "G:\Senior Project\base2\base2.h"

Do you have an instructor that can help you? If not then look again at the CCS examples especially the circular buffer example. Don't add any of you own code. See if you can get it to work with your PIC set up. Use the MPLAB simulator and step through it till you gain an understanding. Know that if you have an instructor he/she is being paid to transfer knowledge to you so ask questions.
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group