meetjestad / mjs_pcb

Other
6 stars 0 forks source link

V3 PCB Considerations: MCU selection #4

Open matthijskooijman opened 4 years ago

matthijskooijman commented 4 years ago

For the next generation PCB, we're looking at switching away from the Atmega328p, since it is becoming too small for future additions (see also #2). This issue summarizes some of our previous considerations and offers space for further discussion.

Package

Ideally, we would use a DIP package, since that is really easy to solder even for novices. However, within the Atmega family, it seems that all chips bigger (in terms of RAM and flash) are also wide dip packages (e.g. the Atmega1284) and a lot bigger. Also, these are quite expensive an offer no extra CPU speed compared to the 328p, so some ARM-based chip is probably better.

However, there seem to no viable ARM-based processors in DIP-package, hence the consideration to use a breakout for the MCU, or maybe prepopulate it.

Looking at SMD-packages, QFP is the most common and still hand-solderable, so probably the most viable. We initially limited to QFP-32 packages, since 32-pins seemed to be just enough for our basic design plus some expansion ports and QFP-32 with its 0.80mm pitch is still fairly easy to solder for someone with some experience (QFP-48 and QFP-64 with 0.50mm pitch is already a bit harder). However, if we are going to automated this part of the assembly, QFP-48 and QFP-64 are probably also feasible (QFN is probably a bridge too far).

SAMD21

Our search mainly looked at the SAMD21 family, since that is used in a lot of Arduino boards and supported by Arduino itself. In addition to the core running on there, the upload method (using a USB bootloader) is probably also well-supported. In our initial testing, we used a SAMD21E (32-pin) with the bootloader from the Adafruit Trinket M0 which uses the same chip (unlike the more commonly used SAMD21G used by Arduino zero and other boards).

RISC-V

We also considered the RISC-V platform / SiFive processors, but those do not seem to be very mature yet and Arduino support is probably imperfect.

STM32

STM32 was originally also looked at briefly (mostly looking for any pre-made breakout boards) and later I looked at them in a bit more detail. Since then, I've had a bit more experience with STM32 chips and I think this is a good option. Arduino support is not provided by Arduino itself, but ST has taken maintainance of the Arduino_Core_STM32 core (there are a few others too) and IMHO is doing a good job at it.

A big advantage of (most) STM32 chips is that (most of) their pins are 5V-tolerant, which is of course helpful to facilitate experimenting with new sensors (even though all specific sensors we are considering now have 3.3V logic).

A challenge is the sketch uploading. The STM32 chips have a builtin ROM bootloader which is convenient (cannot be erased) and often (depends on the chip) can do uploads through USB (using DFU). However, these bootloaders typically listen on one more UARTs, SPI ports, I²C ports, CAN bus, etc. To prevent accidentally putting the bootloader in the wrong mode, these other ports must all have a particular and stable startup state (e.g. SS pins, UART RX, I2C all high).

An alternative is using a custom bootloader occupying the first flash page, of which there are a few available (but I have not looked closely at which, the ones I saw were not that great). There is an Adafruit STM32 board (and reportedly Arduino will release one soon too), so maybe there is some bootloader and other tricks we could copy from there. The Arduino_Core_STM32 also does not have perfect support for USB uploads yet, but I've made some improvements there already and I think those should be usable soon.

If we use a custom bootloader, it would be best if it can be protected somehow, to prevent accidentally overwriting it and preventing further uploads. Protection is typically done at a flash page or section boundary, so this might end up "wasting" some flash space if the bootloader is a lot smaller than that.

Flash & Memory

Currently, we have a 328p with 32K flash and 2K RAM. For Flash, doubling the amount of space would give a lot of room to play, but might still be a bit limited (especially since compiled programs are typically a bit bigger on ARM I think). Four times as much (128K flash) is probably more than enough, but more does not hurt.

As for RAM, I think most chips of these sizes are 32K+, which should be more than enough.

Power usage

Currently, the 328p can sleep at < 1μA, which is probably below the self-discharge and below the average current of MCU and sensors while running. Run current is 40mA or so.

For a new chip, a similar sleep current would be nice, though up to a few μA is probably also acceptable.

This sleep mode should retain RAM. Some chips (e.g. STM32G4 and ESP) can only obtain such low-power sleep when disabling RAM. Often, there are a few RTC registers that can be used to save state, but that greatly complicated firmware programming, especially for novice programmers, so that is IMO not acceptable.

EEPROM

The current 328p has builtin EEPROM that is used to provision it with an id and encryption keys. SAMD21 and most STM32 processors do not seem to have EEPROM built-in, though flash can often be used as an alternative (sometimes there is even a dedicated section of flash that can be used like EEPROM, SAMD21 and some STM32 processors have this).

If a custom bootloader is flashed, we can easily append some id and keys at the end of that flash page as well, since they will be write-once.

Currently, we are not using the EEPROM to remember settings or other things during runtime, but this is something we might add later (for settings to simplify the firmware code, but also for LoRaWAN 1.1 support which requires remembering some information across reboots).

Here is some earlier notes about processor selection from our etherpad:

matthijskooijman commented 4 years ago

We're aiming for STM32 now. KITT has compared a few options, extending to 64-pins rather than 32 or 48, since the plan is to do pick & placing and that gives some more pins for extendability and toggling different power domains.

The current plan is to try STM32L072RZ. I haven't looked at it in detail yet, will try to do so ASAP.

matthijskooijman commented 4 years ago

The STM32L072 series looks like a very good candidate. In particular:

It also has plenty of clocking options, running the CPU on the HSI (high-speed internal oscillator) and using the LSE (low-speed external crystal, i.e. 32kiHz) for precision timekeeping (for time of day / sleep intervals and wakeups / LoRa timestamping) would make sense. Not sure how this should be wired exactly (seems that the RTC and LPTIM low-power timer can both run against the LSE, but neither has (sub-second) input-capture to timestamp the LoRa TX-complete interrupt, but that can probably be done using a regular interrupt as well).