RSSAmplifier

Blog

Cliffle

Fortuna Eruditis Favet

cliffle.comRSS feed ↗63 posts

Latest posts

Crash recovery in 256 bytes

(This continues my series of posts on the exhubris tools I’m building, to enable more people to use Hubris in their embedded systems.) One of Hubris’s strongest features is its ability to handle crashes in drivers and other application logic. It leaves the specific crash handling behavior up to the application programmer through a mechanism called a supervisor. In this post I’ll look at why I made…

Revisiting Hubris appconfigs

So in my day-job over at Oxide we’ve built this nice embedded operating system called Hubris . If you follow my blog, you’re probably aware of it. I also build a lot of embedded electronics outside my day-job, and people sometimes ask me (often excitedly!) if they’re using Hubris. The answer so far is “no.” This is for a variety of reasons, but probably the biggest: it’s actually quite difficult…

From Hubris To Bits

The embedded platform we’ve built for firmware at Oxide is called Hubris . It’s unusual for a microcontroller operating system, and probably the biggest thing that makes it unusual is its use of separately-compiled tasks. Most firmware applications mash all of their task and OS code together in a common memory space, which is simple and efficient, but can lead to subtle bugs. Hubris instead places…

Putting custom firmware on the WASD CODE v2

I have a WASD CODE v2 tenkeyless keyboard, which has been my daily driver for work since about 2017. It’s a great keyboard… mechanically. But its control electronics are fixed-function and don’t quite work the way I want — to say nothing about fancy features like additional key layers. So I fixed it. Now it runs QMK . (Or some bare-metal custom Rust firmware.) This has let me… Try out QMK without…

lilos v1.0 released

After five years of development, something like seven art projects, one commercial product , and many changes to the dark corners of the Rust language, I’ve decided lilos is ready for a 1.0 release! Some parts I’m excited about include: As of this release, the lilos APIs are entirely cancellation-safe. This release contains contributions from five other people, bringing the total number of…

The server chose violence

I’m continuing to reflect on the past four years with Hubris — April Fool’s Day was, appropriately enough, the fourth anniversary of the first Hubris user program, and today is the fourth anniversary of the first kernel code. (I wrote the user program first to help me understand what the kernel’s API wanted to look like.) Of all of Hubris’s design decisions, there’s one that gets a “wait what”…

Who killed the network switch?

We found a neat bug in Hubris this week. Like many bugs, it wasn’t a bug when it was originally written — correct code became a bug as other things changed around it. I thought the bug itself, and the process of finding and fixing it, provided an interesting window into our development process around Hubris. It’s very rare for us to find a bug in the Hubris kernel, mostly because it’s so small. So…

I made a thing to help you make a thing out of a keypad

I do a lot of electronics projects in my spare time, and I tend to try to make reusable parts to save myself effort in the future. Because I have to order ingredients in certain quantities, I often wind up with more than I need for my project. So I’ve opened a Tindie store, called Overengineered Widget Laboratories. Right now there’s one product in the store, called Keypad:GO . See, I built a…

Making my website faster

Since I started running this site in 2011, I’ve adhered to some principles to make it fast, cheap, and privacy-respecting. As few third-party cross-domain requests as possible – ideally, none. No trackers (which tends to follow naturally from the above). Use Javascript but don’t require it – the site should work just fine with it disabled, only with some features missing. No server-side code…

Planning to redirect traffic to HTTPS

tl;dr: Check that your RSS reader is using an HTTPS URL, because the HTTP one will start redirecting soon, and you probably want to find out if it breaks. Edit from four days later: I’ve flipped the switch on this and, from the logs, it doesn’t seem to be messing anybody up. It’s been just about four years since I finally got HTTPS and HTTP/2 working for this site. During that time, I’ve seen…

An STM32 WFI bug

I really like the STM32 series of microcontrollers in general. They’re generally quite reliable, the peripherals are well tested, and more often than not I can just grab one off the shelf and not think about it too much. However, like every microcontroller, they do contain implementation bugs, so it’s always important to read the “Errata Sheet” (or in ST’s language, “Device Limitations”) when…

Mutex without lock, Queue without push: cancel safety in lilos

I’m trying to do something kind of unusual with lilos : in addition to almost all the APIs being safe-in-the-Rust sense, I’m also attempting to create an entire system API that is cancel-safe. I’ve written a lot about Rust’s async feature and its notion of cancellation recently, such as my suggestion for reframing how we think about async / await . My thoughts on this actually stem from my…

Getting file/line in await traces

I recently posted about my debugger for async Rust , which can generate what I call “await-traces” for async code that’s suspended and not currently running. I mentioned at the time that it appeared possible to get the source code file name and line number corresponding to the await points, but left that for future work. This is an update describing that future work.

Composing concurrency in drivers

I recently published an article suggesting a different way of looking at async and await in Rust . In it, I discussed strategies for implementing state machines, and explained why I like async as a tool for building such state machines, even without threads. In this post I’ll work through an example of why I’m so excited about this technique, by building a real driver for a notoriously tricky bus…

How to think about `async`/`await` in Rust

(This is a section of the lilos intro guide that people seemed to like, so to increase its visibility, I’m lifting it up into its own post and expanding it a bit. I hope this is a useful companion piece to the post on async debugging I posted this morning.)) Some documentation of Rust async and await has presented it as a seamless alternative to threads. Just sprinkle these keywords through your…

Writing a basic `async` debugger

I’m a big fan of Rust’s async feature, which lets you write explicit state machines like straight-line code. One of the operating systems I maintain, lilos , is almost entirely based on async , and I think it’s a killer feature for embedded development. async is also popular when writing webservers and other network services. My colleagues at Oxide use it quite a bit. Watching them work has…

Safely writing code that isn't thread-safe

One of the nice things about the Rust programming language is that it makes it easier to write correct concurrent (e.g. threaded) programs – to the degree that Rust’s slogan has been, at times, “fearless concurrency.” But I’d like to tell you about the other side of Rust, which I think is under-appreciated. Rust enables you to write programs that are not concurrent. This feature is missing from…

Why Rust mutexes look like they do

One of the common complaints I hear from systems programmers who try Rust is about mutexes , and specifically about the Rust Mutex API. The complaints usually go something like this: They don’t want the mutex to contain data, just a lock. They don’t want to have to manage a “guard” value that unlocks the mutex on drop – often, more specifically, they just want to call an unlock operation because…

RSS Feed Back On

At some point in the past… I dunno, two years or so, it appears that my RSS feeds broke. I use Zola to generate this site, and they don’t have much in the way of a cross-version compatibility guarantee – minor version updates routinely break my templates. (I’m currently stuck on an older version because of this bug .) They appear to have changed the names of the RSS-related settings, causing my…

On Hubris And Humility

Last week I gave a talk at the Open Source Firmware Conference about some of the work I’m doing at Oxide Computer, entitled On Hubris and Humility. There is a video of the talk if you’d like to watch it in video form. It came out pretty alright! The conference version of the talk has a constantly animated background that makes the video hard for some people to watch. OSFC doesn’t appear to be…

Vanilla sweet potatoes

This is my favorite sweet potato preparation. It produces a creamy puree with a texture like mashed potatoes, but with a flavor that’s somewhere between a side dish and a dessert.

Oatmeal Lace Cookies

This is based on a recipe from my mom, who called these cookies “Alexandrites.” Most folks online seem to call them “lace cookies.” Either way, they are delicious. I’ve tweaked these to suit my preferences, of course – while my recipe may be marked “alpha” hers has decades of cookies behind it.

Sorghum gingersnaps

These cookies come out small, which is good, because it’s hard to stop eating them. That’s why I only bake half a batch at a time. Sorghum syrup may not be a thing where you live. You can try substituting molasses or date syrup. (I haven’t tried either.) This recipe is derived from several online recipes, with a particular influence from Rebecca Blackwell’s recipe .

Boosted cinnamon rolls

This is based on this a recipe from King Arthur Flour , but has been optimized for how I personally prefer cinnamon rolls: with citrusy frosting and a lot of cinnamon taste. It turns out that adding a carefully chosen amount of freshly ground black pepper to cinnamon causes it to taste more cinnamony when it comes out of the oven. Too much pepper, and it tastes like pepper (which I also like, but…

Citrus cream cheese frosting

This frosting is what I prefer on cinnamon rolls. It comes out flavorful and sweet, but not too sweet – and the salt helps to bring back some of the complexity of the citrus that would otherwise be lost to the sugar.

Tangy collard greens

I like my collard greens soft but not mushy, with a mix of salty and sour flavors and not too much sugar. You can achieve this by braising, but I use an electric pressure cooker – it’s much faster. This is derived from a bunch of Internet recipes and then tuned to my taste. This recipe can be doubled, but you may run out of space to steam the greens. You can do it in batches since they’ll shrink a…

Basic granola

Oats have been easier to get than good granola recently, so I’ve taken to making my own. This is remixed from a friend’s recipe.

Saag Whatever

I’m referring to this as “saag whatever” because whether to add mixins – such as paneer, potatoes, or vegetables – is up to you. The recipe doesn’t particularly care as long as your mixins don’t add a bunch of liquid. Boiling or roasting some small potatoes in advance, or alongside, makes for an easy saag aloo. This calls for frozen spinach as a hack to reduce prep time and keep the result green.…

The First-Mover Allocator Pattern

(I’ve updated this pattern, since a lot has changed since 2020. The recommendations here should be ready for the Rust 2024 edition, and are closer to correct in a post-pointer-provenance world.) Here’s another useful Rust pattern. Like the Typestate Pattern before it, I wrote this because I haven’t seen the sort of obsessively nerdy writeup that I wanted to read. And, as with the Typestate…

Accessibility Updates

Since it looks like some folks have been actually reading my blog, I’ve made a pass over the site, looking for accessibility problems. I have increased visual contrast and made links within articles slightly more obvious. The comments in code samples are still under the WCAG recommended constrast level, but they’re generated by a third party syntax highlighting library, so fixing them is more…

Let The Compiler Do The Work

( Series Overview ) In this series so far, we’ve taken a C program and converted it into a faster, smaller, and reasonably robust Rust program. The Rust program is a recognizable descendant of the C program, and that was deliberate: my goal was to compare and contrast the two languages for optimized code. In this bonus section, I’ll walk through how we’d write the program from scratch in Rust. In…

Making Safe Things From Unsafe Parts

( Series Overview ) In part 4 we took the unsafe code that deals with treating arrays of f64 as arrays of vectors, and we corralled it into a safe API. In this installment, we’ll look at the remaining reasons why advance is an unsafe fn , and make it safe — not by removing all the unsafe , but by narrowing it down. This one’s a doozy — the remaining changes to advance are hard to separate, so I’ve…

A More Perfect Union

( Series Overview ) In part 3 we found that our use of uninitialized memory was a premature optimization that didn’t actually improve performance. This left us with only one remaining unsafe function, but, boy, is it a doozy. In this part, I’ll begin the process of corralling its unsafe optimizations into more clearly safe code, by replacing arbitrary pointer casting with a lightweight…

Measure What You Optimize

( Series Overview ) In part 2 we introduced Rust references, and this was enough to convert one of our inner functions into safe Rust. The others are still unsafe . There are several reasons for this. In this, the briefest of sections, we’ll tackle the easiest one: deliberate use of uninitialized memory.

Why Learn Rust the Dangerous Way?

( Series Overview ) I think Rust is a great tool for C programmers to have in their arsenals. But Rust tutorials tend to start with higher-level concepts, focusing on what can be done with safe code and treating unsafe code as the exception. This can be alienating to us hardcore low-level programmers. It’s like offering a course on blacksmithing but then spending all your time talking about how to…

References Available Upon Request

( Series Overview ) In the first part of this tutorial we took an optimized C program and translated it to an equivalent Rust program, complete with all the unsafe weirdness of the original: uninitialized variables, pointer casting and arithmetic, etc. In this section, we’ll begin using Rust’s features to make the program incrementally more robust, while keeping performance unchanged.…

You Can't Write C in Just Any Ol' Language

( Series Overview ) In this part of the series, we’ll take a grungy optimized C program and translate it, fairly literally, into a grungy optimized unsafe Rust program. It’ll get the same results, with the same performance, as the original.

Making really tiny WebAssembly graphics demos

I’ve been studying WebAssembly recently, which has included porting some of my m4vga graphics demos . I started with the Rust and WebAssembly Tutorial , which has you use fancy tools like wasm-pack , wasm-bindgen , webpack , and npm to produce a Rust-powered webpage. And that’s great! But I want to know how things actually work, and those tools put a lot of code between me and the machine. In this…

The Typestate Pattern in Rust

The typestate pattern is an API design pattern that encodes information about an object’s run-time state in its compile-time type . In particular, an API using the typestate pattern will have: Operations on an object (such as methods or functions) that are only available when the object is in certain states, A way of encoding these states at the type level, such that attempts to use the operations…

Rewriting m4vgalib in Rust

If this isn’t your first time visiting my blog, you may recall that I’ve spent the past several years building an elaborate microcontroller graphics demo using C++. Over the past few months, I’ve been rewriting it — in Rust . This is an interesting test case for Rust, because we’re very much in C/C++’s home court here: the demo runs on the bare metal, without an operating system, and is very…

Prefer Rust to C/C++ for new code.

This is a position paper that I originally circulated inside the firmware community at X . I’ve gotten requests for a public link, so I’ve cleaned it up and posted it here. This is, obviously, my personal opinion. Please read the whole thing before sending me angry emails. tl;dr: C/C++ have enough design flaws, and the alternative tools are in good enough shape, that I do not recommend using…

Racing the Beam

This post is the fourth in a series looking at the design and implementation of my Glitch demo and the m4vgalib code that powers it. In part three we took a deep dive into the STM32F407’s internal architecture, and looked at how to sustain the high-bandwidth flow that we set up in part two . Great, so we have pixels streaming from RAM at a predictable rate — but we don’t have enough RAM to hold an…

A Glitch in the Matrix

This post is the third in a series looking at the design and implementation of my Glitch demo and the m4vgalib code that powers it. In part two , I showed a fast way to push pixels out of an STM32F407 by getting the DMA controller to run at top speed. I described the mode as follows: It just runs full-tilt, restricted only by the speed of the “memory” [or memory-mapped peripheral] at either side……

Pushing Pixels

This post is the second in a series looking at the design and implementation of my Glitch demo and the m4vgalib code that powers it. Updated 2015-06-10 : clarifications from reader feedback. For the first technical part in the series, I’d like to start from the very end: getting the finished pixels out of the microprocessor and off to a display. Why start from the end? Because it’s where I started…

Introducing Glitch

Hey, look! I made a little graphics demo!

Switching this site from Jekyll to Hakyll

Update from four years later: I’ve switched away from Hakyll. These notes are here for their historical value only. I used to manage this site with Jekyll . I’ve now switched to Hakyll . Here’s my reasoning and some notes on how it went.

Project Loon

While I’ve been blogging about my personal projects off and on, I’ve been awfully quiet about my day job. Now I can tell you why.

My Recommended Publicfile Patches

While djb is perhaps best known for writing qmail , he also wrote a web server, publicfile . Like his other software, publicfile is simple and robust. I use it to serve this site, among other software . Characteristically for djb, publicfile is pretty minimal out of the box. Here are a few patches I applied to the source to make my server faster, more flexible, and easier to use.

Attacks on my Server: The Data

I try to maintain a reasonably secure webserver. A webserver is a computer, connected to the public internet, that does things (serves pages, etc.) whenever anyone asks it to. This makes it an easy thing to attack: the first step toward attacking a computer is usually getting it to do your bidding, and a webserver does your bidding every time you click a link. My system logs show that I get…

SSH Usernames Used in Attacks On My Server

This is broken out from the longer article, Attacks On My Server: The Data . This data covers only the period between 2012-12-26 22:41 and 2013-01-21 17:05, TAI (which is roughly UTC for our purposes). Points of interest: 28,889 unsuccessful attack attempts. (I’m assuming that any successful attacks have covered their tracks and are not represented here.) 2,185 unique usernames were tried.…