Hi ,
I used a Arduino Duemilanove to generate a 5V trigger signal to be measured by itself through an interrupt (So the microcontroller feeds the trigger is the same as the one measuring it). This is my code
int pin = 13;
volatile int state = LOW;
const int ledPin = 12; // the number of the LED pin
int ledState = LOW; // ledState used to set the LED
long previousMillis = 0; // will store last time LED was updated
long interval = 100; // interval at which to blink (milliseconds)
int trigger = 13; // Trigger Ausgnag
unsigned long microshigh1; //Microsekunden wenn der Trigger auf HIGH geht- vorheriger Trigger
unsigned long microshigh2; //Microsekunden wenn der Trigger auf HIGH geht- aktueller Trigger
unsigned long deltamicros; //Abstand zweier high Flanken
void setup()
{
//Wie werden die Arduino ÜPins benutzt?
Serial.begin(115200);
pinMode(pin, OUTPUT);
attachInterrupt(0, ignite, CHANGE); //put interrupt on pin 2---> Triggereingang
pinMode(ledPin, OUTPUT);// Virtueller trigger
}
void loop()
{
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > interval) {
// save the last time you blinked the LED
previousMillis = currentMillis;
// if the LED is off turn it on and vice-versa:
if (ledState == LOW)
ledState = HIGH;
else
ledState = LOW;
// set the LED with the ledState of the variable:
digitalWrite(ledPin, ledState);
}
}
void ignite()
{
state = !state;
digitalWrite(pin, state);
digitalWrite(10, LOW);
microshigh2 = micros();
deltamicros= microshigh2-microshigh1;
Serial.println(deltamicros);
microshigh1= microshigh2;
}
The result is the following received by the serial out:
int pin = 13;
volatile int state = LOW;
const int ledPin = 12; // the number of the LED pin
int ledState = LOW; // ledState used to set the LED
unsigned long previousMillis = 0; // will store last time LED was updated
unsigned long interval = 100; // interval at which to blink (milliseconds)
int trigger = 13; // Trigger Ausgnag
unsigned long microshigh1; //Microsekunden wenn der Trigger auf HIGH geht- vorheriger Trigger
unsigned long microshigh2; //Microsekunden wenn der Trigger auf HIGH geht- aktueller Trigger
unsigned long deltamicros; //Abstand zweier high Flanken
void setup()
{
//Wie werden die Arduino ÜPins benutzt?
Serial.begin(115200);
pinMode(pin, OUTPUT);
attachInterrupt(0, ignite, CHANGE); //put interrupt on pin 2---> Triggereingang
pinMode(ledPin, OUTPUT);// Virtueller trigger
}
void loop()
{
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > interval) {
// save the last time you blinked the LED
previousMillis = currentMillis;
// if the LED is off turn it on and vice-versa:
if (ledState == LOW)
ledState = HIGH;
else
ledState = LOW;
// set the LED with the ledState of the variable:
digitalWrite(ledPin, ledState);
}
}
void ignite()
{
state = !state;
digitalWrite(pin, state);
digitalWrite(10, LOW);
microshigh2 = micros();
deltamicros= microshigh2-microshigh1;
Serial.println(deltamicros);
microshigh1= microshigh2;
}
This wasn’t the root cause. I tried to put the microshigh1 and 2 into volatile memory state improving speed…no success as well
MarkT,
in general I do agree, but
- I need to know if the interrupt is working with a minimum (or at least a defined) delay
- the code shows an intervall of 100mS at 115200baud which should be quick enough to submit the data
- the serial data submission is after the interrupt work...shouldn't lead to a delay
But anyhow I do agree that this is not optimum, but I do not know any other way to control function accuracy and I do not have a oscilloscope
Ahh- I misunderstood all of you not using SerialPrint at all. Sorry! Now I changed the code and put the command in the loop
void loop()
{
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > interval) {
// save the last time you blinked the LED
previousMillis = currentMillis;
// if the LED is off turn it on and vice-versa:
if (ledState == LOW)
ledState = HIGH;
else
ledState = LOW;
// set the LED with the ledState of the variable:
digitalWrite(ledPin, ledState);
Serial.println(deltamicros);
}
}
I decreased the speed of blinking to give more time for SerialPrintThe result remains unchanged. Still 1mS variation:
int pin = 13;
volatile int state = LOW;
const int ledPin = 12; // the number of the LED pin
int ledState = LOW; // ledState used to set the LED
unsigned long previousMillis = 0; // will store last time LED was updated
unsigned long interval = 1000; // interval at which to blink (milliseconds)
int trigger = 13; // Trigger Ausgnag
unsigned long microshigh1; //Microsekunden wenn der Trigger auf HIGH geht- vorheriger Trigger
unsigned long microshigh2; //Microsekunden wenn der Trigger auf HIGH geht- aktueller Trigger
unsigned long deltamicros; //Abstand zweier high Flanken
void setup()
{
//Wie werden die Arduino ÜPins benutzt?
Serial.begin(115200);
pinMode(pin, OUTPUT);
attachInterrupt(0, ignite, CHANGE); //put interrupt on pin 2---> Triggereingang
pinMode(ledPin, OUTPUT);// Virtueller trigger
}
void loop()
{
unsigned long currentMillis = millis();
if(currentMillis - previousMillis > interval) {
// save the last time you blinked the LED
previousMillis = currentMillis;
// if the LED is off turn it on and vice-versa:
if (ledState == LOW)
ledState = HIGH;
else
ledState = LOW;
// set the LED with the ledState of the variable:
digitalWrite(ledPin, ledState);
Serial.println(deltamicros);
}
}
void ignite()
{
digitalWrite(pin, state);
digitalWrite(10, LOW);
microshigh2 = micros();
deltamicros= microshigh2-microshigh1;
microshigh1= microshigh2;
state = !state;
}
unsigned long deltamicros; //Abstand zweier high Flanken
Used by loop() and the ISR. Should, therefore, by volatile.
The deltamicros variable takes time to convert to a string, and to shift the bytes to the serial port. An interrupt can occur while that is happening. You need to copy the valuable to another location, and output the copy.
Even during a copy operation, while 4 bytes are copied, an interrupt can occur. So, you need to disable interrupts before the copy starts. and then enable them again as soon as the copy completes.
What is generating the external interrupt? Are you sure that it is consistently happening exactly one second apart?
Dear all,
I have found the issue. The code for blinking the trigger is based on mS and the ISR is based on microseconds. So I changed the code to the following:
int pin = 13;
volatile int state = LOW;
const int ledPin = 12; // the number of the LED pin
int ledState = LOW; // ledState used to set the LED
unsigned long previousMillis = 0; // will store last time LED was updated
unsigned long interval = 1000; // interval at which to blink (milliseconds)
int trigger = 13; // Trigger Ausgnag
volatile unsigned long microshigh1; //Microsekunden wenn der Trigger auf HIGH geht- vorheriger Trigger
volatile unsigned long microshigh2; //Microsekunden wenn der Trigger auf HIGH geht- aktueller Trigger
volatile unsigned long deltamicros; //Abstand zweier high Flanken
void setup()
{
//Wie werden die Arduino ÜPins benutzt?
Serial.begin(115200);
pinMode(pin, OUTPUT);
attachInterrupt(0, ignite, CHANGE); //put interrupt on pin 2---> Triggereingang
pinMode(ledPin, OUTPUT);// Virtueller trigger
}
void loop()
{
unsigned long currentMillis = micros();
if(currentMillis - previousMillis > interval) {
// save the last time you blinked the LED
previousMillis = currentMillis;
// if the LED is off turn it on and vice-versa:
if (ledState == LOW)
ledState = HIGH;
else
ledState = LOW;
// set the LED with the ledState of the variable:
digitalWrite(ledPin, ledState);
Serial.println(deltamicros);
}
}
void ignite()
{
digitalWrite(pin, state);
digitalWrite(10, LOW);
microshigh2 = micros();
deltamicros= microshigh2-microshigh1;
microshigh1= microshigh2;
state = !state;
}
And the result with 1000microseconds is reasonable good including SerialPrint: