This content is copied from our blog post on the same topic. Discuss the changes here!
Today, after long last, we’re shipping the Photon!
Over the past two years, we’ve shipped 50,000 Spark Cores to customers all over the world. We learned a lot from our first product, and we’ve fed those learnings into the development of the Photon. The Photon is better than the Spark Core in every way, and we couldn’t be more excited to share it with you.
The Photon is designed to be backwards compatible with the Spark Core, but there are some differences that you should be aware of if you’ve been using a Spark Core. Most of these changes are dramatic improvements, but they are differences nonetheless.
There’s a lot of content here, so if you want just the summary, here you go:
- The Photon includes a more powerful and more reliable Wi-Fi module, and you’ll have a lot more RAM and processing power at your disposal.
- There are a bunch of new hardware peripherals, and the Photon can be surface mounted (if you buy it without headers).
- We now have our own modules, the PØ and the P1, for sale alongside the Photon. Great for when you want to scale up manufacturing.
- The firmware includes a full RTOS (Real Time Operating System), and the Wi-Fi connectivity code will soon run alongside your code in a more intelligent way than it did on the Spark Core.
- We’ve made some awesome changes to our firmware to separate your code from the system code so that over-the-air firmware updates are BLAZING fast (a couple seconds to update).
- We fixed lots of bugs. Most of those fixes (and many of the improvements) will be available on the Spark Core as well in a few weeks, including significant reductions in memory consumption (both FLASH and RAM).
Ok! Now, for those who want all the details, let’s dive into what’s changed:
Hardware
From Texas Instruments to Broadcom. The Spark Core used a Wi-Fi module from Texas Instruments called the CC3000. The Photon includes an upgrade to our own Wi-Fi module - the PØ - which includes a Broadcom Wi-Fi chip (BCM43362) and a souped up microcontroller (STM32F205). Broadcom makes the Wi-Fi chips in most routers and phones, so their chips are best-in-class. Expect big improvements in stability.
Power consumption has been dramatically reduced, and you have access to better low power modes. Simply due to hardware changes (a better Wi-Fi chip and a switch-mode power supply), average power consumption has dropped from ~150mA on the Spark Core to ~80mA on the Photon. In addition, the Photon has many more options for low power modes, including modes where you can trade off Wi-Fi latency for power consumption, bringing your power consumption down closer to ~15mA. And if you’re creating a battery-powered product, you can put the Photon entirely to sleep and achieve power consumption as low as 160uA.
The Photon is surface mountable. Most of you have ordered Photons with headers, which fit into a breadboard and are great for prototyping. We also sell Photons without headers, which can be soldered directly to a circuit board either with a soldering iron or with a reflow oven (using castellated edges). When you mount the Photon down to a PCB, you also have access to the USB data lines, the LED pins, and the SETUP button pin so that you can expose those features on your own circuit board.
The Photon has two different antenna options on every board. Every Photon includes both a chip antenna and a u.FL connector (for external antennas). By default, the Photon will use the chip antenna, but you can switch to the u.FL connector with one line of code.
The Photon has lots of new peripherals available. The Spark Core had UART, SPI, and I2C peripherals exposed, as well as ADCs (analog pins) and timers (PWM pins). The Photon has the same capabilities, plus a second SPI bus, two Digital to Analog Converters (DAC), a CAN bus, and I2S. These peripherals are not all supported in software yet, but they will be supported soon. The WAKEUP and VBAT pins are also exposed, which helps with low power modes.
Cleaner layout and fancy colors. We did some fancy footwork with the hardware design to make it extra pretty. The most noticeable changes are that the LED on D7 is exactly where you’d expect it to be, and we’ve adopted a new color scheme: matte black soldermask and cyan silkscreen.
A few things were removed. We took off the external flash to save space (since we had a lot more internal flash to work with), and removed the A6 and 3V3* pins to make room for other new features. If you want external flash, check out our P1 module, which includes external flash inside the Wi-Fi module.
We’ve got our own Wi-Fi modules for manufacturing at scale. The PØ, the module inside the Photon, is available for $10/unit (cloud service included). We also sell a variation called the P1 which is a tad bigger than the PØ but includes an antenna and external flash; the P1 is available for $12/unit (cloud service included). Both of these modules include the STM32F205 microcontroller, so you don’t need an additional processor to run your device.
Firmware
We decreased the time to do an Over-the-Air firmware update from more than a minute to just a few seconds. One of the biggest issues with the Spark Core was that over-the-air firmware updates could be somewhat slow, taking a minute or more. This slows down development, so people would do their development locally and program over USB. We’ve made some improvements (detailed below) that dramatically increase the speed of an OTA update so most updates now take just a couple of seconds. We hope that will speed up your development and make the cloud a bit more useful.
We built a Hardware Abstraction Layer (HAL). In order to compile one firmware application against two different target architectures (the Core and the Photon), we built a Hardware Abstraction Layer, or HAL, that makes it much more straightforward to port our firmware libraries to any hardware! This HAL also made possible Bluz and will be used heavily in the Electron. We can’t wait to see which hardware platforms you’ll adapt our firmware libraries to next!
We combined and simplified our firmware libraries into one repository. Our firmware used to be broken up into three libraries: the core firmware library, the communication library, and the library of common drivers. We’ve now combined all of our firmware into one repository and reorganized the firmware so it’s easier to pull out separate bits and pieces if you need them.
We added an RTOS (FreeRTOS) to provide scheduling for the Wi-Fi connectivity code. Real-time operating systems, or RTOSes, provide some of the features of a full operating system but with a very small amount of overhead. Professional engineers working with microcontrollers will typically use an RTOS to add multithreading and lightweight memory management while still allowing real-time hardware interactions that a system with a full OS (e.g. Linux) would not be able to do. We’ve implemented FreeRTOS on the Photon so that we can run the system code (mostly connectivity stuff) and your application in two separate threads. You can also use the RTOS for your own multithreaded code; as we iterate on our firmware, we’ll be providing simple APIs to help you do this in an Arduino-y kind of way.
We separated the system code and your application code into three separate binaries that are dynamically linked and can be reprogrammed separately. A lot of the improvements in OTA speeds came from separating system and application code. The system code can be hundreds of kilobytes, whereas your application code might only be a few KB. If an OTA update requires rewriting the entire program as it does on the Core, that means we’re spending a lot of time downloading the same system code that’s already on the device. By splitting the system and application, we can provide a faster and lower-risk over-the-air firmware update.
We made lots of smaller improvements to performance and stability. These improvements will be released as firmware v0.4.0, which will be available on the Spark Core as well in a few weeks. Here’s a comprehensive list of the improvements we’ve made:
Enhancements:
-
loop()
iteration rate increased by 1000 times - from 200 Hz to over 200 kHz! - Compiler: Removed all warnings from the compile (and made warnings as errors) so compiler output is minimal.
- Debugging: SWD Support, thanks to Elco Jacobs. #337
-
Spark.publish()
returns a success value - #388 -
Spark.process()
as the public API for running the system loop. #347 - Sleep no longer resets (on the Photon) #283
- Support for application code outside of the firmware repo. #374
- MAC Address available in setup via ‘m’ key. #352
- SoftAP setup on the Photon
-
Spark.sleep()
changed toSystem.sleep()
and similarly fordeviceID()
#390 - Listening mode uses existing serial connection if already opened. #384
-
Spark.publish("event", PRIVATE)
shorthand - #376 - Improved integrity checks for firmware images
- Added additional safe/recovery mode in bootloader (> 6.5 sec : restore factory code without clearing wifi credentials)
- Enabled CRC verification in bootloader before restoring/copying the firmware image from factory reset, ota downloaded area etc.
- Added ‘program-serial’ to build target to enter serial ymodem protocol for flashing user firmware (Testing pending…)
- Cloud string variables can be re-defined #241
- Removed hard-coded limit on number of functions and variables #111
- Parameterized function callbacks, lambda support for functions #311
- C++ STL headers supported
- Can duplicate the onboard RGB LED color in firmware. #302
-
WiFi.selectAntenna()
- select between internal (chip) and external (u.FL) antenna on Photon: #394 -
WiFi.resolve()
to look up an IP address from a domain name. #91 -
System.dfu()
to reboot the core in dfu mode, until next reset or next DFU update is received.
Bugfixes:
- SOS calling
Spark.publish()
inSEMI_AUTOMATIC
/MANUAL
mode - Subscriptions maintained when cloud disconnected. #278
- Fix for events with composite names. #382
-
WiFi.ready()
returning true afterWiFi.off()
in manual mode. #378 -
Serial.peek()
implemented. #387 - Mode button not working in semi-automatic or manual mode. #343
-
Time.timeStr()
had a newline at the end. #336 -
WiFi.RSSI()
caused panic in some cases. #377 -
Spark.publish()
caused SOS when cloud disconnected. #322 -
TCPClient.flush()
discards data in the socket layer also. #416
More to come
We still consider our platform a work-in-progress, and while this is a huge step forward for us, it’s still just one more step on the journey. We’re eager for your feedback; if you encounter bugs or want to request new features when you receive your Photon, create a Github issue or contribute a Pull Request; we’d love your help!