Today I played with the delayMicroseconds() function - http://arduino.cc/forum/index.php/topic,132983.0.html - It seems to be difficult to get delays of 1 and 2 usec right. So I tried to make a function that delayed for exactly 1 usec and started experimenting with the volatile keyword in (for me) new ways.
This way I "fabricated" 4 functions:
- delay125ns();
- delay250ns();
- delay500ns();
- delay1000ns();
The timings are approx within 1% tested on a 16Mhz Duemillanove. I tested these functions by running them in a loop, first with one call , and then a second loop with 2 calls, so the difference is the time used by the functions as the loop overhead is subtracted too.
Note: There are better ways to implement these functions - using asm("nop"); - but this was just fun!
The functions:
void delay125ns()
{
volatile uint8_t x=0;
return;
}
void delay250ns()
{
volatile int x=0;
return;
}
int delay500ns()
{
volatile int x=0;
return x;
}
int delay1000ns()
{
volatile int x = 0;
volatile int y = 0;
return x+y;
}
// profi way to implement such delay functions
void d250ns()
{
asm("nop");
asm("nop");
asm("nop");
asm("nop");
}
The testprogram with functions:
void setup()
{
Serial.begin(9600);
Serial.println("start...");
unsigned long m;
unsigned long n;
Serial.println("delay125ns");
m = micros();
for (unsigned int i=0; i<16000; i++) delay125ns();
m = micros() - m;
n = micros();
for (unsigned int i=0; i<16000; i++)
{
delay125ns();
delay125ns();
}
n = micros() - n;
Serial.print("Extra 1000 calls take: ");
Serial.println((n-m)/16);
Serial.println("delay250ns");
m = micros();
for (unsigned int i=0; i<16000; i++) delay250ns();
m = micros() - m;
n = micros();
for (unsigned int i=0; i<16000; i++)
{
delay250ns();
delay250ns();
}
n = micros() - n;
Serial.print("Extra 1000 calls take: ");
Serial.println((n-m)/16);
Serial.println("delay500ns");
m = micros();
for (unsigned int i=0; i<16000; i++) delay500ns();
m = micros()- m;
n = micros();
for (unsigned int i=0; i<16000; i++)
{
delay500ns();
delay500ns();
}
n = micros()- n;
Serial.print("Extra 1000 calls take: ");
Serial.println((n-m)/16);
Serial.println("delay1000ns");
m = micros();
for (unsigned int i=0; i<16000; i++) delay1000ns();
m = micros() - m;
n = micros();
for (unsigned int i=0; i<16000; i++)
{
delay1000ns();
delay1000ns();
}
n = micros() - n;
Serial.print("Extra 1000 calls take: ");
Serial.println((n-m)/16);
}
void loop()
{}
void delay125ns()
{
volatile uint8_t x=0;
return;
}
void delay250ns()
{
volatile int x=0;
return;
}
int delay500ns()
{
volatile int x=0;
return x;
}
int delay1000ns()
{
volatile int x = 0;
volatile int y = 0;
return x+y;
}