The IDE is really terrible. Fortunately, it has a use external editor button in the preferences. Then you can just it as a giant run button.
but can I bind M-x compile to that run button? Huh? can I?
On a mac you could hook it up to the GUI scripting layer. No idea what your options are.
I think my favored option remains the "not GUI scripting layer" that I definitely have available to me, which doesn't require running a behemoth java program just to get a run button.
I mean, I think I agree in general, but something about the voodoo you know vs the voodoo you don't.
I think I also have a weakness for not breaking into abstractions until I've already absorbed more than I should of of minor aggravation.
This is a little funny. The MaKeyMaKey shows up as a "USB serial" device, but that really just means that it speaks some particular protocol on the USB which, as it so happens, has good support for bulk-transfer of data in both directions and, more importantly, support in every operating system off the shelf in the past N years. (If you want to make your head hurt, go look at the USB packet formats and protocols; the particular stack of goo employed here is USB CDC ACM. See http://www.usb.org/developers/devclass_docs/usbcdc11.pdf
, or better, don't.)
The "ACM" in all this is "Abstract Control Model" which basically manages all the metadata about the serial stream -- baud rate, control line state, etc. A typical USB-to-serial widget will take the ACM command which sets baud rate (as well as the width of a byte, the number of stop bits, and parity coding) and use this to adjust its on-board clock generator so that the right waveforms exit its pins. But really, it's just a particular packet on the USB (and happens to be tagged with a value whose mnemonic is SET_LINE_CODING). Similarly, there's a packet to toggle the "carrier" indicator -- called DTR on RS-232 devices (tag mnemonic SET_CONTROL_LINE_STATE; the Arduinos started(?) this trend by hooking the AVR's RESET pin to their USB-to-serial chip's DTR output pin, IIRC.)
If you want code, the particular hack you're running up against is this bit of the firmware: https://github.com/sparkfun/MaKeyMaKey/blob/master/firmware/Arduino/hardware/MaKeyMaKey/cores/arduino/CDC.cpp#L109
. If it looks like the host has done the requisite magic, write a magic value to the magic address 0x800 (hope nobody else was using that -- blech) and turn on the watchdog timer at 120ms, which means that in about 120ms the chip will reboot (unless somebody's calling wdt_reset(), in which case this hack won't work -- double blech). The bootloader checks for this magic cookie here: https://github.com/sparkfun/MaKeyMaKey/blob/master/firmware/Arduino/hardware/MaKeyMaKey/bootloaders/caterina/Caterina.c#L130
As a quick follow-on, you should be able to automate this with
"stty /dev/ttyACM0 1200; echo -n '' > /dev/ttyACM0; avrdude ..." rather than needing to interact with screen.
Edited at 2013-01-10 07:18 am (UTC)
Naturally; I just already had screen in my bash history with a different baud rate at the time
I'm frankly alarmed how much this all makes perfect sense. I actually was at the point of concluding it had to be at the usb-to-serial layer that the magic was happening, but you've saved me a bunch of guesswork with your precise explanation, and saved me time hunting around in the firmware. Anyway thanks a ton. :) this low level hardware stuff is pretty fun after all, the occasional double-blech nonwithstanding
I'd probably call it (and think most people would agree) "user program" and if pressed "statically-linked against support libraries". It is also "firmware", especially from the perspective of the program talking to it over USB, tho', which cares not a whit about the internals (it would be equally happy if you coded the whole thing in Verilog and had an ASIC fabricated).
The bootloader is a separate blob, and actually has some on-CPU facilities for protecting itself against errant programmers (For all the gory details, see chapter 28.1 among others of http://www.atmel.com/Images/doc7766.pdf
). It looks like their bootloader expects to always be entered at startup (suggesting that the chip has the BOOTRST fuse programmed, or that HWBE is programmed and they can pull on /HWB on startup.) and will always go to boot-loader mode after an external reset (so if you just whack the /RESET pin, assuming that's enabled!, everything should be golden; as you can see, there are a lot of configuration options over here. It's a bit of a mess.)
All of that aside, you'd be really hard pressed to get the chip into a truly un-programmable state, though you might need some external hardware to get it back to happiness if you've flashed a bad boot loader, like an SPI, JTAG, or, in the absolute worst case, parallel programming hardware. Sections 28.5 and on document more than you'd ever care to know about such beasts; I suggest not reading them and just enjoying knowing that options exist if you need them.
wes you are setting a dangerous precedent by providing really excellent answers to my vague questions :P
Actually wait wait wait whoaaaa. If the special magic thing that detects the SET_LINE_CODING USB packet is in the program that I upload every time to the board, does that mean I can brick it into an unprogrammable state if I mess around with the code doing that check? c.c