mikeayles

Joined 11 months ago

Karma
413
Submissions
76
Member since
Nov 25
I build complex technical tools, from automated hardware development pipelines to raycasting engines in CAD software.

The DOOM on Engineering Tools Series:

OpenSCAD-DOOM: Raycasting in a parametric CAD language, now playable in browser. (The Register)

KiDoom: DOOM rendered on PCB traces. #1 on HN. (The Register, Hackaday)

ScopeDoom: Vector rendering on an oscilloscope via audio DAC. #1 on HN. (The Register, Hackaday)

The Serious Work:

Phaestus: Compiler for physical products. Generates schematics, PCBs, enclosures, and firmware from natural language.

Bitwise-MCP: MCP server for embedded systems. Indexes 1000+ page reference manuals with hybrid keyword/semantic search.

TOKN: Token-Optimised KiCad Notation. A compact encoding format that reduces schematic token count by 92%, enabling LLM circuit generation. Includes benchmark suite comparing model performance on hardware tasks.

Engine Simulator: Thermodynamic diesel engine model at 0.1° crank resolution, vanilla JS in browser.

I specialise in solving "impossible" technical problems and shipping validated products.

[email protected] | mikeayles.com

View on Hacker News

Recent submissions

Comment · 1 month ago
The space is definitely heating up.

Flux.ai being the incumbent Silixon based out of the UK have been showing demos Quilter and DeepPCB for layout The recent OpenAI demo...

I went the other way and pre-designed sub circuits with a set of rules that allows simple merge assembly, unfortunately I didn't have the time or budget to continue with it, but I took the constrained approach as with hardware, things can't be 99%.

The one thing I will say, is that my experience of hardware engineers is very gatekeepy.

Any questions about the use of AI for any form of automation on forums/Reddit get shot down instantly and the OP's told 'skill issue' more or less. In my opinion, just as with software, most work is simple and should be automated, there will always be a need for the real engineering when it comes to high specification work, high volume optimisation and hardware debug (although Claude code is pretty handy at driving a Jlink)

Comment · 2 months ago
Good question. short version: it's a shared wall, not a per-request bump. one KV260, one model on the fabric at a time, so the rotation is global. but the ~25s is mostly software, not fabric-dark time. the PL reconfigure is ~1-3s via fpgautil, the rest is orchestration (daemon teardown, streaming the weights back into URAM, clock change, coherence check, chat-server reconnect). DFX keeping the sequencer + I/O live only recovers that 1-3s slice, and it fights the design, since the weights are smeared across every URAM column while a reconfigurable partition wants a contiguous pblock.

The swap needs a fresh bitstream at all only because four little ROMs are baked at synthesis: layernorm gammas, the activation-quant scale, two dequant tables. the embeddings already ride the boot-streamed weight image. make those four boot-loadable through the same path and a same-arch model hot-swaps with no reconfigure. There is basically zero margin at the moment to implement this.

which is a decent excuse for a 24h telemetry update.

Peak 46 concurrent connections monday afternoon, 61 uniques in the busiest half hour, ~6,600 requests / ~400k tokens total. At no instant did more than 2 inferences overlap (although it came close once). the fabric finishes a ~100-char reply in ~2ms of compute (end-to-end round-trip is ~20-60ms once you add network + server), so even with 40+ people connected the queue sits empty ~100% of the time. Worst 30-second window of the whole day was p95 59.9ms, and the heaviest burst (~200 requests in 5 minutes from one enthusiastic visitor) didn't even produce it. still ticking at ~37 connections this morning, latency flat.

That's the counterintuitive bit about a 20k tok/s model with short replies: the "single stream" is busy for milliseconds per request, so it timeshares across human typing speed essentially for free. the synthetic ceiling (2,000 concurrent requesters, p95 ~9.4s, zero errors) is ~40x past anything real traffic did. every actual visitor had the chip to themselves.

After this is all over, I'll do a post-mortem to see how it held up. I was really hoping for FP with the amount of effort this one took compared to my other submissions, which really would have stressed it, but I guess it was just a bit too niche!

Comment · 2 months ago
I 100% agree the model is basically useless. that was never the deliverable. the artifact here is the inference engine, not the model living in it. 3.16M params at character level is just what fits in ~3MB of on-chip SRAM.

Plus I treated it as a good learning experience to get better with FPGA's but also system design.

Comment · 2 months ago
Appreciated. and yeah, agreed the interesting comparison isn't "is this scalable as-is" (it isn't, PL fabric, cost, power), it's that the CIM / analog-compute startups you mention are chasing exactly this endpoint with real money and years of R&D, the bar for making something useful is brutally high.

However, if no-one made anything that was useless on the same thesis, a lot of these concepts would have never got off the ground. I would hazard a guess that people like taalas would have started with a (much much bigger) fpga to validate whether the approach was possible before committing to designing a chip big enough to fit an 8B model in it.

I just nerd sniped myself...

VP1902 could fit around a 500m model in, whereas a cadence protium rack of them could squeeze in a ~6B at 8bit, or a ~13B at 4bit. So accounting for the headroom of distributed compute, Llama 3.1 8B at 4bit. I don't want to even estimate how long synthesis and place and route would take on that!

Comment · 2 months ago
Just a quick test to see if i'm back
Comment · 2 months ago
You're correct, the flat line is aggregate only. the fabric is saturated from a few dozen active clients onward, so extra connections can't buy throughput, they just queue. per-user p50/p95 across that same sweep: 17ms/30ms solo, 450ms/545ms at 100, ~2s/2.4s at 500, 3.8s/4.4s at 1000, 6.3s/9.4s at 2000. zero errors or drops at every stage. It degrades as a well-behaved queue, not a cliff, but nobody would call 6s at the top end snappy.

The benchmark sweep is 2,000 concurrent active requesters hammering it constantly, real traffic is mostly lurkers, which cost a file descriptor and nothing else. the interactive feel actually gives out earlier than the queue math. The speculative-typing UI wants sub-second replies, and that budget blows around 100–150 simultaneous typists.

I've been logging the stats since it went live, unfortunately it didn't hit FP. Peak was 10 concurrent connections (13 uniques in the busiest half hour), ~580 requests and ~37k tokens served, and at no point did two people actually have an inference in flight at the same moment which would have been the real test for the queue, every visitor got the fabric to themselves, p50 ~23ms. so the 2,000-conn drill was not stressed today. the one blemish: a single window with p95 ~57s, which lines up with the model-rotation FPGA reconfigure rather than load. A request that arrives mid-reflash waits out the ~25s swap. if this thread sends 50× more people, the queue math above says it holds.

I need to discard the requests that overlap the model changeover for a truer result.

Comment · 2 months ago
Comment · 2 months ago
I started this about 10 weeks ago when the Taalas chatjimmy demo first did the rounds, Llama 8B baked into custom silicon, 17k tok/s for a single user. Their whole thesis is that inference is bound by reading the weights, so stop fetching them from far away. I wanted to see how far that idea stretches on a 'consumer hardware': every weight resident in SRAM, zero DRAM My chip only gives you ~3 MB to live in, so the model is 3.16M parameters and the tokens are characters, but the physics is the same bet. Only difference is their model is actually good!

The annoying part: I wanted this live last week, which would have landed the same day as the AMD acquisition news, on AMD's own silicon no less. Life got in the way, so here it is a week late instead.

Comment · 2 months ago
I'm using the AMD (Xilinx) K26. It's a Zynq Ultrascale+, the successor to the old classic 7000's. I'm running it on the KV260 dev board, because I'm using it for another side project.

The K26 has a quad core A53 core alongside the programmable logic (PL, or Fabric). The A53 is pretty weak, and doesn't have any hardware matmul operations, so despite the KV260 being sold as a 'vision ai starter kit' and the vitis object detection running on the arm cores, they're pretty weak cores for anything AI.

For my use, I need true determinism, so my vision pipeline is all implemented in the PL, and it was pretty disapointing that the vitis libraries are basically just opencv on linux, rather than really pushing the fabric. If I wanted probabalistic AI running on a CPU, then I sure as heck wouldn't choose a quad core A53.

Which led me to have a play with this, I saw the taalas/chatjimmy demo and wondered what I could push the fabric to.

The round trip time to DDR or CPU via AXI meant I had to keep the entire inference engine in fabric. The A53 is simply a pipe that gets a request from my server (which has a cloudflare tunnel to the real world for the live demo in the blog post) and manages a queue. So it feeds a string in, and gets a hopefully longer string back a few uS later.

It's all in verilog, because that's what i'm more used to. I did get Claude Code to do a moderate amount, as it's a side project on a side project after all, but pushing an FPGA to it's limit is definitely not as comfortable for it as it is writing a crud app in TS.

I'm using tinystories, as we are talking about megabytes of URAM/BRAM. If I used the DDR, it definitely would have been a real model, but that wasn't my goal. My goal was to hit 100,000tok/s, and even when I conceded on absolutely everything, with a token prediction size of 1tok, I topped out at 60,000tok/s. ?But increasing the window to make an actually plausible chat (story generator, it doesn't understand questions, you need to prompt it with 'once upon a time...' and it finishes it for example) I managed to break 20k tok/s.

I also created the lemmatised version, which was inspired by Kevin from the office (why use many word when few do trick) and trained a new model, I was expecting the output model to be smaller, but was suprised that it came out the same size, but it ran 30%ish faster. In hindsight it makes sense, the parameter count is fixed by the architecture, not the corpus, so training on compressed text doesn't shrink the model at all. What it does is compress the output distribution. The same story takes ~30% fewer characters to tell, so the effective speed goes up even though the per-token rate is identical. The dumbness is the optimisation.

Fully agree on publish early. The blog post with the live demo (a websocket straight to the board through a cloudflare tunnel, so you're genuinely talking to the fabric) is written and sitting in drafts while I fiddle with it. This thread is my peer pressure, it goes live in the next day or two.

Comment · 2 months ago
It will be, I'm just not happy with my blog post before making it live. The blog will have a live interactive chat and a link to the repo with the HDL.

I don't think anything I did was particularly novel, as I really just wanted to see how fast I could push a commodity FPGA to it's limit.

Scaling to an ASIC or getting into the billions of params is where the real engineering is! This was just a side project for a side project for me while the FPGA was idle

Comment · 2 months ago
AMD could have saved their money and used their own hardware! I've got a language model doing 60k tok/s on AMD hardware already, a Xilinx Kria K26 SOM, with the weights baked into URAM/BRAM with zero DRAM in the token loop. Same thesis as Taalas: single-stream decode is bandwidth bound, so stop fetching weights from far away.

Caveats stacked high, obviously. It's 3.16M parameters (tinystories, and I also have a kevin-speak lemmatised version), the tokens are characters, and the 60k record is 16 streams that each remember exactly one token of context, so it's blisteringly fast at saying nothing. The honest build with full context and KV caching still does ~19k tok/s on one stream though.

I keep messing with the blogpost with the live demo, but I'm planning on flipping it to live in the next day or two

Live from the official Hacker News API

A modern reader for Hacker News · SvelteKit + Skeleton