Toasty, an async ORM for Rust

Toasty is an asynchronous ORM for the Rust programming language that prioritises ease of use. Toasty supports SQL and NoSQL databases, including DynamoDB and Cassandra (soon).
We can see users being created (in memory).  It's possible to use the underlying SQLite driver as well.

Demystifying Alignment and Memory Layout in Rust

Posted in Work > Software Engineering > Rust Projects (Rustlang)

This is by far the best article I've seen on the subject in terms of simplicity and explaining quickly what it means to have a #[repr(C)] annotation on types.
The most eye opening bit are the visuals, with first the C representation.  Notice how there's extra padding, to ensure everything is byte-aligned. Consider,
#[repr(C)] struct Foo { tiny: bool, normal: u32, small: u8, long: u64, short: u16, }
  1. tiny: single byte, padded to 4 bytes so as to be byte-aligned. It's surprising that we are wasting 3-bytes and 7-bits to represent 1 bit!!
  2. small: This is a single byte, but since the struct's largest value stored is a long (u64), which needs 8-bytes, this is padded as 1 byte + 7 by ...(continued)

Journey into no_std: Padding u8 values using 2-bytes

Posted in Work > Software Engineering > Rust Projects (Rustlang)

Let's look at some code first
impl fmt::Write for ByteMutWriter<'_> { fn write_str(&mut self, s: &str) -> fmt::Result { let cap = self.capacity(); for (i, &b) in self.buf[self.cursor..cap] .iter_mut() .zip(s.as_bytes().iter()) { *i = b; } self.cursor = usize::min(cap, self.cursor + s.as_bytes().len()); Ok(()) } }
This the meat and potatoes, although I haven't had time to optimise this for performance by any means. Astute readers are welcome to comment and share any improvements this can use.
We can also write this in a functional style. A mutable iterator is created into the shared slice buf and then z ...(continued)

Journey into no_std: copying a &[u8] into a u8

Posted in Work > Software Engineering > Rust Projects (Rustlang)

Others have made the distinction that a [u8] (a Dynamically-sized view into a contiguous sequence [T]) is ideally referred to as a bare slice.  We can make the distinction that a shared slice type is &[T] and one that is mutable is a &mut [T].
Slices are basically a ptr and the length of the "view", and therefore have twice size of pointers (when compared to Sized types).
let pointer_size = std::mem::size_of::<&u8>(); assert_eq!(2 * pointer_size, std::mem::size_of::<&[u8]>());
There's a handy function core::array::from_fn which can be used like this
fn main( ...(continued)

Dynamic dispatch (and downcasting) in Rust isn't always a good idea

Posted in Work > Software Engineering > Rust Projects (Rustlang)

Traits and Trait objects are one of the best parts of Rust, but generally have not had a need to reach for a Box<dyn FooTrait> in a long time, beyond boxing std::error::Error. I normally reach for generics with impl FooTrait and you can get a lot done with generics (static dispatch).
Here's a terrible contrived example that I came up with, and yes, it is horrible! I promise though, it gets much better towards the end. Do note there will be some warnings as I haven't fully cleaned everything up for RA and Clippy offences - let's go!
As someone mentioned on Discord, Any is a poor man's enum.  This code is a great idea of trying to solve something, and wr ...(continued)

TIL from Solving a Simple CS Interview Question, and profiling with Flamegraph and Heaptrack in Rust

Posted in Work > Software Engineering > Rust Projects (Rustlang)

Failures are unexpected, but they are also a great learning opportunity, and I've decided to do just that.
I was asked a super simple question, that unexpectedly had me try to solve it in a totally wrong context, and that made me loose sight of the question in the first place.

My first mistake...

My brain immediately switched into "hmm, what's the best way to solve this in Rust at 10,000ft...", and the first thing I wrote was something along the lines of "pub struct SellerItems<Vec<(HashMap<_>)>>" or something like that.  It was bloody awful and my brain shutdown. Taking me outside my comfort zone, was the requirement of writing "pseudocode" in a Google doc.  No NeoVim, Rust-analyzer, nada... niet!
Instead, I should have taken a ...(continued)

HOWTO create a bash script to use VeraCrypt

In this video on my new channel I walk you through the process of putting together a simple bash script to use the VeraCrypt CLI to quickly generate an encrypted container. In a later fix (off screen), I also ensured that the password is not leaked to STDOUT's history with some shell redirection
echo "" printf '%s\n' \ 'WRITE THIS DOWN IN A SECURE PLACE WITH A CRAYON' "$1" \ 'Hide it in a dark hole, darker the better!' 1>&2 echo "" do_log "INFO VeraCrypt file ${VERACRYPT_FILE} mounted at /Volumes/${VERACRYPT_MOUNT_PATH}" # vim: ts=4:sw=4:sts=4:noet:ft=sh
Please do comment on whether you found this useful and I hope to make this public, during the coming week.

Getting Started with NVIDIA Jetson Orin Nano with help from Shawn Hymel

Having been a long time fan of SparkFun, any probably most of us in the Electronics and maker space, have at least at some point, seen Shawn with his bright red bow-tie and wonderful Video content.
Couple weeks ago, I decided to dust of an older Jetson Xavier Nano but stumbled on a post by Shawn featuring a more up to date "Orin Nano".  Price wise, the 8GB model was more accessible as I'm still just playing around in the ML space, and it is a decent starter platform.
Since my board was to run the latest Jetpack v6.x I realised (with Shawn's help) I would need to use the SDK Manager approach, and this involves running Ubuntu 22.04 LTS.

Starter code-bases - Are they worth it? Not everyone thinks so.

Starters are popular on Github. Try googling for "Node starter" or "Python starter" (which you don't need really). But this concept makes more sense say for a Node Webpack and Typescript starter. I asked about a C++ (Cpp) starter on Reddit and got a bit of flame - which is fair. This is because I partially recalled the ModernCppStarter, which I had used ages ago.
I also used the terminology FFI and they hate this as they are used to "extern C". You can see some of the comments here.
This is less of a "thing" in specific languages such as C++ / Rust etc as we don't use starters, just the language and curate the best dependencies for the task at hand.
The "Starter" concept is more pre ...(continued)

Avoiding the Arduino Portenta H7 "Orange LED of Hell" with STM32CubeIDE

Whilst working on the earlier UART code with the Portenta H7, I wanted to ensure I was running the correct SMT32 power config, and decided to generate the config and run this on my Portenta H7.
Unfortunately, the STM32CubeIDE tools flash into memory 0x08000000 instead of 0x08040000, the significance here is that the bootloader resides between these two addresses. When the bootloader is effectively wiped from the H7, its Power Management controller IC (PMIC) is no longer correctly configured at cold-start, and this renders your board as DOA with the "Orange LED from Hell".

Post Archive