Starting with the Librem 14 laptop we are including fully liberated Embedded Controller (EC) firmware with all the source code available. This is something we set as a goal a long time ago, and now we are finally here. Let’s first start by explaining what the EC is and does.
A PC these days is a pretty complicated thing. It does not only consist of the main CPU (in this case the Intel Core i7 10710U mobile low voltage), but also a lot of peripherals. The main CPU is very good at what it is supposed to do as its main task, running the main operating system, but it is not so well tuned for lower level things like managing a keyboard matrix or (and this is quite amazing) powering itself up.
PCs have been around since the 1980s and their hardware design still shows this legacy. Already in early PCs there was a small helper CPU to handle the low level dirty work for the big one and this was the keyboard controller. The keyboard controller was a small microcontroller on its own running a very small program that helped the power up and down sequencing as well as managing a bespoke keyboard matrix [1]. Since then a lot has happened. Over the years as this keyboard controller grew and was assigned more and more tasks, it developed into the Embedded Controller.
With more tasks assigned to the EC, the software and its capabilities grew which makes it a pretty essential piece these days, especially for laptops. So the first thing the EC needs to do is to control the power up and power down of the machine, which means to enable or disable certain voltage domains, doing that in a controlled fashion honoring dependencies (often some power rails are derived from others), and also taking into account the power supply constraints of the main CPU in certain power modes. This is especially important for low power states like suspend to RAM where you just want to power what is needed. There are also other very interesting peripherals attached to the EC. Of course the EC controls the keyboard matrix, i.e. it assigns keypresses in that matrix to key scan codes sent to the main CPU.
There are also devices in the Librem 14 attached to PWMs (Pulse Width Modulator) which we want to get control over, like the CPU fans! Yes, there are two of them, we have 6 CPU cores with 12 threads in total. When running at full load a second heat spreader and fan helps to keep the CPU at acceptable temperatures, so rather than having one fan running at full throttle we have two fans running at still reduced speed. The main CPU communicates with the EC and tells it the CPU package temperature. The EC then decides based on an algorithm how fast the fans shall go. But you may not always want it the same way. Say, you are doing light web surfing at night in your bed and don’t want to annoy your partner. In that case you may choose to accept a bit warmer device but therefore silent. Some other time you may want to have the device as cool as possible, e.g. to prevent your hands from sweating even more on a warm summer day, but can accept more noise, like in an office. With the Libre EC we have that choice.
Also the power indicator LED is controlled by the EC. We have three colors to choose from, orange, green and white. They all share one PWM for common brightness control and can be turned on and off individually. The power indicator LED is located just above the F8 key and is mirrored additionally on the outside next to the power connector so that you can also see the power state when the LCD lid is closed. How the colors are used is now up to us! What I am currently implementing is this:
Why green for charging you may ask? Why not orange like everyone else? Well, actually, because I think it does not make sense. Red or orange are warning colors, these signal a “not good” state. But charging is a good state, while low battery warning is a bad state and I wanted to reserve orange for signaling a bad state. And of course white is neutral for a normal powered up state. Makes no sense to you? Well, you can change it, the code is open!
With the Librem 14 we also announced and implemented a notification LED, just above the F7 key. The idea behind that LED is basically the same as with the LED found in many smartphones. If the display is off or you are working on another virtual desktop applications can use this LED to signal something – incoming email or message, system notifications or whatever! We have implemented this as an RGB LED, all three channels controlled by a separate 8 bit PWM, so 256x256x256 colors! The userspace plumbing for this feature in PureOS has already been done for the Librem5 where we have exactly the same thing, an RGB PWM-controlled notification LED. I am pretty sure we will see a lot of creative use cases for these LEDs!
Another feature that has been requested frequently and which I am personally also looking forward to is better control over the battery charger. The EC indeed controls that and with the Libre EC firmware we now finally can have a say over it! Lithium Ion batteries are pretty good, they can store a lot of energy compared to their weight and they can also sustain pretty high current loads. But they are also a bit picky. They do not like to be deeply discharged, they do not like to be charged more than they are specified and they also do not like to be charged too often. So for example trying to charge them to 100% every time you connect a power supply is not such a brilliant idea for the overall battery lifetime.
ECs have to make some assumptions here. Keeping it safe and extending battery lifetime by not charging to 100% all the time will of course result in less runtime on battery in certain situations which some users may not appreciate. That’s why most devices by default always charge to 100% once they reconnect to a power source. The problem is though that users are often given no choice if they want that or not.
The EC can not know what my use case is, but I do. So I would like to be able to tell the EC to stop it and do as I wish, eventually accepting certain shortcomings. Most of the time my laptop runs from the charger and if I use the battery at all it’s to carry it from one power outlet to the next or from office to home and back. Knowing that I do not need a full charge I am totally fine with my battery having 80%, 70% or 60% (or less), I don’t care. And if I finally reach lower levels like 30% then I would like it to only recharge to, say, 80%, that’s enough for my use case and will last me weeks until I reach 30% again. Some other day I may know that I need to go on a train ride without power outlets, then I would like to be able to tell the EC to charge to 100% one time.
That’s what we can do now with the Libre EC. The charge controller in the Librem 14 is connected to the EC via I2C and can be programmed, it can be enabled and disabled, we can tell it the charging current to allow for slow charging (better for the battery but takes longer) or fast charging. And of course we can control the level up to which it shall charge. This will help to extend the battery lifetime significantly.
The userspace interface for this user control of LEDs, fans, battery etc. are still a bit in the works. Although we do not have to implement the full EC code from scratch since we base it on the EC code developed as free software from System76 [3], it is still a lot of work. The EC chip used in the Librem 14 was not yet supported, our Librem 14 hardware design is different in many details and on top we have additional features that were not reflected by the System76 code. We are working on adding all of that and will of course make the code public in our own repository as well as upstreaming as much as we can, we are already in touch with their maintainer.
And since it is the first time we have liberated EC firmware we also have quite a steep learning curve. Like I mentioned, PCs are complicated and so are the EC firmware requirements. But we are working hard on it! And it is taking shape. A lot is working already, powering up/down, charger control, PWMs.
We still need to work on main CPU sleep states as well as representation of user controllable settings into Linux userspace. And we want to do very thorough testing of all of that before we start shipping product. The EC is critical, it can brick the device or worse. We will see that the EC firmware can be recompiled and flashed in the field by everyone(*). Some of the before-mentioned features will come as a user serviceable firmware upgrades after shipment of the laptops has started, for which we will of course provide pre-compiled binaries too.
So stay tuned! This will be fun!
[1] https://en.wikipedia.org/wiki/Keyboard_matrix_circuit
[2] https://en.wikipedia.org/wiki/Pulse-width_modulation
[3] https://github.com/system76/ec/
(*) a failed EC flash can brick the laptop and only be recovered using
an external flash chip programmer. We can not take responsibility for
bricked devices when flashed with improper EC firmware, unfortunately. We will of course help to recover from flashing improper firmware, but eventually need to ask for cost reimbursement (like shipping).