Some source code wasn't part of `FMT_PATHS` so wasn't checked for
correct formatting. This change includes all this source code and
excludes cgo/testdata because it contains files that can't be parsed.
You can see that it works with the following command:
tinygo run -target=simavr ./testdata/recover.go
This also gets the following tests to pass again:
go test -run=Build -target=simavr -v
Adding support for AVR was a bit more compliated because it's also
necessary to save and restore the Y register.
This is a small change to make it easier to support architectures that
need to restore more than just the sp and pc registers. In particular,
it is needed for the AVR architecture that needs to restore the frame
pointer (Y register).
If an interrupt happens between the writes to SPL and SPH, the stack
pointer is inconsistent and terrible things will happen. Therefore,
disable interrupts while updating the stack pointer.
Interrupts are restored _before_ the write to SPH. This is safe, because
interrupts are re-enabled with a one cycle delay. The avr-gcc and Clang
compilers do the same thing when they need to update the stack pointer.
It's almost impossible to test for this bug, but it should make firmware
just a little bit more reliable.
Previously we used to scan between _edata and _end. This is not correct:
the .data section starts *before* _edata.
Fixing this would mean changing _edata to _etext, but that didn't quite
work either. It appears that there are inaccessible pages between _etext
and _end on ARM. Therefore, a different solution was needed.
What I've implemented is similar to Windows and MacOS: namely, finding
writable segments by parsing the program header of the currently running
program. It's a lot more verbose, but it should be correct on all
architectures. It probably also reduces the globals to scan to those
that _really_ need to be scanned.
This bug didn't result in issues in CI, but did result in a bug in the
recover branch: https://github.com/tinygo-org/tinygo/pull/2331. This
patch fixes this bug.
Precise globals require a whole program optimization pass that is hard
to support when building packages separately. This patch removes support
for these globals by converting the last use (Linux) to use
linker-defined symbols instead.
For details, see: https://github.com/tinygo-org/tinygo/issues/2870
This replaces "precise" global scanning in LLVM with conservative
scanning of writable MachO segments. Eventually I'd like to get rid of
the AddGlobalsBitmap pass, and this is one step towards that goal.
Simplify the interrupt-based timer code in a few ways:
- Do not recalibrate the timer every 100ms. Instead, rely on the fact
that the machine package will calbrate the timer if necessary if it
makes changes to Timer0.
- Do not configure Timer0 and then set nanosecondsInTick based on that
value. Instead, use a fixed value.
These two changes together mean that in code that doesn't use PWM,
nanosecondsInTick will be constant which makes the TIMER0_OVF interrupt
handler a lot smaller.
Together this reduces the code size of AVR binaries by about 1200 bytes,
making it pretty close to the pre-timer code size (only about 250 bytes
larger).
It also somehow fixes a problem with
tinygo.org/x/drivers/examples/ws2812 on the Arduino Uno. I'm not quite
sure what was going wrong, but bisecting pointed towards the timer code
(https://github.com/tinygo-org/tinygo/pull/2428) and with this
simplification the bug appears to be gone.
Scan globals conservatively by reading writable sections from the PE
header.
I'd like to get rid of needing to precisely scan globals eventually, and
this brings us one step closer. It also avoids a bug with ThinLTO on
Windows.
This patch adds support for generating GOOS=darwin GOARCH=arm64
binaries. This means that it will become possible to run `go test` on
recent Macs, for example.