Is there a limit of 250.000 interrupts/sec for Due?

This code piece from Mr. Arduino's ov7670 camera software configures PWM on Uno to generate 8MHz clock signal for ov7670:

I wanted to test it and tried to use my Due in order to count the interrupts per second like I did before:

There I was able to measure 32K interrupts per second, and later more than 40k interrupts per second.

I tried different OCR2A values and the lowest that did count all interrupts (Frequency reported by Nano, left side) was 38 or 205128Hz. Se here screenshot for 32 or 242424Hz (big screenshot here):

31 translates to 250KHz and that is where the Due program does not output anything anymore.
It seems that 250.000 interrupts per second make "delay(1000)" to not complete anymore.

This is the setup, photo taken while on train this evening (big here):

I tried first with this bidirectional voltage leveler:
http://www.aliexpress.com/item/1Pcs-5V-to-3-3V-IIC-I2C-Logic-Level-Converter-Bi-Directional-Module-for-Arduino/32307221398.html

And later with self made 1kΩ/1kΩ+1kΩ level shifter as can be seen in the photo.
Identical measurements for both.

Is there a 250.000 interrupts/second limit for Due?
I do not have a scope to look at the wave generated by Nano.
Attaching both sketches for investigation.

Hermann.

sketch_jan11b.ino (306 Bytes)

sketch_jan11a.ino (405 Bytes)

I think, it's about right. Usually, you should configure a hardware counter-timer, w/o software interrupt it may count up to 42MHz.

http://coolarduino.blogspot.ca/2015/06/frequency-counter-for-arduino-due.html

Thank you, that link is wonderful -- and answers this threads question with NO (limit).

I did setup the connections for frequency measurement as described in "Counter_1d.ino":

Then I did set OCR2A=0 for Nano resulting in 8MHz frequency (reported in below Serial monitor).
The frequency measured by Due (upper Serial monitor) is nearly exactly 8MHz:

Next I wanted to try "TimerSet.ino" for period detection.
But that file is broken in the .zip on Google Drive.
I just copied it from the 2nd posting:
http://coolarduino.blogspot.ca/2015/06/frequency-counter-for-arduino-part-2.html

In order to see a nice value for period I did set OCR2A=199 resulting 40KHz from Nano.
The period 25 measured by Due matches that frequency exactly:

Hermann.

I ran your benchmark here, using a function generator to drive pin 2. Arduino Due stopped printing at only 156 kHz in my test.

volatile unsigned long count=0;
unsigned long last=0;
unsigned long now;

void fcnt(void) { count++; }

void setup() {
  Serial.begin(9600);
  pinMode(2, INPUT);
  attachInterrupt(digitalPinToInterrupt(2), fcnt, FALLING);
  //attachInterrupt(2, fcnt, FALLING);  //Arduino 101
}

void loop() {
  noInterrupts();
  last = count;
  interrupts();
  delay(1000);
  noInterrupts();
  now = count;
  interrupts();
  Serial.println(now - last);
}

I am not sure what the difference is between your 156KHz and my 250KHz limit setup other than the [noI|i]nterrupts() calls you added.

I tried different methods to stop after 1 second:

...
    //delay(1000);
    //t0 = millis();  while (millis()-t0 < 1000) { }
    //for(i=0; i<5591798; ++i) {}
    ///++i;
...

All did not work, and the only explanation I can find is that Due is 100% busy with handling the 250k interrupts and has no time left to process normal statements (even single "++i;" statement without loop does not give any output.

The good news is that the frequency measurement library can measure up to 42MHz!
So many useful hardware features on the SAM processor.
Have not found out yet how to influence the duty cycle on the Nano code, will read the AVR spec (for verifying that reported duty is correct, "analogWrite(11,64)" hangs the program):

...
	DDRB|=(1<<3);//pin 11
	ASSR &= ~(_BV(EXCLK) | _BV(AS2));
	TCCR2A=(1<<COM2A0)|(1<<WGM21)|(1<<WGM20);
	TCCR2B=(1<<WGM22)|(1<<CS20);
	OCR2A=199;//(F_CPU)/(2*(X+1))
	DDRC&=~15;//low d0-d3 camera
	DDRD&=~252;//d7-d4 and interrupt pins
...

My interest here is optimizing attachInterrupt. My own implementation on Teensy has a long-standing TODO, to optimize using the ARM CLZ (count leading zeros) instruction, instead of testing several bit separately. But even with the current code, it manages up to 1117 kHz before the loop no longer runs.

I'm also the author of the FreqCount library. If you'd like to contribute the Due hardware support, please add the timer stuff in the #defines and submit a pull request on github. Many libraries like FreqCount are designed with abstraction layers to support many different chips, but Due isn't supported only because nobody has gone to the extra effort to contribute the timer defs.

Tested value 247 kHz. It confirms, that attacheInterrupt is indeed slow, 4usec for going in-and-out.

I want to use an interrupt for counting pulses coming from out of arduino due.
with code below:

const byte ledPin = 13;
const byte interruptPin = 53;
//volatile byte state = LOW;

unsigned long sCount = 0;
void setup() {
Serial.begin(9600);
pinMode(ledPin, OUTPUT);
pinMode(interruptPin, INPUT);
attachInterrupt(digitalPinToInterrupt(interruptPin), blink, CHANGE);
// attachInterrupt(interruptPin, blink, RISING);
}
void loop() {
// digitalWrite(ledPin, state);
Serial.println(sCount);
}

void blink() {
sCount++;
}

By counting program sketch in arduino due the incoming pulses is shown regular increasing in serial monitor like this:1,2,3,4,5,6,.....
But in interrupt code it dose not work correct,and in serial monitor increasing numbers is irregular numbers.
In serial monitor appears number 1 or number 2 after opening it(serial monitor)and it seams not correct.
I connect pulses with an optical fiber to arduino and it works relatively acceptable but with increasing
numbers two by two like this:2,4,6,8,10,.....
It seems sensitive input to noises in interrupt sketch condition,than counting sketch condition.
Please advise me in this case.
Regards,
Hamid

Email: tanit_mehr@yahoo.com

Hello,

I want to use an interrupt for counting pulses coming from out of arduino due.
with code below:

const byte ledPin = 13;
const byte interruptPin = 53;
//volatile byte state = LOW;

unsigned long sCount = 0;
void setup() {
Serial.begin(9600);
pinMode(ledPin, OUTPUT);
pinMode(interruptPin, INPUT);
attachInterrupt(digitalPinToInterrupt(interruptPin), blink, CHANGE);
// attachInterrupt(interruptPin, blink, RISING);
}
void loop() {
// digitalWrite(ledPin, state);
Serial.println(sCount);
}

void blink() {
sCount++;
}

By counting program sketch in arduino due the incoming pulses is shown regular increasing in serial monitor like this:1,2,3,4,5,6,.....
But in interrupt code it dose not work correct,and in serial monitor increasing numbers is irregular numbers.
In serial monitor appears number 1 or number 2 after opening it(serial monitor)and it seams not correct.
I connect pulses with an optical fiber to arduino and it works relatively acceptable but with increasing
numbers two by two like this:2,4,6,8,10,.....
It seems sensitive input to noises in interrupt sketch condition,than counting sketch condition.
Please advise me in this case.
Regards,
Hamid

The sketch below works nicely. Use 250000 for your baud rate with serial monitor because Serial uses interrupts and (maybe) it interfere with your attachinterrupt :

const byte ledPin = 13;
const byte interruptPin = 53;


volatile uint32_t sCount, Flag;

void setup() {

 Serial.begin(250000);
 
 pinMode(interruptPin, INPUT);  
 attachInterrupt(digitalPinToInterrupt(interruptPin), blink, CHANGE);

}
void loop() {

 if (Flag = 1) {
  Serial.println(sCount);
  Flag = 0;
 }
}

void blink(void) {
 sCount++;
 Flag = 1;

}