looking help on 8051 timer interrupt and switch input

Thread Starter

Parth786

Joined Jun 19, 2017
642
Again I ask, can you set breakpoints and step through the code in your sim? I believe the sim supports that kind of debugging if you know how to do it?
I was searching way to set breakpoints in proutes simulator. I will take time to understand to set breakpoints. as soon as possible I will try to set break point

Also, a quick look at the display output shows me:
You are getting 4 buttons reported so the get password routine is probably working (it got 4 of something).
You have at least a partial 'Try Again' message so the check password routine and test is probably working (3333 is not the password).
Why you are getting all of those '3's is probably because you haven't initialized the return value in CheckSwitches.
There are the some issues like when I press button "1" it doesn't display quickly on screen. any button number display after some specific delay time. during this time if I press any buttons it will show on screen but after that if I press any button it doesn't show on screen. so I think there is delay problem
 

JohnInTX

Joined Jun 26, 2012
4,787
Why you are getting all of those '3's is probably because you haven't initialized the return value in CheckSwitches.
Is this fixed?

Why does that routine have to return anything?
Need an answer on this.

Breakpoints are usually set by clicking in the source code window when you are preparing to run. When you run the code, it will stop at the breakpoint. You then can single-step the code through a routine to see how each step is working. You also can open a 'Watch' window (or whatever it's called) and specify variables to 'watch'. After each step, the watches will be updated and you can see how the data moves around in your program. Learning to use these tools is vital if you are going to go anywhere in embedded programming. Otherwise, when something does not work, you are left guessing..

Delays:
I don't see anywhere where you have determined how long a delay is for a count value. I would consider (again) using the Delay routine that is in the LCD code. It seems to be calibrated.
 
Last edited:

Thread Starter

Parth786

Joined Jun 19, 2017
642
Is this fixed?

Need an answer on this.

Breakpoints are usually set by clicking in the source code window when you are preparing to run. When you run the code, it will stop at the breakpoint. You then can single-step the code through a routine to see how each step is working. You also can open a 'Watch' window (or whatever it's called) and specify variables to 'watch'. After each step, the watches will be updated and you can see how the data moves around in your program. Learning to use these tools is vital if you are going to go anywhere in embedded programming. Otherwise, when something does not work, you are left guessing..
I was trying to set break point in proteus simulator I have checked this two video https://www.google.co.in/search?q=how+to+set+break+point+proutes+&ie=utf-8&oe=utf-8&client=firefox-b&gfe_rd=cr&dcr=0&ei=pO3DWfXRLeGK8QfWxLeYBw
but when I pause simulation. I don't see the source code so I just trying to address this problem
Is this fixed?
Delays:
I don't see anywhere where you have determined how long a delay is for a count value. I would consider (again) using the Delay routine that is in the LCD code. It seems to be calibrated.
OK I do some modification and try to fix issues and let you know
 

Thread Starter

Parth786

Joined Jun 19, 2017
642
Again I ask, can you set breakpoints and step through the code in your sim? I believe the sim supports that kind of debugging if you know how to do it?
I have done long search to know that weather my simulator set break point or not. I found that simulator support that type of debugging but it need .cof file but my compiler does not generate this file so that is reason I can't set break point in simulator. so I have two choice, either I choose another compiler or do test manually. means try with different type of approach until i get the success

I have seen program is working but there is only one problem. Input doesn't show on right time, on screen. so I think there is only problem with delay routine. I am still working on it. I am testing program with few changes. may be one of approch will work.

I know moving on another topic without completeing first one is bad thing but If you don't mind can we start with interrupt. flow chart is already made. I am just asking you will you continue with interrupt?

Note : still I am working on password project. once I get success I will let you know. I think I have learned lot from this project. I know some things left in program but belive me I will do it as soon as possible
 
Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
I know moving on another topic without completing first one is bad thing but If you don't mind can we start with interrupt. flow chart is already made. I am just asking you will you continue with interrupt?
Note : still I am working on password project. once I get success I will let you know. I think I have learned lot from this project. I know some things left in program but belive me I will do it as soon as possible
I think you should finish the password project first. You need to demonstrate that you can drill down into problems and fix them in a timely, organized manner AND acquire some debugging tools and skills on something you know before proceeding on to anything else. Otherwise, you will wind up in the same place with half-written code that you don't understand how to fix. I personally don't want to do that.

If you want, post what you have on the interrupt stuff including the project description and flow chart but let's finish one thing before going off into another - much harder thing.
 

cmartinez

Joined Jan 17, 2007
8,763
Parth, John is right. A very important part of people's education is not just knowing stuff, but rather developing one's sense of discipline. I strongly suggest you finish each step of your project first, and thoroughly give it its finishing touches, before moving on to the next stage.
That way you will also have a lot less debugging and testing to do when you assemble each component and routine at the very end.
 

Thread Starter

Parth786

Joined Jun 19, 2017
642
I think you should finish the password project first. You need to demonstrate that you can drill down into problems and fix them in a timely, organized manner AND acquire some debugging tools and skills on something you know before proceeding on to anything else. Otherwise, you will wind up in the same place with half-written code that you don't understand how to fix. I personally don't want to do that.
Parth, John is right. A very important part of people's education is not just knowing stuff, but rather developing one's sense of discipline. I strongly suggest you finish each step of your project first, and thoroughly give it its finishing touches, before moving on to the next stage.
That way you will also have a lot less debugging and testing to do when you assemble each component and routine at the very end.
OK I will follow your advice. I had some issues regarding compiler and simulator. I was trying to solve them one by one. so that's why I took so much time to reply.
I was learning how to set break point in source code. Look at below picture, this is one example of my effort. There are two red dots. These are the break points of program but I don't understand how does this break point will help me to solve problem in my original password project.
Do you want to continue with this thread?

upload_2017-9-26_21-43-31.png
Note: LED project shown in picture to learn use of break point with simple example
 
Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
Breakpoints allow you to stop the code at the selected point and then examine the various program variables to see if they are what you would expect from your design. Also, you can single-step the code from a breakpoint to trace the code flow and see that it goes where you expect it to go.

I haven't used your particular setup but the general procedure is the same for most:
To examine variables, you usually open a 'WATCH' window like the window on the lower right. Note the one called LOOP. As you hit that breakpoint over and over, you will see LOOP increment. Add variables to the watch window by clicking (or right-clicking maybe) the 'Name' column and type in the name.
A lot of times you can just mouse-over the variable when the execution is at a breakpoint and its value will pop up.

To step the code use the icons at the top of the upper right window. From left to right they are:
Run/Stop
Step Over - execute one line of code. If it is a function call, call the function and stop when the function ends - useful to step over delays or functions that you know are working
Step Into - execute one line of code. If it is a function call, enter the function and step through it line by line.
Step Out Of - when inside a function, this finishes up and exits without stepping through the rest of the code.
?
(I don't know what the red indicator is)

Stepping delays is tedious so once they are working, I would step over them.

The LED code doesn't have a lot of places to set a breakpoint without winding up in the delay routine. You might modify it by commenting out the delays then just stepping the while(1) loop. The LED indicator should turn on and off as you go round and round. You can also see the value of the SFR corresponding to P1, the LED port. Note that the Most Significant Bit is 0, that means that the LED is OFF. Clicking that little '+' sign should expand that SFR line into individual bits. Nice, yes?

In the password code:
A good use for breakpoints is in the wait for a switch routine. Set a breakpoint where you return the value. The code should run until you hit a button. Look at the return value in WATCH to see what it is.
Another use would be in the check switches routine. Set a breakpoint on one of the buttons. The code should run until the button is hit and then you can step the code to see how the return value is used. Step it and see how the value gets stored into the array and the array index gets incremented until the array is filled.
Step through check password and see how it compares the fixed password to the one entered on a character by character basis until it gets a mismatch or gets all the way through successfully.
Lots of possibilities - with practice, you'll know where to set the breakpoints, what to watch and how to step.

Load your other simple programs and step through them, too. Play around with it until you are comfortable. Any time spent on learning this tool will pay you back many times in the future!

A really good use for all of this is learning C. Write simple programs using the various constructs, compile them and step through them to see how they work, where the data goes etc.

For further info, use the HELP facility for your software or read the manual if you have one.

BTW: the Delay routine shown does NOT use the parameter passed when it is called so the time will be what you specify in the function call - how would you fix that?
 
Last edited:
helo folk!!!
You can try this code for resolve the problem micro controller 8051 time interrupt

C:
#include<reg51.h>
void cct_init(void);
void InitTimer0(void);


int main(void)
{
   cct_init();             // Make all ports zero
   InitTimer0();           // Start Timer0

   while(1)                // Rest is done in Timer0 interrupt
   {
   }
}

void cct_init(void)
{
    P0 = 0x00; 
    P1 = 0x00; 
    P2 = 0x00; 
    P3 = 0x00;
}


void InitTimer0(void)
{
    TMOD &= 0xF0;    // Clear 4bit field for timer0
    TMOD |= 0x02;    // Set timer0 in mode 2
 
    TH0 = 0x05;      // 250 usec reloading time
    TL0 = 0x05;      // First time value
 
    ET0 = 1;         // Enable Timer0 interrupts
    EA  = 1;         // Global interrupt enable
 
    TR0 = 1;         // Start Timer 0
}


void Timer0_ISR (void) interrupt 1   // It is called after every 250usec
{
    Out = ~Out;  // Toggle Out pin

    TF0 = 0;     // Clear the interrupt flag
}
Thank you
best regard for
shujat khan

(moderator's note: promotional link removed by moderator, posting such links can result in a ban)
 
Last edited by a moderator:

Thread Starter

Parth786

Joined Jun 19, 2017
642
Everything was fine but there was mistake in my delay routine. Now I have corrected my mistake. Now I am able to see what I want to do
upload_2017-9-28_11-45-31.png
Note: I couldn't capture screen shot of four number because delay time was very short.
 

JohnInTX

Joined Jun 26, 2012
4,787
Looks good. What was the problem?
Post the code so we can see how you did it.
FWIW, 'YOUR' is not used correctly. It should be you're, a contraction of 'you are'. But in this context, I would just say 'Welcome'. Spelling and grammar are important in a user interface. Don't feel bad, a depressingly high percent1age of native English speakers do not use 'your' correctly either.

Do those things then post the problem statement and flow chart for the interrupt stuff.
 

Thread Starter

Parth786

Joined Jun 19, 2017
642
Looks good. What was the problem?
Post the code so we can see how you did it.
FWIW, 'YOUR' is not used correctly. It should be you're, a contraction of 'you are'. But in this context, I would just say 'Welcome'. Spelling and grammar are important in a user interface. Don't feel bad, a depressingly high percent1age of native English speakers do not use 'your' correctly either.

Do those things then post the problem statement and flow chart for the interrupt stuff.
There was problem in my delay routine and had some other issues

upload_2017-9-28_19-40-32.png
This is working code
C:
#include <REG51.h>

/*Data pins connected to port P1 of 8051 */

#define  Data_Port_Pins  (P1)

#define Switch_Pressed  (1)
#define Switch_Not_Pressed  (0)

sbit  Switch_1 = P2^4;
sbit  Switch_2 = P3^0;
sbit  Switch_3 = P3^3;
sbit  Switch_4 = P3^7;

sbit  Register_Select_Pin  = P2^0;  /* Register Pin of LCD connected to Pin 0 of Port P2 */
sbit  Read_Write_Pin  = P2^1;  /* Read/Write Pin of LCD connected to Pin 1 of Port P2 */
sbit  Enable_Pin  = P2^2;  /* EN pin connected to pin 2 of port P2 */

/* Function for creating delay in milliseconds */
  void Debounce_time(unsigned int n)
     {
         unsigned y;
         for (y=0; y<n; y++);
    }

bit check_Switch_1(void)
    {
        if(Switch_1 == 0)                           /* Switch is pressed */
        {
              Debounce_time(22000);           /* wait 22 msec */
               if(Switch_1 == 0)                     /* check switch again */
                return Switch_Pressed;          /* switch is really pressed */
         }
                return Switch_Not_Pressed;
}
bit check_Switch_2(void)
{
        if(Switch_2 == 0)                             /* Switch is pressed */
        {
            Debounce_time(22000);             /* wait 22 msec */
            if(Switch_2 == 0)                        /* check switch again */
               return Switch_Pressed;           /* switch is really pressed */
  }
  return Switch_Not_Pressed;
}
bit check_Switch_3(void)
 {
         if(Switch_3 == 0)                            /* Switch is pressed */
          {
               Debounce_time(22000);            /* wait 22 msec */
               if(Switch_3 == 0)  /* check switch again */
                return Switch_Pressed;  /* switch is really pressed */
          }
                  return Switch_Not_Pressed;
}
bit check_Switch_4(void)
{
       if(Switch_4 == 0)                                   /* Switch is pressed */
       {
           Debounce_time(22000);                  /* wait 20 msec */
            if(Switch_4 == 0)                             /* check switch again */
           return Switch_Pressed;                    /* switch is really pressed */
         }
             return Switch_Not_Pressed;
}
/* check switches */
unsigned char Check_Switches(void)
  {
      unsigned char ReturnValue;
      ReturnValue = 0;
       if (check_Switch_1()== Switch_Pressed )
        {
             ReturnValue = '1' ;
        }
  else if (check_Switch_2()== Switch_Pressed)
       {
             ReturnValue = '2';
       }
  else if (check_Switch_3()== Switch_Pressed)
     {
            ReturnValue = '3';
      }
  else if (check_Switch_4()== Switch_Pressed)
     {
         ReturnValue = '4';
     }
       return ReturnValue;
  }
unsigned int wait_for_a_switch(void)
  {
    unsigned int Switch_Number = 0;                   /* start with 'no switch'*/
   while (Switch_Number == 0)                         
    {
       Switch_Number = Check_Switches();  /*and loop until you get some non zero value (switch pushed)*/
    }
      return Switch_Number;  /* then return that value */
}
  unsigned int wait_for_no_switches(void)
  {
      unsigned int Switch_Number = 0;  // start with 'no switch'
     while (Switch_Number != 0)
     {
        Switch_Number = Check_Switches();
     }
       return Switch_Number ;
 }
 
/* Function to send command instruction to LCD */
  void LCD_Command (unsigned char command)
   {
       Data_Port_Pins = command;
       Register_Select_Pin =0;
       Read_Write_Pin=0;
       Enable_Pin =1;
      Debounce_time(1000);
      Enable_Pin =0;
  }
  
/* Function to send display data to LCD */
  void LCD_Data (unsigned char Data)
   {
     Data_Port_Pins = Data;
     Register_Select_Pin=1;
     Read_Write_Pin=0;
     Enable_Pin =1;
     Debounce_time(2000);
     Enable_Pin =0;
  }
  
/* Function to prepare the LCD  and get it ready */
  void LCD_Initialization()
  {
     LCD_Command (0x38);
     LCD_Command (0x0e);
     LCD_Command (0x01);
     LCD_Command (0x81);
  }
    unsigned char password[4]={'4','3','1','2'};
    unsigned char input[4];
    void Get_Password (void)
{
    unsigned char index;
    for(index=0; index<4; index++)
  {
      wait_for_no_switches();
      input[index]=wait_for_a_switch();
      LCD_Data(input[index]);
  }
}
 bit Check_Password(void)
{
     unsigned char index;
     for(index=0; index<4; index++)
   {
    if(input[index] != password[index])           /* check each input character against the password chars */
       return 0;                                                /*return FALSE on the first mismatch */
  }
       return 1;                                                // it got through 4 matches so input matches password - return TRUE
}

/* Function to send string to LCD */
void LCD_String (unsigned char *string)
{
    int x=0;
     while(string[x]!='\0')
   {
     LCD_Data(string[x]);
     x++;
     Debounce_time(10000);
   }
   return;
}
void main(void)
{
/*initSYSTEM */
  unsigned char string1[]= "Enter Password";
  unsigned char string2[] =" YOU'RE WELCOME";
  unsigned char string3[] ="Try Again";

  LCD_Initialization();

   while(1)
  { 
    LCD_String (string1);
    LCD_Command (0xc0);
    Get_Password();
  
   if(Check_Password())                  /* returns TRUE if password and input matches - show result */
  { 
      LCD_Command (0x01);
       LCD_String (string2);
   }
           
  else
  {
       LCD_Command (0x01);
       LCD_String (string3);
       Debounce_time(40000);
       LCD_Command (0x01);
   }
     Debounce_time(100);  /* wait to display result message,  */
  }

}
 

Thread Starter

Parth786

Joined Jun 19, 2017
642
Do those things then post the problem statement and flow chart for the interrupt stuff.
I have made this flow chart for timer interrupt

upload_2017-9-28_19-45-39.png

Suppose counter is 3 bit. it man it can count value from 0 to 7 number

count : 0-1-2-3-4-5-6-7

High value = 5 Number
Low value = 3 number

When timer start to count, means it will count from number 3 up to number 5 . after that it become over flow means again counter will count from zero. does it means the time taken by ISR from number 3 up to number 5 is interrupt time

Note : This is just small example for better understanding. I understand 8051 has 16 bit counter
 
Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
OK! On to the interrupts. So first, what is it supposed to do?

And let's use the real 8051 timer. I don't want to spend time on hypothetical hardware that isn't like any real hardware.

To compute the timer settings you will need to know
1) the interrupt period (time between interrupts)
2) which timer you want to use
3) the basic input frequency to the timer. In a standard 8051, I think that is Fosc/12.
From those values you can calculate how many timer ticks there are between interrupts and from that, what to set the timer to on each interrupt.
 
Last edited:

Thread Starter

Parth786

Joined Jun 19, 2017
642
OK! On to the interrupts. So first, what is it supposed to do?
When interrupt occur, then tells the processor to stop what it is doing, and handle a task first. After the interrupt i, the processor goes back to whatever it was doing before. and timers are used to generate time delays

And let's use the real 8051 timer. I don't want to spend time on hypothetical hardware that isn't like any real hardware.

To compute the timer settings you will need to know
1) the interrupt period (time between interrupts)
2) which timer you want to use
3) the basic input frequency to the timer. In a standard 8051, I think that is Fosc/12.
From those values you can calculate how many timer ticks there are between interrupts and from that, what to set the timer to on each interrupt.
One timer tick take = 1.085uS
Total count by 16 bit counter = 65,536 ticks

Timer ticks * 1.085uS = Desired time

Suppose I need 40 ms delay

40ms = 40,000 uS
Timer ticks = 40,000/1.085 = 36, 866
assume its high value of counter
Than low value = 65,535-36,866 = 28, 669

interrupt period = 40 ms
TH0 = 36,866
TL0 = 28,669
Does this value give 40 ms delay ?
 
Last edited:

cmartinez

Joined Jan 17, 2007
8,763
When interrupt occur, then tells the processor to stop what it is doing, and handle a task first. After the interrupt i, the processor goes back to whatever it was doing before. and timers are used to generate time delays


One timer tick take = 1.085uS
Total count by 16 bit counter = 65,536 ticks

Timer ticks * 1.085uS = Desired time

Suppose I need 40 ms delay

40ms = 40,000 uS
Timer ticks = 40,000/1.085 = 36, 866
assume its high value of counter
Than low value = 65,535-36,866 = 28, 669

interrupt period = 40 ms
TH0 = 36,866
TL0 = 28,669
Does this value give 40 ms delay ?
Neither TH0 nor TL0 can be greater than 255. Total timing in cycles is determined by 256*TH0 + TL0
 

JohnInTX

Joined Jun 26, 2012
4,787
When interrupt occur, then tells the processor to stop what it is doing, and handle a task first. After the interrupt i, the processor goes back to whatever it was doing before. and timers are used to generate time delays
Parth, I know what an interrupt is - I want to know what this program is supposed to do. Flash an LED? If so at what rate?

@cmartinez is correct in pointing out that you can't cram a 16 bit number like 28669 into an 8 bit register. Plus, I don't think your understanding of the timer is correct. It does not count between two different values (like your 3 to 5 example). It simply counts up to FFFFh (in MODE 1, 16 bits counter) and interrupts when it rolls over from FFFFh ->0000h. It will count from there. If you don't want the full 65536 counts between interrupts, that's when you reload the timer to some intermediate value.

In your example, you correctly subtract the number of counts from 65335 but you only use the result, not both numbers. The result is 28669. Converting to hex is 6FFDh. So TH0 is loaded to 6fh and TLo is loaded to FDh on init and each interrupt.

EDIT: Those values will cause an interrupt roughly every 40ms. The max time in MODE1 (16bits) is about 71.1ms.

But.. why reload at all? Timer MODE2 counts TL0 up, interrupts when it overflows FF->00 then reloads TL0 with the value in TH0 automatically. That's how I would do it...
 
Last edited:
Top