Posts

S4A debugging with avr-gdb and simavr

Image
While this has been possible for a while in S4A, with long workarounds, it got a lot easier in the 5.0 beta IDE. Using the "open folder" project structure, save work into a folder and build, the "Terminal" button enables. Press it and you're in a terminal session within the folder, with a command line build ready to go. Run "make simulate-gdb" and you have the program running on simavr, with the debug port open for avr-gdb to attach to. Create a separate Terminal window with the same button for your avr-gdb session and run "avr-gdb main.elf" to pick up the image symbols. In the session choose "target remote :1234" and you're in! My preferred run mode for avr-gdb is "layout asm" or "layout reg" (seen here). Obviously it's not for a beginner, but for an experienced gdb jockey it should prove interesting. Hints You can find these on other blogs about gdb and simavr. But might be useful here. To dump memory..

Investigating a compiler bug

 On rare occasions we find a bug in the compiler. exploring this one was instructive. A user reported that the simple instruction... print(Float(Int32(60000.00)) was printing 33003.00! Confirmed this is not expected on a macOS playground, then dug into where this came from. It's well documented how the S4A compiler produces AVR machine code... Swift code is compiled to bitcode, then an llvm AVR assembler compiles the bitcode for AVR, so one of these steps is at fault, right? There's actually a hidden subtlety in the first step, swift compilation. Because most of the time when you write Swift code, without realising it you're actually using a swift library and non primitive types... the standard library! So in fact there's effectively hidden Swift code inside the above simple swift code. While the micro swift standard library is not open source, it's very closely based on the common, open source swift library. From that we can see a constructor for Float from Int32 t

S4A known directories

 the IDE has grown organically over the years and many things are not documented. I thought something useful might be the (current) set of directories used by S4A 4.9.2 (note, these things change often) In ~/Library/Application Support/SwiftForArduino... Boards - a supplementary boards.yaml file and related images, allowing you to add board definitions, which will be detected if their USB VID/PID match Builds - dynamically created/destroyed folders that contain the files built from source code, created on demand and deleted when you close the project, there is an advanced setting to keep contents Extensions/Build - the location for build plugins used by the board definitions, e.g. 0-series atmega chip build plugins Extensions/Upload - the location for upload plugins used by the board definitions, e.g. 0-series atmega chip upload plugins Extensions/Modules - added into the swift compile and clang compile paths, you can put built modules in here for import into your code Libraries - auto

code signing, entitlements, bundles, sandboxes, hardened runtime, notarisation, app store security

Some people had mentioned troubles with code signing, i thought a brain dump of my learnings on it might be informative and helpful as I've learned a lot in developing a mac app (the s4a IDE).  Some of these concepts are used in ios too but this post is about mac apps. First up, terminology. Code signing. *** This is a variant of normal PKI (public key infrastructure) signing. A hash is made of the binary you're signing (the actual macho executable file), then encrypted with your private key to make a signature that anyone with your public key can decrypt and verify to check your binary hasn't been altered in any way since you signed it. Code signing could in theory be done with any tool, (many of these concepts are NOT mac/ios only concepts but follow general unix/windows/etc. principles and ideas widely used across industry), but in reality, people on a mac use the built in (to macOS) tool "codesign" which is a command line tool that can create, alter, remove an

Comparing iLEDs

This might seem a bit off topic, but i've never seen the need for this blog to only be about S4A. :) There are a bunch of RGB LEDs out there that are controlled by a one wire protocol (note: readers, feel free to add any info in the comments section or links to similar comparison blog posts, let's help each other out!) Most of them are made by world semi, hence the WS part numbers. Here are some comparison links: https://www.utmel.com/components/ws2811-vs-ws2812b?id=614 https://www.pololu.com/category/180/sk6812-ws2812b-based-led-strips https://cdn.sparkfun.com/assets/learn_tutorials/1/0/5/WS2812B_VS_WS2812.pdf https://www.suntechleds.com/info/ws2813-vs-ws2815-digital-programmablel-led-str-36642316.html needless to say any of the relatively small family of core ileds are then resold by a variety of manufacturers in a variety of form factors, but fundamentally the code needed to control them is the same for each family (note, I'm not talking about other chips that are contro

All about bootloaders

 BOOTLOADERS *** Some interesting general boot loader facts: The Boot Loader is basically a section at the top of flash memory, how big it is depends on the BOOTSZ1 and BOOTSZ0 bits in the Low Fuse byte. It has the special property that ONLY while the core is running instructions in the bootloader, a special instruction called SPM will function. This function allows writing data to the flash memory. As normal with all flash, you need to erase the page you are writing first, otherwise your write operation will often not function correctly. I think you can change 1 bits to 0 bits but not the other way around, which is true for all flash writing. So the flash erase process always sets a flash memory page to all 0xFF (all 1 bits) The usual way the boot loader runs is if the fuse bit BOOTRST is active (i.e. it reads as a 0!) then when the MCU is reset, it will start execution at the beginning of the bootloader (as defined above). If the bit is not set, it will start execution at 0x0000. But

Pushing the limits

 The nice thing about Swift for Arduino these days is we are having a lot of conversations like "exactly how much performance can you get from an atmega328p, how much program space is the limit? what about RAM?" To me it shows we've gone far beyond the 'hobbyist' place we started from and now as we build professional products, we are dealing with the same issues all professional embedded developers grapple with... in a word efficiency. To that end I thought it might be worth me putting down some thoughts on what some of the numbers are, where the overheads are, what are the limits on RAM and program memory? I'm talking here to the atmega328p as that's what most of our work uses.. the classic Arduino UNO heart, but of course similar things would apply for other chips. In spec, we have 2k RAM, 32k program memory? Can I use all of those? Of course not. ;-) Let's break it down. PROGRAM MEMORY You might have seen my earlier article with a breakdown of what