/******************************************************************************
ZeroJitter.c Generates zero-error and zero jitter interrupt period.
Open-source - 21 Nov 2009 - www.RomanBlack.com/one_sec.htm
PIC 12F675, 4MHz xtal.
This is like my zero-error 1 second timing system, that uses a convenient
constant to set ANY period (with 1 timer tick resolution).
However this system has zero jitter!
Can be used to generate 1 second period, or 50Hz freq output etc.
******************************************************************************/
// PERIOD sets the pin toggle freq; toggle PERIOD = (xtal / 4 / freq / 2)
#define PERIOD 10000 // (xtal 4Mhz) TMR0 1MHz, 10000 = 100Hz toggle (50Hz output)
#define PER_COUNTS ((PERIOD / 100) - 1) // don't edit this!
#define PER_REMAINDER (PERIOD - (PER_COUNTS * 100)) // don't edit this!
unsigned int pcount; // used in interrupt to count PER_COUNTS
//-----------------------------------------------------------------------------
//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
void interrupt()
{
//-----------------------------------------------------
// this is the TMR0 overflow interrupt.
// Note! TMR0 has a 3 tick write latency, writes must be -3
//-----------------------------------------------------
// check if time to toggle the output pin
if(!pcount)
{
asm {
movlw 0x01 ; // mask for pin 0
xorwf GPIO,f ; // toggle PIC pin GPIO.0
}
pcount = (PER_COUNTS+1); // how many delays to make total
TMR0 -= (PER_REMAINDER-3); // first delay will be ==remainder
}
// else make a normal delay
else
{
TMR0 -= (100-3); // make another 100 tick delay
}
pcount--;
//-----------------------------------------------------
// clear the TMR0 overflow flag and exit
INTCON.T0IF = 0;
}
//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
//=============================================================================
// MAIN
//=============================================================================
void main ()
{
//-----------------------------------------------------
// PIC 12F675 setup ports
ANSEL = 0; // ADC off
CMCON = 0x07; // comparators off
GPIO = 0b00000000; // clear GPIO
TRISIO = 0b00000000; // All outputs
WPU = 0b00000000; // pin pullups; 1 = pullup on (for button)
//-----------------------------------------------------
// timer setup etc
OPTION_REG = 0b00001000; // TMR0 on, 1:1 prescale
pcount = 0;
INTCON = 0b10100000; // GIE on, T0IE on (turn interrupt on)
//-----------------------------------------------------
// main run loop here
while(1)
{
continue; // loop and do nothing, just let the interrupt happen
}
}
//-----------------------------------------------------------------------------