Author Topic: Does micronucleus introduce issues with interrrupts?  (Read 2764 times)

deHarry

  • Newbie
  • *
  • Posts: 5
Does micronucleus introduce issues with interrrupts?
« on: February 01, 2019, 11:09:58 am »
Hello Guys!
I have a weird problem with a DigiSpark (clone).

I program my Digispark with Visual Studio7 with installed MicroVisual extension.
This couple runs smoothly for all Arduinos I used (Uno, Nano, Micro, Mega) as well as with several ESP8266 derivates.
The step to Attiny85 and DigiSpark was not so easy, but I managed this with the help of some friendly users who had similar problems in the beginning. Now code for the DigiSpark is also generated in this environment.
Nota bene: VisualMicro is terrific in not changing anything in the sources, so it is possible to switch unhampered between VS7 and Arduino-IDE for compiling and downloading (I use both ways alternating (not regularly alternating :) ).

So far the intro, now the problem:
If I compile my program for an AtTiny85 @16MHz, all is well, no issues.
If I compile the unchanged sources for a DigiSpark (Default @16,5 MHz), I have problems when checking timings in the INT0 ISR.

The code analyzes the serial DCC signal coming in on pin 7 (PB2) and distinguishes between "0" (square wave with ~100 µs period) and "1" (square wave with ~60 µs period).

Nota bene II: Regardless of the methode used to download the resulting code onto the chip, if build target is "Digispark" the code doesn't work as expected, if build target is "AtTiny85 @16MHz", it works like a breeze.
Ok, there are diffenreces in code size, I think they come from different libraries, but that shouldn't result in busting the code.
"Different methods of downloading" means: I flash with "mySmartUSB light" or alternately via USB (micronucleus bootloader).

Having read about "issues with INT0" (in older versions of micronucleus) I changed the signal sampling from INT to PCINT0 (pin change int).
-> Same result, AtTiny85 code works, Digispark code doesn't.

Next idea I tested: Replace attachInterrupt() by manual register fumbling.
-> Same result, AtTiny85 code works, Digispark code doesn't.

As stated above, it is independent of the tool I use for compiling (VS7 od Arduino IDE) and independent of the download method (ok, the AtTiny85 has to be flashed with the programmer, every time, of course).

I did some oscilloscope work and found that the routine which distinguished between 60 and 100 microseconds, respectively, gets disturbed when Digispark is selected as build target.

Any ideas on the cause (and the remedy) for the given problem?
Thanks in advance!

[edit]
I forgot to mention, I already used micronucleus V1.06 (this version resided on the DisgiSparks when ordered) and V2.04.
Here no difference, too.
And I always use a Digispark as hardware.
[/edit]

Harry
« Last Edit: February 01, 2019, 11:16:25 am by deHarry »

deHarry

  • Newbie
  • *
  • Posts: 5
Re: Does micronucleus introduce issues with interrrupts?
« Reply #1 on: February 02, 2019, 01:03:31 pm »

[edit]
Hi again!
I wonder if I just should delete this post...

I did more research and reflashed micronucleus (and the "selfprogram enable" fuse bit) and now I get similar results for this toggle sketch when compiling for AttIny85 or for DigiSpark.
I must have gotten something really wrong when I took my first measurements  ::)
Sorry for any inconveniences I may have imposed to anyone...

Ok, my original program doesn't run still, but the timing of Digispark with micronucleus seems to NOT be the reason.
I will investigate further.
[/edit]


I'm back...  :D

I did some measurement to clearify the problems I stumble into.
The sketch is the bare minimum, just declare pin B1 as output and a while(1) loop (in setup) where I switch the defined output from low to high and vice versa. This switching I recorded with my oscilloscope.

Code: [Select]
// Zeit messen (Clockfrequenz)
unsigned long zeitmessung = 0;
unsigned long letztezeit = 0;

void setup()
{

  pinMode(PB1, OUTPUT);

  // check clock frequency
  while (1)
  {
  zeitmessung = micros();
  //zeitmessung = millis();
  if ((zeitmessung - letztezeit) > 100)
  {
  //bitSet(PORTB, PINB1); // debug (LED)
  //bitClear(PORTB, PINB1); // debug (LED)
  digitalWrite(PB1, !digitalRead(PB1)); // debug, Toggle (LED)
  letztezeit = zeitmessung;
  }
  }
}

void loop() {
// we nerver come here
}

So, what did I get?
When compiling for AtTiny85 and download via ISP programmer (mySmartUSB light) this results in following

Picture „100micros.png“

You see some decent jitter (96..112 µs) for a 100µs loop. I think that's ok.

Now the same compiled for Digispark...
Output of Arduino IDE:

Code: [Select]
Der Sketch verwendet 792 Bytes (13%) des Programmspeicherplatzes. Das Maximum sind 6012 Bytes.
Globale Variablen verwenden 17 Bytes des dynamischen Speichers.
C:\Users\Harry\AppData\Local\Arduino15\packages\digistump\tools\micronucleus\2.0a4/launcher -cdigispark --timeout 60 -Uflash:w:C:\Users\Harry\AppData\Local\Temp\arduino_build_63068/TimingTest.ino.hex:i
Running Digispark Uploader...
Plug in device now... (will timeout in 60 seconds)
> Please plug in the device ...
> Press CTRL+C to terminate the program.
> Device is found!
connecting: 16% complete
connecting: 22% complete
connecting: 28% complete
connecting: 33% complete
> Device has firmware version 2.4
> Device signature: 0x1e930b
> Available space for user applications: 6522 bytes
> Suggested sleep time between sending pages: 7ms
> Whole page count: 102  page size: 64
> Erase function sleep duration: 714ms
parsing: 50% complete
> Erasing the memory ...
erasing: 55% complete
erasing: 60% complete
erasing: 65% complete
> Starting to upload ...
writing: 70% complete
writing: 75% complete
writing: 80% complete
> Starting the user app ...
running: 100% complete
>> Micronucleus done. Thank you!

I would say, all went well, the code from above is in the Digispark.
Let's see, what we get here...

Picture „digi100_1.png“

This time there is no clean square wave, we see one spurious spike in the middle of the first "high" periode.
But definitely way more astonishing is the periode of the signal: 8.86 ms (MILLI seconds, I expected 200 µs MICRO seconds).

Whats wrong with the timing of the Digispark, when micronucleus is still residing in flash. (I checked that with mySmartUSB light. From 0000 to 116B lies the program code, from 197B til the end of flash lies micronucleus, in between the flash is filled with 0xFF).

The same hardware, the Digispark, flashed as Attiny85 behaves well, flashed as DigiSpark via USB and with micronucleus onboard, everything is weird  :(

No wonder why checking the DCC signal for "1" and "0" doesn't succeed, having these findings in mind.

Is there something obvious in using the DigiSpark with USB upload I missed?

Harry
« Last Edit: February 03, 2019, 12:17:05 pm by deHarry »

deHarry

  • Newbie
  • *
  • Posts: 5
Re: Does micronucleus introduce issues with interrrupts?
« Reply #2 on: February 14, 2019, 05:03:00 am »
Hi All!

In addition to my last writing (-> no timing issues as described in the lower part of my previous post) I want to add my final findings after some days of unhappy code pimping and taking measurements.

As stated in my first post on that issue, I can assure that there is a problem with the timing of micros() when the code is downloaded via USB and micronucleus.
Regardless of choosing "Digispark(Default - 16,5 MHz)" or "Digispark (16mHz - No USB)", respectively, the code doesn't work as expected.

The reason for that is a significant jitter in the timing of micros() as well as sporadic triggers of the IRQ routine (no guess where they come from, the DCC signal on PB2 is (more or less) clean).
Furthermore it's of no relevance whether I choose external INT0 or pin change PCINT0 as trigger for the IRQ routine.

These issues prevent sampling of serial signals (@~8 kHz signal frequency) nearly perfect :(

Is there anybody out here in this forum who is able - and willing - to give a hint on how to circumvent these problems?
Did nobody experience similar problems with his Digispark?

I will happily give it a try if someone can give a clue...
Thanks!

Harry