Digital Clock using pic18f8680, counters, external clocks

Collapse
X
 
  • Time
  • Show
Clear All
new posts
  • sljackson36
    New Member
    • Feb 2014
    • 1

    #1

    Digital Clock using pic18f8680, counters, external clocks

    I am trying to design a program that uses a 1 Hz external clock to create a digital clock. The clock must display the hours and minutes in this format, HH:MM, using the 24 hour military format. I have to assume the output is four 7-Segment displays. I have to use a counter to cause an interrupt every 60 seconds, I need to provide a C programming solution to provide the output in BCD. This is what I have so far:

    Code:
    #include <pic18f8680.h>
    #include <timers.h>
    void int0_ISR (void);
    static unsigned char count;
    
    #pragma code high_vector = 0x08
    void high_interrupt (void)
    {
              _asm
              goto int0_ISR
              _endasm
    }
    
    #pragma interrupt int0_ISR
    void int0_ISR (void)
    {
          if (INTCONbits.INT0IF)  // verify interrupt caused by 
                                  // INT0
          { 
                INTCONbits.INT0IF = 0; // clear INT0 flag
                count++;
                PORTD = ~count; // display INT0 interrupt count 
                                // on LEDs
          }
    }
    
    #pragma code
    
    void main (void)
    {
           count          = 0; // initialize count
           TRISD          = 0; // configure PORTD for output
           PORTD          = 0xFF; // turn off all LEDs
           RCON           = 0x80; // enable priority interrupts
           INTCON         = 0xD0; //
    I can't figure out how to get the format to HH:MM in 24 hour format or use a counter to cause an interrupt every 60 seconds, or any thing else, I don't even know if I have the correct code so far, I don't understand C language or assembly language for the pic18f8680 , I am having a hard time trying to understand both. Can someone pls help
    Last edited by Banfa; Feb 5 '14, 09:24 AM. Reason: Please put code inside [code]...[/code] tags
  • Banfa
    Recognized Expert Expert
    • Feb 2006
    • 9067

    #2
    OK do you have the datasheet? If not get it, it is available here on the Microchip website. This tells you everything you need to know about the processors capabilities and how to access them through software and what external hardware to use.

    It gives you details of the registers that are used to configure each peripheral device including the memory location of the registers and what each bit in each register does.

    A register in a device like this is just a memory location that is used to access a device, you get control registers that you write to in order to configure a peripheral device and data registers that some devices will have that allow you to read/write data from/to a peripheral device (such as a serial port).

    So to get a clock going you are going to need to
    1. Configure one of the chips on board timers.
    2. Configure the interrupts to receive the interrupt from the timer
    3. Implement and interrupt routine to handle the timer interrupt


    The microprocessor you have is way over spec'd for the job you are doing so there will be a lot of registers and peripheral devices that you just don't use. However you are driving 4 7 segment displays which will require 28 outputs and possibly a blinking : ? Which would require an extra one for 29. That's OK you have 9 IO ports or 69 available IO pins, however the number of pins on the physical package is 80 and because of this limitation a lot of pins have multiple functions so you need to choose IO ports that do not use the pins of other peripherals you wish to use.

    The chip has 4 timers and you need to choose the best one for your purposes, however Timer0 is the simplest. It can run in 8 or 16 bit counter mode with a prescaler of 2 to the power n where n is 1 - 8. It outputs an interrupt when its counter wraps from max value to 0.

    This means that you can get a timer interrupt frequency of various powers of 2 between <INPUT CLOCK>/512 to <INPUT CLOCK>/16777216. 1 minute, 60 seconds is not likely to be a reasonable power of 2 scaler of your input clock frequecy so trying to set-up a 1 minute timer is likely to lead to a very inaccurate clock.

    Let's say that you using a 2.048MHz crystal as your clock source (useful since it is a power of 2). If we use the 8 bit counter with a prescaler of 256 then the frequency of your interrupts will be (2.048MHz / 256) / 256 = 31.25 Hz, or 1/31.25 * 1000 = 32 millisecond tick. This is good because it is a whole number, no need to try and take account of fractions to keep your clock ticking accurately.

    So you count milliseconds, every-time you get an interrupt you add 32 to your millisecond count and if it gets above 1000 you take off 1000 and add 1 to your second count. When your second count gets to 60 your zero it and add 1 to your minute count and update the display.

    You can adjust the timer to get a slower tick frequency if you want but what you can not do is accurately get a 1 minute tick, try to do that and you will be dropping fractions of a second all over the place and slowly drifting away from real time.


    Anyway start by getting the data sheet, skim the whole thing then read in detail the parts that are relevant to your design. You should need to do very little (if any) assembler, C is not too hard a language to pick up.

    Just be sure that you do not try to access your data from 1 (or more) interrupts and a main loop at the same time, that way lies chaos.

    Comment

    Working...