Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronic Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

Register Log in

How can I get 200 ns or more delay?

Status
Not open for further replies.

amitdandyan

Newbie level 6
Joined
May 8, 2009
Messages
14
Helped
0
Reputation
0
Reaction score
0
Trophy points
1,281
Activity points
1,396
Timer 0 Help needed

I am using PIC18F252 with 20MHz crystal, I have tried to use the following program to get the delay(ON/OFF time of LED) minimum i.e. 200ns, but the delay I am getting is 5ms.

Please let me know what is the mistake in my program.

unsigned cnt;

void interrupt() {
cnt++; // Increment value of cnt on every interrupt
TMR0L = 96;
INTCON = 0x20; // Set T0IE, clear T0IF
}

void main() {
ADCON1 = 0x0F; // Set AN pins to Digital I/O
T0CON = 0xC4; // Set TMR0 in 8bit mode, assign prescaler(1/32) to TMR0
TRISB = 0; // PORTB is output
PORTB = 0x00; // Initialize PORTB
TMR0L = 96; // Timer0 initial value
INTCON = 0xA0; // Enable TMRO interrupt, TMR0 Overflow Interrupt Enable bit(bit 5)
cnt = 0; // Initialize cnt

do {
if (cnt == 1) {
PORTB = ~PORTB; // Toggle PORTB LEDs
cnt = 0; // Reset cnt
}
} while(1);
}
 

itaig

Member level 1
Joined
Jul 24, 2009
Messages
35
Helped
6
Reputation
12
Reaction score
1
Trophy points
1,288
Activity points
1,513
Re: Timer 0 Help needed

Try declaring cnt as a volatile.
eg:

volatile unsigned cnt;

Part of the optimisation the compiler will do is read cnt once into a register and then never read it again. The compiler will also then proceed to optimise the loop then declare a lot of code dead and remove it.

Declaring the variable as volatile will force the compiler to actually access the memory location instead of caching in a register.

Another thing is you should disable interrupts before accessing a volatile variable larger than 8 bits and disabling after you have finished with it but only in non-interrupt routines and only on processors that can't do the operation with one cpu instruction. The same also applies if you want to do a read-modify-write operation that requires multiple instructions. The reason for this is to prevent an interrupt occuring part way through a read or write of the variable. Failure to do this can introduce some very interesting bugs.

Hope this helps.
 

issaiass

Member level 3
Joined
Oct 21, 2004
Messages
59
Helped
4
Reputation
8
Reaction score
2
Trophy points
1,288
Activity points
404
Timer 0 Help needed

Only you have to do on your main is:
- Disable Timer
- Clear Timer Counter Register
- Enable Timer Interrupts and Clear Interrupt Flag
- Write your Preset Counter
- Enable Timer
- *Be sure your global interrupts are enables
- Loop forever

On your interrupt:
- Clear Interrupt Flag
- Toggle your bit


void main() {
ADCON1 = 0x0F; // Set AN pins to Digital I/O
T0CON = 0x; // Set TMR0 in 8bit mode, please assign prescaler(1/2) to TMR0
TRISB = 0; // PORTB is output
PORTB = 0x00; // Initialize PORTB
TMR0L = 1; // Timer0 initial value
INTCON = 0xA0; // Enable TMRO interrupt, TMR0 Overflow Interrupt Enable bit(bit 5)
while(1);
}

void interrupt () { // Please setup your interrupt well
PORTB = ~PORTB; // Toggle PORTB LEDs
INTCON = 0x20;
}
 

Status
Not open for further replies.
Toggle Sidebar

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Top