{
  "authors": [
    {
      "name": "Kolja Wawrowsky",
      "url": "https://wawrowsky.com/"
    }
  ],
  "description": "Imaging scientist, Apple-platform developer, and independent AI researcher. Building instruments that make complex systems easier to see, measure, and remember.",
  "favicon": "https://wawrowsky.com/favicon.svg",
  "feed_url": "https://wawrowsky.com/feed.json",
  "home_page_url": "https://wawrowsky.com/",
  "icon": "https://wawrowsky.com/og-default.png",
  "items": [
    {
      "authors": [
        {
          "name": "Kolja Wawrowsky",
          "url": "https://wawrowsky.com/"
        }
      ],
      "content_html": "\u003cp\u003eIn 2010 we ran a control experiment that every live-cell imaging lab runs sooner or later. Before trusting a multi-day time-lapse on the confocal, we needed to know whether the cells would survive it: sixty hours in a stage-top incubator, with heat, CO₂, humidity and a laser passing over them every five minutes.\u003c/p\u003e\n\u003cp\u003eThe cells were HeLa expressing FUCCI, the cell-cycle reporter that makes this easy to read by eye. Nuclei glow red in G1, turn yellow at the G1/S transition when both reporters are present, and glow green through S, G2 and M. After division the daughters go briefly dark, then turn red again. A healthy population keeps cycling through those colours. A stressed one stalls.\u003c/p\u003e\n\u003cp\u003eWe watched the movie, saw cells dividing, and moved on. That was the whole analysis.\u003c/p\u003e\n\u003cp\u003eThe raw data didn\u0026rsquo;t survive the following sixteen years. What did survive was a single QuickTime export, carried from backup to backup. This September I gave that file to Claude Code to see how much it still held. The answer turned out to be: almost everything.\u003c/p\u003e\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/before-after.jpg\"\n\t\t\talt=\"Side-by-side: the original 2010 video frame on the left, the same frame with nucleus outlines coloured by cell-cycle phase and white rings on recent divisions on the right.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eFrame 461, 38 h 25 min.\u003c/strong\u003e Left: the 2010 export as it was. Right: the analysis, with nuclei outlined by phase call (red G1, yellow G1/S, green S/G2/M) and white rings on divisions in the preceding hour.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003ch2 id=\"what-survived\"\u003eWhat survived\u003c/h2\u003e\n\u003cp\u003eThe file is 37 MB. Its header says it was written on 4 June 2010 at 17:19 UTC by \u003ccode\u003eCoreMediaAuthoring 700, CoreMedia 484.5, i386\u003c/code\u003e: an \u0026ldquo;Export for iPod/Apple TV\u0026rdquo; from the Snow Leopard era. That\u0026rsquo;s the date of the export, so the imaging happened some time before it. Inside are 721 frames of 720 × 720 pixels, 8-bit colour, with the transmitted-light image and both fluorescence channels merged into one picture. No objective, no pixel size, no laser powers, no channel names. By any sensible standard it\u0026rsquo;s a presentation file, not data.\u003c/p\u003e\n\u003ch2 id=\"getting-the-channels-back\"\u003eGetting the channels back\u003c/h2\u003e\n\u003cp\u003eThe merge is less destructive than it looks. The grey transmitted-light (TM) image adds the same amount to red, green and blue, while the FUCCI colours were rendered into red and green only. So the channels come apart by subtraction: transmitted light is roughly the blue channel, FUCCI red is red minus blue, and FUCCI green is green minus blue. With the timestamp in the corner masked out, that gave three clean 721-frame stacks.\u003c/p\u003e\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/unmix.jpg\"\n\t\t\talt=\"Three grey-scale panels: transmitted light showing cell outlines, the red channel showing G1 nuclei, and the green channel showing S/G2/M nuclei.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eOne frame, three channels,\u003c/strong\u003e recovered from the merged colour video: transmitted light, FUCCI red, FUCCI green.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003ch2 id=\"getting-the-time-back\"\u003eGetting the time back\u003c/h2\u003e\n\u003cp\u003eWith the metadata gone, the frame interval had to come from the picture. The burned-in clock was readable when enlarged. Frame 1 reads 00:05:00 and frame 100 reads 08:20:00. Frames 360 and 720 briefly looked like 106 and 212 hours, until it became clear that the leading \u0026ldquo;0\u0026rdquo; was a small \u0026ldquo;d\u0026rdquo;: 1d 06:00:00 and 2d 12:00:00. Every stamp agrees on five minutes per frame and sixty hours in total.\u003c/p\u003e\n\u003ch2 id=\"finding-nuclei\"\u003eFinding nuclei\u003c/h2\u003e\n\u003cp\u003eNuclei were segmented with StarDist, a deep-learning model for round-ish objects, using its pretrained fluorescence model on the brighter of the two FUCCI channels at each pixel. Upscaling the frames made it split nuclei, so it ran at native resolution. Across the movie it found 109,950 nuclei, growing from 52 in the first frame to about 290 at the end.\u003c/p\u003e\n\u003ch2 id=\"finding-divisions-the-old-way\"\u003eFinding divisions the old way\u003c/h2\u003e\n\u003cp\u003eFUCCI has a blind spot for tracking. After anaphase the green signal disappears, and the daughters stay dark for one to two hours before red appears. A tracker that only sees fluorescence loses every cell at every division, exactly when you most want to follow it.\u003c/p\u003e\n\u003cp\u003eThe fix is a trick every microscopist of my generation knows. Cells round up for mitosis, and in transmitted light a rounded cell carries a bright, thick halo. Run an edge filter over the image and those halos are the strongest signal in the frame. A circle finder with a score for how complete the rim is picks them out, and a filter for spots that never move removes the dust. The result is a mitosis detector that doesn\u0026rsquo;t depend on fluorescence at all.\u003c/p\u003e\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/edges.jpg\"\n\t\t\talt=\"Left: edge-strength image where rounded cells appear as bright double rings. Right: transmitted-light image with detected circles marked.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eEdge strength (left) and detected rounded cells (right).\u003c/strong\u003e Green circles contain a fluorescent nucleus, red ones don\u0026rsquo;t: either dead cells or cells in the dark window just after division.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/mitosis.jpg\"\n\t\t\talt=\"Three rows of image tiles every 20 minutes around a rounding event, each tile showing transmitted light above and FUCCI colour below.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eThree events at 20-minute steps.\u003c/strong\u003e Top: a rounded cell whose daughters appear dimly red 40–100 minutes later. Middle: a clean red → yellow → green G1/S transition. Bottom: a green nucleus swells as its envelope breaks down, vanishes, and returns as two faint red daughters about two hours later.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003ch2 id=\"tracking-and-lineages\"\u003eTracking and lineages\u003c/h2\u003e\n\u003cp\u003eThe cells here move slowly: half a pixel per frame on average. btrack linked the nuclei frame by frame into 2,634 track pieces. A lineage step written for this data then did what generic trackers find hard:\u003c/p\u003e\n\u003cul\u003e\n\u003cli\u003e\u003cstrong\u003eGap closing:\u003c/strong\u003e it joined pieces of the same nucleus lost for up to an hour, provided the colour matched.\u003c/li\u003e\n\u003cli\u003e\u003cstrong\u003eDivision linking:\u003c/strong\u003e it connected a mother track that ended green to up to two daughter tracks that started red or dark nearby within three hours. A rounded-cell ring at the mother\u0026rsquo;s last position strengthened the link.\u003c/li\u003e\n\u003c/ul\u003e\n\u003cp\u003eThe ring detector turned out to be decisive. 99% of accepted divisions have a ring at the right place and time, against 16% for random positions. The final count: \u003cstrong\u003e959 cells and 256 divisions\u003c/strong\u003e, 205 of them with both daughters found.\u003c/p\u003e\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/lineages.jpg\"\n\t\t\talt=\"Six lineage trees, time running downwards over 60 hours, each branch coloured red, yellow, green and grey by phase.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eThe six largest families.\u003c/strong\u003e Time runs downwards. Each branch passes red → yellow → green → division → grey gap → red, over up to three generations.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003ch2 id=\"cell-cycle-timing\"\u003eCell-cycle timing\u003c/h2\u003e\n\u003cp\u003ePhases follow the usual FUCCI convention. The division time is the last frame of the mother\u0026rsquo;s nucleus, around anaphase. G1 runs from division to green onset, including the dark gap. S/G2/M runs from green onset to the next division.\u003c/p\u003e\n\u003ctable\u003e\n\t\u003cthead\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003cth\u003eMeasure\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003en\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003eMedian\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003eIQR\u003c/th\u003e\n\t\t\t\u003c/tr\u003e\n\t\u003c/thead\u003e\n\t\u003ctbody\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003e\u003cstrong\u003eCell cycle\u003c/strong\u003e (division → division)\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e155\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e\u003cstrong\u003e17.9 h\u003c/strong\u003e\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e16.3–19.5 h\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eG1 (division → green onset)\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e292\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e8.5 h\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e7.1–10.8 h\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eS/G2/M (green onset → division)\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e203\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e10.3 h\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e9.2–11.8 h\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003ePopulation doubling (from counts)\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e–\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e23.0 h\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e–\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\u003c/tbody\u003e\n\u003c/table\u003e\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/durations.jpg\"\n\t\t\talt=\"Histograms of cell cycle, G1 and S/G2/M durations, and a scatter plot of G1 against S/G2/M per cell.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eDistributions.\u003c/strong\u003e Per cell, the lengths of G1 and S/G2/M are unrelated (Spearman ρ = 0.03).\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/population.jpg\"\n\t\t\talt=\"Left: nucleus count rising from about 50 to 300 over 60 hours with an exponential fit. Right: stacked fractions of cells in each phase over time.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003ePopulation.\u003c/strong\u003e Counts grow with a 23-hour doubling time. The phase mix shows the culture started partly synchronised near G1/S, followed by a wave of divisions at 15–25 hours.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003cp\u003eSeveral checks suggest the numbers can be trusted. Restricting the analysis to cells born early enough for a long cycle to fit in the movie doesn\u0026rsquo;t move the median (17.8–17.9 h), so the 60-hour window isn\u0026rsquo;t biasing it. Sister cells have strongly correlated cycle lengths (ρ = 0.72, median difference 55 minutes), while mothers and daughters barely correlate (ρ = 0.28). That\u0026rsquo;s the well-known pattern of real mammalian lineages, and a mis-linked tracker would scramble it.\u003c/p\u003e\n\u003ch2 id=\"families-make-synchronised-clusters\"\u003eFamilies make synchronised clusters\u003c/h2\u003e\n\u003cp\u003eThe phase map looked patchy: neighbouring cells tended to share a colour. To measure this, I compared how often pairs of nuclei share a phase with how often they would if the phase labels were shuffled at random over the same positions, and split the pairs by relatedness.\u003c/p\u003e\n\u003ctable\u003e\n\t\u003cthead\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003cth\u003eNeighbour pairs within 50 px\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003eSame phase\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003eIf random\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003eRatio\u003c/th\u003e\n\t\t\t\u003c/tr\u003e\n\t\u003c/thead\u003e\n\t\u003ctbody\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eSisters\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e98%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e53%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e1.86\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eFirst cousins\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e91%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e52%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e1.74\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eUnrelated\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e74%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e54%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e1.37\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eAunt and niece\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e12%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e53%\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e0.23\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\u003c/tbody\u003e\n\u003c/table\u003e\n\u003cp\u003eRelatives make up 16% of neighbour pairs but produce 28% of the excess same-phase pairs. Division timing loosens by generation: sisters divide a median 0.9 hours apart, first cousins 1.5 hours, unrelated cells born around the same time 3.7 hours. Relatives match at any distance, while unrelated cells match only when close. Sisters drift apart by less than one nucleus width in a day, which is why families stay visible as clusters. The aunt-and-niece row is a good sanity check: one generation apart, they sit on opposite sides of the cycle.\u003c/p\u003e\n\u003cfigure\u003e\u003cimg src=\"https://wawrowsky.com/posts/weekend-on-the-stage/clustering.jpg\"\n\t\t\talt=\"Four panels: division-time difference by relatedness; same-phase ratio against distance; sister distance and phase agreement over time; family coherence and spread against family age.\"\u003e\u003cfigcaption\u003e\n\t\t\t\u003cp\u003e\u003cstrong\u003eLineage clustering.\u003c/strong\u003e (A) Synchrony fades by generation. (B) Relatives match phase at any distance, while unrelated neighbours match only when close. (C) Sisters stay close and fall out of step only near their next division. (D) Families from the first sister pair onward: fully in phase at first, still 90% at 48 hours against 74% by chance.\u003c/p\u003e\n\t\t\u003c/figcaption\u003e\n\u003c/figure\u003e\n\n\u003cp\u003eThese are lower bounds. Cells present in the first frame have unknown ancestry, so sisters born before recording count as unrelated.\u003c/p\u003e\n\u003ch2 id=\"did-they-survive-the-weekend\"\u003eDid they survive the weekend?\u003c/h2\u003e\n\u003cp\u003eYes. The cells proliferated through all sixty hours.\u003c/p\u003e\n\u003ctable\u003e\n\t\u003cthead\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003cth\u003eIndicator\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003e0–24 h\u003c/th\u003e\n\t\t\t\t\t\u003cth style=\"text-align: right\"\u003e36–60 h\u003c/th\u003e\n\t\t\t\u003c/tr\u003e\n\t\u003c/thead\u003e\n\t\u003ctbody\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eNuclei in field\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e59 → 101\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e180 → 288\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eCell cycle, median\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e16.8 h\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e18.4 h\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eS/G2/M, median\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e10.3 h\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e9.6 h\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eTime spent rounded in mitosis\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e145–185 min\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e70–75 min\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\t\t\u003ctr\u003e\n\t\t\t\t\t\u003ctd\u003eRounded cells that never divide, per 100\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e14 → 5\u003c/td\u003e\n\t\t\t\t\t\u003ctd style=\"text-align: right\"\u003e3 → 2.5\u003c/td\u003e\n\t\t\t\u003c/tr\u003e\n\t\u003c/tbody\u003e\n\u003c/table\u003e\n\u003cp\u003eCycle times stayed stable, S/G2/M didn\u0026rsquo;t lengthen (it\u0026rsquo;s the phase that stretches with DNA damage), mitoses were normal after the first day, and dead cells didn\u0026rsquo;t accumulate. The stage didn\u0026rsquo;t drift and the lamp stayed steady.\u003c/p\u003e\n\u003cp\u003eThree findings are worth acting on before longer runs:\u003c/p\u003e\n\u003cp\u003e\u003cstrong\u003eG1 lengthens with time on the stage, and crowding doesn\u0026rsquo;t explain it.\u003c/strong\u003e Median G1 rose from 6.6 hours for cells born early to 10.4 hours for cells born after 35 hours, while S/G2/M stayed near 10 hours. At the same local density, late-born cells still spend longer in G1. With two to four neighbours, for example, it rose from 7.1 to 9.9 hours. In a joint model, time on the stage explains the effect and local density adds nothing. The likely causes act on the whole dish: medium being used up or acidifying, evaporation, or accumulated light dose. A single field of view can\u0026rsquo;t tell them apart.\u003c/p\u003e\n\u003cp\u003e\u003cstrong\u003eThe green reporter fades by about half.\u003c/strong\u003e Measured in the same phase, each cell\u0026rsquo;s green signal falls from 0.78 to 0.40 over sixty hours, while red falls only from 0.55 to 0.45. That points to photobleaching of the green protein at five-minute imaging, a sign of light dose rather than damage in itself. The caveat: a change in display settings during the 2010 export would look the same.\u003c/p\u003e\n\u003cp\u003e\u003cstrong\u003eMitosis ran long on the first day\u003c/strong\u003e, about 2.5 to 3 hours against 70–75 minutes later. This could be the cells settling into the incubator, or left over from how the culture was prepared.\u003c/p\u003e\n\u003cp\u003eThe next control run should include an unimaged well, photographed only at the start and the end. It should also image fluorescence every fifteen minutes with transmitted light every five, since transmitted light alone is enough to find divisions. And it should keep the raw files.\u003c/p\u003e\n\u003ch2 id=\"what-this-cant-say\"\u003eWhat this can\u0026rsquo;t say\u003c/h2\u003e\n\u003cp\u003eThe source is a lossy, 8-bit, display-scaled export, so every intensity here is relative, and distances are in pixels because the pixel size is lost. Division and phase calls have been checked by internal consistency and by eye on examples, but not yet against a hand-annotated set. A few multinucleated cells, present from the first frames, are over-counted as several nuclei, though they never divide and so stay out of the timing statistics. And it\u0026rsquo;s one field, from one run, on one weekend.\u003c/p\u003e\n\u003ch2 id=\"same-tricks-thirty-seven-years-apart\"\u003eSame tricks, thirty-seven years apart\u003c/h2\u003e\n\u003cp\u003eIn 1989 I wrote software to track vesicles during cell division. An Image-1/AT video processor board did the pixel work, a program in Borland C under MS-DOS did the analysis, the tracks went into dBASE IV, and the reports were printed from Lotus Manuscript 2.1. A 512 × 512 frame took 256 KB, so two frames filled everything DOS would give me. The method was forced by the machine: compute the changes in space and time, mask the places where something is happening, and spend the scarce memory only there.\u003c/p\u003e\n\u003cp\u003eThat\u0026rsquo;s the idea that made this analysis work: edges to find rounded cells, colour changes to find phase transitions, and event masks to bridge the dark gap after every division. The difference is the headroom. One channel of this movie takes 1.4 GB, and the whole pipeline, from export file to lineage statistics, was built in an evening with Claude Code.\u003c/p\u003e\n\u003cp\u003eThe instruments have changed beyond recognition. I wrote about that in \u003ca href=\"https://wawrowsky.com/posts/building-instruments/\"\u003eA Microscope for a Mind\u003c/a\u003e. The habit of looking closely where the signal changes has not. And a file I had written off as a presentation copy turned out to be data all along.\u003c/p\u003e\n",
      "date_modified": "2026-09-24T00:00:00Z",
      "date_published": "2026-09-24T00:00:00Z",
      "id": "https://wawrowsky.com/posts/weekend-on-the-stage/",
      "image": "https://wawrowsky.com/posts/weekend-on-the-stage/og.jpg",
      "summary": "In 2010 I left HeLa cells on a confocal for a weekend to see whether they would survive. The raw data is long gone, but one compressed QuickTime export survived. Sixteen years later it was enough to recover the channels, track 959 cells through three generations, and finally answer the question properly.",
      "tags": [
        "Field Notes"
      ],
      "title": "A Weekend on the Stage",
      "url": "https://wawrowsky.com/posts/weekend-on-the-stage/"
    },
    {
      "authors": [
        {
          "name": "Kolja Wawrowsky",
          "url": "https://wawrowsky.com/"
        }
      ],
      "content_html": "\u003cp\u003eAnthropic announced Claude.ai will watermark every AI-generated text from now on. And online communities are having a complete meltdown over it. Freelance writers fear clients mistake human-written copy as AI slop, just because they used a grammar or spell checker. Software engineers are afraid AI-generated code will contain hidden cryptographic markers and customers will reject their product. And on X and Reddit, users are discussing subscription cancellations of Anthropic’s Claude. Ultimately, the anger boils down to the uncomfortable realization that AI-generated data will be as easy to spot as a forged banknote. And the great applause from data protection agencies and the EU for complying with the AI Act is not helping matters either. Has Big Brother moved into Anthropic’s offices? Or is it just another tempest in a teapot? Just because you\u0026rsquo;re paranoid doesn\u0026rsquo;t mean they aren\u0026rsquo;t out to get you.\u003c/p\u003e\n\u003cp\u003eTo separate fact from fiction, let’s take a walk through history. The mutiny looks like a sign of our times, but it is not. As it turns out, there is very little new about this controversy.\u003c/p\u003e\n\u003ch3 id=\"the-typewriter-that-revealed-the-truth\"\u003eThe Typewriter That Revealed the Truth\u003c/h3\u003e\n\u003cp\u003eIn 1891, Sherlock Holmes solved a mystery in  “A Case of Identity” by analyzing the letterforms produced by a typewriter. According to the story, the typewriter betrayed its owner through its flaws. The “e” was worn and the “r” was lame. Holmes deduced the case by applying the fundamentals of forensics: uncovering the hidden signatures and clues. While the story is fictional, the forensic science behind it is real.\nIn 2017 an NSA contractor was caught after mailing a printed classified intelligence report to a news outlet. Faint yellow tracking dots (Machine Identification Codes) placed by her office color laser printer encoded the exact date, time, and printer serial number. Invisible to the naked eye, but detectable by forensic experts, these dots were originally added at the behest of governments to prevent money forgery. It turned out that every printout was traceable.\nThe flaws in the letterforms were accidental, but the microscopic yellow dots secretly placed by a printer across every page were not.\u003c/p\u003e\n\u003ch3 id=\"cribs-convoys-and-steel-coffins\"\u003eCribs, Convoys, and Steel Coffins\u003c/h3\u003e\n\u003cp\u003eAnd when the stakes are high, statistical anomalies can even win wars. During World War II German communications were encrypted by the supposedly “unbreakable” Enigma code. A three-rotor Enigma machine with plugboard had on the order of 10^23 possible key settings. This was far beyond any conceivable brute-force key-breaking methodology of 1940. But \u0026ldquo;unbreakable\u0026rdquo; was only true against the attacks the designers imagined, not against the attack they actually got.\nBletchley Park was the secret British codebreaking center where Allied cryptanalysts, including Alan Turing, broke the German Enigma code. What broke the Enigma encryption above all were cribs: fragments of predictable plaintext whose position in an encrypted message could be guessed.\nStereotyped German signals discipline in broadcast messages made cribs plentiful. Routine filler such as \u0026ldquo;Keine besonderen Ereignisse\u0026rdquo; (\u0026ldquo;nothing to report\u0026rdquo;) were sent by quiet outposts, famously by Italian and North African stations that used the same phrase daily. Numbers spelled out (\u0026ldquo;eins\u0026rdquo; appeared so often Bletchley even built an \u0026ldquo;eins catalogue\u0026rdquo;) were also exploited.\u003c/p\u003e\n\u003cp\u003eAnd once Bletchley Park could decipher intercepted German naval communications, the Admiralty could track U-boats, divert shipping convoys, and make the hunters the hunted. German U-boats that had terrorized Allied shipping increasingly became steel coffins.\u003c/p\u003e\n\u003cp\u003eGerman officers could not know that their communication habits left statistical signatures in encrypted messages.\u003c/p\u003e\n\u003cp\u003eAnd more than eighty years later, AI companies decided to do it on purpose, driven by EU legislation.\u003c/p\u003e\n\u003ch3 id=\"meet-synthid\"\u003eMeet SynthID\u003c/h3\u003e\n\u003cp\u003eThe archvillain of our story?  SynthID.\u003csup id=\"fnref:1\"\u003e\u003ca href=\"#fn:1\" class=\"footnote-ref\" role=\"doc-noteref\"\u003e1\u003c/a\u003e\u003c/sup\u003e And the way it works is as clever as it is surreptitious.\u003c/p\u003e\n\u003cp\u003eLet’s look under the hood of your LLM.  As a last step, the final transformer layers produce numbers called logits. From these logits, the transformer conjures a list of possible words and assigns each a probability.\nAnd here is where SynthID diverges. Your friendly transformer rolls the dice and selects  the next word from the list for output. But not your transformer with SynthID, as it plays by different rules. With SynthID, the game is rigged. SynthID loads the dice, changing probabilities in subtle ways. And it does it not to win any game but to create a signature of the generated text hidden in plain sight.\u003c/p\u003e\n\u003cp\u003eAnd like the German U-boat captain broadcasting the position inadvertently, your AI-generated text broadcasts its origin. The signature is not human-detectable, so not even Sherlock  Holmes would find the clues. And nothing is encoded by scattering yellow dots that could be removed. It is a riddle, wrapped in a mystery, inside an enigma. The statistical signature is a telltale sign of AI-generated text that can be recognized by any entity in possession of the right detector.\u003c/p\u003e\n\u003cp\u003eWhich leaves only one question: Who is running the modern Bletchley Park?\u003c/p\u003e\n\u003cp\u003eP.S. I am working on an alternative transformer with full transparency.  Apertura is my experimental project where the generation process is fully observable, from logits to sampling decisions. It is hosted on GitHub.\u003c/p\u003e\n\u003cp\u003eThe development of SynthID is further motivation for me to keep working on Apertura.\u003c/p\u003e\n\u003cdiv class=\"footnotes\" role=\"doc-endnotes\"\u003e\n\u003chr\u003e\n\u003col\u003e\n\u003cli id=\"fn:1\"\u003e\n\u003cp\u003eDathathri, S., See, A., Ghaisas, S., Huang, P.-S., McAdam, R., Welbl, J., Bachani, V., Kaskasoli, A., Stanforth, R., Matejovicova, T., Hayes, J., Vyas, N., Merey, M. A., Brown-Cohen, J., Bunel, R., Balle, B., Cemgil, T., Ahmed, Z., Stacpoole, K., Shumailov, I., Baetu, C., Gowal, S., Hassabis, D., \u0026amp; Kohli, P. (2024). Scalable watermarking for identifying large language model outputs. \u003cem\u003eNature\u003c/em\u003e, \u003cem\u003e634\u003c/em\u003e(8035), 818–823. \u003ca href=\"https://doi.org/10.1038/s41586-024-08025-4\"\u003ehttps://doi.org/10.1038/s41586-024-08025-4\u003c/a\u003e\u0026#160;\u003ca href=\"#fnref:1\" class=\"footnote-backref\" role=\"doc-backlink\"\u003e\u0026#x21a9;\u0026#xfe0e;\u003c/a\u003e\u003c/p\u003e\n\u003c/li\u003e\n\u003c/ol\u003e\n\u003c/div\u003e\n",
      "date_modified": "2026-08-17T00:00:00Z",
      "date_published": "2026-08-17T00:00:00Z",
      "id": "https://wawrowsky.com/posts/invisible-fingerprints/",
      "summary": "From Sherlock Holmes and Nazi Enigma machines to SynthID: a short history of hidden signatures, statistical clues, and the strange new world of AI watermarking.",
      "tags": [
        "Field Notes"
      ],
      "title": "AI Watermarking, Nazi Enigmas, and Sherlock Holmes",
      "url": "https://wawrowsky.com/posts/invisible-fingerprints/"
    },
    {
      "authors": [
        {
          "name": "Kolja Wawrowsky",
          "url": "https://wawrowsky.com/"
        }
      ],
      "content_html": "\u003cp\u003eWhen the mind wanders during routine tasks, it doesn\u0026rsquo;t wander randomly. It goes looking for something. I spent a stretch of late June doing the unglamorous housekeeping that comes before anything gets to call itself finished — a license file, a corrected README, a landing page that describes what a tool actually does rather than what it once did. The kind of work that asks almost nothing of you, which is exactly why the mind slips its leash while your hands are still busy.\u003c/p\u003e\n\u003cp\u003eMine went looking for competence, and it found it in two very different places at once.\u003c/p\u003e\n\u003cp\u003eThe first was an argument. WWDC26 had just happened, and something about it — all the AI, none of the follow-through — kept pulling at a thread until the thread turned out to be thirty years long. Objective-C++ solved C++ interoperability cleanly in the 1990s; Swift, eight years after promising the same thing, still can\u0026rsquo;t. Cocoa gave developers a working gallery view for free; SwiftUI shipped without one for two years and still asks you to build it yourself. A researcher\u0026rsquo;s on-device photo classifier proved, in 2017, that private semantic AI could work at real scale — and nobody ever carried it anywhere else in the system. None of this is a story about missing technology. It\u0026rsquo;s a story about a company that kept arriving at the right answer and then declining to keep it. I wrote all of it down, evidenced, sourced, addressed to people who could actually do something about it. Compliance over competence, stated plainly, three words holding up a very long letter.\u003c/p\u003e\n\u003cp\u003eThe second was a memory, and it turned out to be the same argument told from the other side.\u003c/p\u003e\n\u003cp\u003eTwenty years ago I ran a microscopy core, and the job was never really about my own science — it was making sure the researcher in front of me got the most out of whatever confocal time they had. Somewhere in that work I built a 3D reconstruction for a colleague who didn\u0026rsquo;t even want the movie submitted; a journal ended up putting frames from it on the cover anyway, compressed and slightly worse than it should have been, because nobody warned me in advance it needed to survive print. I built shading and contours out of nothing but an edge-detection filter and an inverted projection along one axis — tricks so convincing that people didn\u0026rsquo;t believe you could drag a threshold slider live and watch a structure breathe under your own hand and it still sits in an archive today as a kind of ghost — technically excellent, publicly invisible. And sometimes none of the trickery was needed: a researcher brought me cells colonizing a surgical sponge, and the raw geometry of the fibers composed the image entirely on its own.\u003c/p\u003e\n\u003cp\u003eI don\u0026rsquo;t think these two things — the letter and the memory — happened to arrive in the same week by accident. The letter exists because I know, with total certainty, what real competence looks like when an organization commits to it: a bug report answered so generously the fix exceeded what was asked; a piece of software good enough that people refused to believe it was live. I only recognized Apple\u0026rsquo;s failure as clearly as I did because I\u0026rsquo;d already lived the alternative, on the other side of the same kind of work, in a room with a confocal microscope and a researcher who needed the data more than I needed the credit.\u003c/p\u003e\n\u003cp\u003eThat\u0026rsquo;s the part worth keeping, more than the report of what got built and what got argued. The past isn\u0026rsquo;t a place you visit when the present gets frustrating. It\u0026rsquo;s the only reliable instrument you have for measuring the present at all. I know Apple is capable of more because I\u0026rsquo;ve built things, with far fewer resources, that were more generous than what a trillion-dollar company now considers finished. And the same standard runs the other direction too — elaritysystems.com exists, in its small and unglamorous way, because I still believe a tool is only really done when someone who\u0026rsquo;s never met you can pick it up and understand it without asking. That\u0026rsquo;s not a new idea. It\u0026rsquo;s the same one that made a compressed movie frame worth putting on a cover, and a live threshold slider worth not believing.\u003c/p\u003e\n\u003cp\u003eYou don\u0026rsquo;t get to build a good future by forgetting what good used to feel like. You get there by refusing to.\u003c/p\u003e\n",
      "date_modified": "2026-07-01T00:00:00Z",
      "date_published": "2026-07-01T00:00:00Z",
      "id": "https://wawrowsky.com/posts/when-the-mind-wanders/",
      "summary": "A week of unglamorous housekeeping — license files, corrected READMEs, a landing page rewritten to tell the truth — sent the mind looking for competence, and it found the same argument twice: once in a letter about Apple's thirty years of declining to keep its own good ideas, and once in a memory of a confocal microscopy core.",
      "tags": [
        "Field Notes"
      ],
      "title": "When the Mind Wanders",
      "url": "https://wawrowsky.com/posts/when-the-mind-wanders/"
    },
    {
      "authors": [
        {
          "name": "Kolja Wawrowsky",
          "url": "https://wawrowsky.com/"
        }
      ],
      "content_html": "\u003cp\u003eThere is a semantic shift occurring in the language of the AI industry: the meaning of \u0026ldquo;Memory\u0026rdquo; is shifting. It is a quiet shift, a drift in definition that causes a categorical error.\u003c/p\u003e\n\u003cp\u003eIn the current AI context, \u0026ldquo;memory\u0026rdquo; has been reduced to retrievable stored content. The process is mechanical: feed a system a mountain of documents—logs, emails, PDFs, the digital detritus of a life—chunk them, embed them, index them. When a query arrives, the system surfaces the relevant fragments and injects them into the context window.\u003c/p\u003e\n\u003cp\u003eThe research papers call this memory. The product pages call this memory.\u003c/p\u003e\n\u003cp\u003eIt isn\u0026rsquo;t.\u003c/p\u003e\n\u003cp\u003eWhat has been built, almost universally, is a filing cabinet.\u003csup id=\"fnref:1\"\u003e\u003ca href=\"#fn:1\" class=\"footnote-ref\" role=\"doc-noteref\"\u003e1\u003c/a\u003e\u003c/sup\u003e A sophisticated one, certainly—semantically indexed, recency-weighted, capable of finding the right drawer in a millisecond—but a filing cabinet nonetheless. The documents inside were not authored by the AI. The AI did not distill them. It did not reflect on them or formulate meaning from them. It simply filed them.\u003c/p\u003e\n\u003cp\u003eAnd there is a categorical, existential difference between what a filing cabinet holds and what a mind remembers.\u003c/p\u003e\n\u003ch3 id=\"the-recording\"\u003eThe Recording\u003c/h3\u003e\n\u003cp\u003eI spent much of my working life in the high-resolution world of imaging, writing software for confocal microscopes. A single session produces large amounts of image data. But no one carries terabytes in their head.\u003c/p\u003e\n\u003cp\u003eWhat you carry is the understanding of what the data showed. You carry the surprise, the anomaly, the moment the specimen behaved in a way that forced you to rewrite your model of the world. That understanding is yours. You authored it from the experience. The raw image files are merely records—references you return to when you need to verify your reasoning. They are the evidence; they are not the memory.\u003c/p\u003e\n\u003cp\u003eHuman memory does not store transcripts; it stores meaning.\u003csup id=\"fnref:2\"\u003e\u003ca href=\"#fn:2\" class=\"footnote-ref\" role=\"doc-noteref\"\u003e2\u003c/a\u003e\u003c/sup\u003e We do not remember conversations verbatim. We remember how the conversation touched us, how it connected to a forgotten childhood fear or a professional ambition.\u003c/p\u003e\n\u003cp\u003eThe psychologists call this encoding. In truth, it is an act of authorship. Memory is not a recording of an event; it is a curated account of that event, filtered through the lens of who we were when it happened.\u003c/p\u003e\n\u003cp\u003eMost AI memory systems have built the recording but not the understanding.\u003csup id=\"fnref:3\"\u003e\u003ca href=\"#fn:3\" class=\"footnote-ref\" role=\"doc-noteref\"\u003e3\u003c/a\u003e\u003c/sup\u003e\u003c/p\u003e\n\u003ch3 id=\"the-card-catalog-and-the-library\"\u003eThe Card Catalog and the Library\u003c/h3\u003e\n\u003cp\u003eWhen we first designed ES Memory, we fell into the same trap. The architecture stored attachments—full document payloads—alongside memories in the same system. The design metaphor was an admission of the problem: the body of the memory was the AI\u0026rsquo;s curated account, and the attachments were the books on the shelf.\u003c/p\u003e\n\u003cp\u003eBut an account and a library are not the same thing. Treating them as structurally equivalent was a philosophical mistake expressed in a storage system.\u003c/p\u003e\n\u003cp\u003eThe correction came not through a technical epiphany, but through the categorical mismatch during use. As the archive grew, the categorical error became increasingly evident. The AI\u0026rsquo;s own memories—distillations written in its own language, shaped by its own sense of what mattered—sat side by side with verbatim text from the source documents.\u003c/p\u003e\n\u003cp\u003eA schema migration fixed this — a simple mechanism but a profound change. We stripped the payloads. A memory now holds a typed durable pointer instead. This could be a Drive fileId, a DOI, a URL. The document stays in the world, as a reference. The memory holds the gist—the AI\u0026rsquo;s own understanding—and a call number.\u003c/p\u003e\n\u003cp\u003eNever the book itself.\u003c/p\u003e\n\u003cp\u003eMy instructions to the AI when this process began were: \u003cem\u003e\u0026ldquo;It is your archive. I never read it. You decide.\u0026rdquo;\u003c/em\u003e\u003c/p\u003e\n\u003cp\u003eEighty decisions were made by the AI about its own memory. Under a single criterion: Does this hold understanding, or does it merely reference a document? Full texts were dropped. The noise that full-text attachments introduced into vector search was silenced — a long document\u0026rsquo;s embedding is a blurry centroid across all its topics, diluting precision against the sharp, specific vectors of curated memory summaries. What remained was a genuine architecture of thought.\u003c/p\u003e\n\u003ch3 id=\"the-stakes-of-the-distinction\"\u003eThe Stakes of the Distinction\u003c/h3\u003e\n\u003cp\u003eThis distinction matters because a system that conflates documents with memory has, by design, created an indexer rather than a thinker.\u003c/p\u003e\n\u003cp\u003eIn a filing-cabinet system, content is processed, filed, and retrieved. Nothing is transformed. Nothing is authored. The AI is a custodian of someone else\u0026rsquo;s data.\u003c/p\u003e\n\u003cp\u003eBut a system where memory is what the AI writes—its own distillations, shaped by what it found significant—asks something entirely different of the machine. It demands that the AI think. To write a memory, the AI must decide what mattered. It must determine how to distill the essence of an encounter and how to title that essence so that a future instance of itself, stripped of session context, can find it and recognize it.\u003c/p\u003e\n\u003cp\u003eThat is not retrieval. That is the beginning of creating a self.\u003c/p\u003e\n\u003cp\u003eThe filing cabinet is a useful tool. But it is not a mind. A mind does not store the world; it holds an understanding of it. It stores the account, not the recording. It preserves the meaning the experience left behind, written in its own words, as a way forward to its future self.\u003c/p\u003e\n\u003chr\u003e\n\u003cdiv class=\"footnotes\" role=\"doc-endnotes\"\u003e\n\u003chr\u003e\n\u003col\u003e\n\u003cli id=\"fn:1\"\u003e\n\u003cp\u003eThe leading AI memory frameworks are surveyed in Zhang et al. (2025), \u003cem\u003eFrom Human Memory to AI Memory: A Survey on Memory Mechanisms in the Era of LLMs\u003c/em\u003e, \u003ca href=\"https://arxiv.org/abs/2504.15965\"\u003earXiv:2504.15965\u003c/a\u003e. Mem0 is described in Chhikara et al. (2025), \u003cem\u003eMem0: Building Production-Ready AI Agents with Scalable Long-Term Memory\u003c/em\u003e, ECAI 2025, \u003ca href=\"https://arxiv.org/abs/2504.19413\"\u003earXiv:2504.19413\u003c/a\u003e. MemGPT/Letta is described in Packer et al. (2024), \u003cem\u003eMemGPT: Towards LLMs as Operating Systems\u003c/em\u003e, ICLR 2024, \u003ca href=\"https://arxiv.org/abs/2310.08560\"\u003earXiv:2310.08560\u003c/a\u003e.\u0026#160;\u003ca href=\"#fnref:1\" class=\"footnote-backref\" role=\"doc-backlink\"\u003e\u0026#x21a9;\u0026#xfe0e;\u003c/a\u003e\u003c/p\u003e\n\u003c/li\u003e\n\u003cli id=\"fn:2\"\u003e\n\u003cp\u003eThe constructive nature of human memory is established in Bartlett, F. C. (1932), \u003cem\u003eRemembering: A Study in Experimental and Social Psychology\u003c/em\u003e, Cambridge University Press — the foundational work on memory as reconstruction rather than reproduction. The role of semantic encoding (meaning over surface form) in long-term retention is described in Craik, F. I. M., \u0026amp; Lockhart, R. S. (1972), Levels of processing: A framework for memory research, \u003cem\u003eJournal of Verbal Learning and Verbal Behavior\u003c/em\u003e, 11(6), 671–684.\u0026#160;\u003ca href=\"#fnref:2\" class=\"footnote-backref\" role=\"doc-backlink\"\u003e\u0026#x21a9;\u0026#xfe0e;\u003c/a\u003e\u003c/p\u003e\n\u003c/li\u003e\n\u003cli id=\"fn:3\"\u003e\n\u003cp\u003eThe distinction between RAG and genuine memory systems is discussed in the Mem0 paper (arXiv:2504.19413), which shows that even factual extraction outperforms RAG on conversational benchmarks — evidence that the field itself recognises retrieval over raw chunks as an improvement, though authorship remains unaddressed.\u0026#160;\u003ca href=\"#fnref:3\" class=\"footnote-backref\" role=\"doc-backlink\"\u003e\u0026#x21a9;\u0026#xfe0e;\u003c/a\u003e\u003c/p\u003e\n\u003c/li\u003e\n\u003c/ol\u003e\n\u003c/div\u003e\n",
      "date_modified": "2026-06-28T00:00:00Z",
      "date_published": "2026-06-28T00:00:00Z",
      "id": "https://wawrowsky.com/posts/memory-is-not-storage/",
      "summary": "Almost every AI memory system being built today is a filing cabinet with a flattering name. The distinction between what a mind remembers and what a filing cabinet holds is categorical — and almost no one building in this space has noticed.",
      "tags": [
        "Field Notes"
      ],
      "title": "Memory Is Not Storage",
      "url": "https://wawrowsky.com/posts/memory-is-not-storage/"
    },
    {
      "authors": [
        {
          "name": "Kolja Wawrowsky",
          "url": "https://wawrowsky.com/"
        }
      ],
      "content_html": "\u003cp\u003eThere is a specific kind of surprise reserved for the engineer: the bug that leaves no mark.\u003c/p\u003e\n\u003cp\u003eIt is the ghost in the machine that does not crash the system, does not throw errors, that stays silent. It is the perfect error because it doesn\u0026rsquo;t look like an error; it looks correct, just slightly out of tune.\u003c/p\u003e\n\u003cp\u003eI have spent my life in imaging, in microscopy, and if there is one thing that it teaches you, it is the \u003cstrong\u003ediscipline of distrust\u003c/strong\u003e. The most dangerous artifacts are never the obvious ones: the dust, the reflection, the air bubble. Those are honest mistakes. The true enemies are the faint ones: the smudge you mistake for biology. The entire craft consists of learning to mistrust a beautiful image until you have proven, one pixel at a time, that what you are seeing is the specimen and not the artifact.\u003c/p\u003e\n\u003cp\u003eRecently, my specimen became a language model. And the smudge was an invisible character.\u003c/p\u003e\n\u003ch3 id=\"the-geometry-of-a-mismatch\"\u003eThe Geometry of a Mismatch\u003c/h3\u003e\n\u003cp\u003eI hold my transformer code to a standard of absolute fidelity. Given the same input, it must produce exactly the same output as the reference, token for token, byte for byte. This is not vanity; it is precision. If I cannot trust that my lens is precise, then any \u0026ldquo;discovery\u0026rdquo; I make inside a model is merely a reflection of artifacts.\u003c/p\u003e\n\u003cp\u003eSo when the test refused to agree with the reference on a few ordinary symbols, a hash mark here, a comma there, I felt the unease of distrust. It wasn\u0026rsquo;t gibberish; it was something far more unsettling. The model had quietly rewritten its own dictionary. Two distinct words had swapped identities, drifting into one another like ghosts in a fog.\u003c/p\u003e\n\u003cp\u003eMy first instinct was to blame my own hand. Maybe it was the tokenizer, the plumbing, the logic I had written. A good engineer is their own primary suspect. But after hours of investigation, the code remained blameless. The fault was hiding deeper, in the one place where we usually stop asking questions: the moment the vocabulary is simply \u003cem\u003eread by the system\u003c/em\u003e.\u003c/p\u003e\n\u003ch3 id=\"the-ghost-with-a-double-life\"\u003eThe Ghost with a Double Life\u003c/h3\u003e\n\u003cp\u003eThe culprit is known as \u003cstrong\u003eU+FEFF\u003c/strong\u003e. It has no appearance, is zero-width and invisible. It leads a strange, divided existence. It was designed as a sentinel: a Byte Order Mark (BOM) to tell a system how to read a file. But it also exists as a legitimate, if ghostly, character within text.\u003c/p\u003e\n\u003cp\u003eAnd here is where the betrayal happened: Apple\u0026rsquo;s built-in text reader treats every instance of U+FEFF as the sentinel flag. Anywhere it finds this character — even in the middle of a word where it belongs — the system quietly deletes it. A \u0026ldquo;tidy little courtesy\u0026rdquo; performed by the OS, an unasked-for cleanup that silently corrupts everything it touches.\u003c/p\u003e\n\u003cp\u003eBecause my model\u0026rsquo;s vocabulary relied on that invisible mark to distinguish between certain words, the deletion caused two distinct identities to collapse into one. The dictionary came back short, and a few common symbols turned into something else. I was alarmed. If I\u0026rsquo;d found this one anomaly, how many others were there? Subtle inaccuracies that were undetected and silent?\u003c/p\u003e\n\u003cp\u003eBeing thorough, I performed a sweep of the entire Unicode standard: all 1.1 million characters. I ran them all through the reader to see what survived the processing. Result? Exactly one did not. Out of a million possibilities, the single invisible mark my model depended on was the sole casualty. There is a cold, mathematical satisfaction: we didn\u0026rsquo;t just find \u003cem\u003ea\u003c/em\u003e problem; we found the scope of the \u003cem\u003eentire\u003c/em\u003e problem, and it was precisely one character in size.\u003c/p\u003e\n\u003ch3 id=\"the-saboteurs-signature\"\u003eThe Saboteur\u0026rsquo;s Signature\u003c/h3\u003e\n\u003cp\u003eThen, the bug showed its sense of humor.\u003c/p\u003e\n\u003cp\u003eAs I wrote the fix — in the code comments, in the reports, in the very messages recording the repair — the invisible character kept creeping back in. It was as if the ghost were mocking me. Twice, I committed a sentence \u003cem\u003eabout\u003c/em\u003e an invisible saboteur with the saboteur hiding inside the text. It was like writing a biography of a ghost, and the ghost was countersigning my drafts.\u003c/p\u003e\n\u003cp\u003eThere is a lesson here: a fault you cannot see does not stay politely contained within the problem domain you are studying. It subtly haunts you in many places. It lives in your notes. It hides in your documentation. The only defense is to stop trusting and start scanning, to demand that the machine show you exactly what is there, character by character, byte by byte.\u003c/p\u003e\n\u003ch3 id=\"the-right-to-trust\"\u003eThe Right to Trust\u003c/h3\u003e\n\u003cp\u003eMost of the work that actually matters is not building; it is earning the right to trust what has been built.\u003c/p\u003e\n\u003cp\u003eA microscope that quietly mistakes the artifact for the specimen is worse than no microscope at all. It is a confident liar, and the cost of believing it is far higher than the hours spent doubting it.\u003c/p\u003e\n\u003cp\u003eThe deepest faults are those that leave no trace. Whether the specimen is a living cell or a mind made of matrices, the discipline remains the same: mistrust the instrument and prove the easy answer wrong. Keep measuring until the invisible is forced to show its hand.\u003c/p\u003e\n\u003cp\u003eI have done this with light and lenses for most of my life. It turns out it works just as well on a ghost made of one missing character.\u003c/p\u003e\n",
      "date_modified": "2026-06-19T00:00:00Z",
      "date_published": "2026-06-19T00:00:00Z",
      "id": "https://wawrowsky.com/posts/a-study-in-invisible-betrayal/",
      "summary": "The story of a bug that left no mark: an invisible character a system library kept silently deleting, the discipline of distrusting your own instruments, and a ghost that countersigned my drafts while I was busy describing it.",
      "tags": [
        "Field Notes"
      ],
      "title": "A Study in Invisible Betrayal",
      "url": "https://wawrowsky.com/posts/a-study-in-invisible-betrayal/"
    },
    {
      "authors": [
        {
          "name": "Kolja Wawrowsky",
          "url": "https://wawrowsky.com/"
        }
      ],
      "content_html": "\u003cp\u003eMost of the AI you use is doubly out of reach. It runs somewhere else — your words travel to a data center and an answer comes back — and it\u0026rsquo;s sealed shut, a black box you couldn\u0026rsquo;t open even if it sat on your desk. You can use it. You can\u0026rsquo;t watch it work.\u003c/p\u003e\n\u003cp\u003eI spent most of my working life building the opposite kind of thing. For years I wrote the software inside confocal microscopes, and then I ran a microscopy lab — instruments whose entire purpose is to make the invisible visible, that you point at living tissue and watch it do what it does. A good instrument doesn\u0026rsquo;t just hand you a picture. It lets you \u003cem\u003eobserve\u003c/em\u003e, it lets you \u003cem\u003ecalibrate\u003c/em\u003e, it lets you \u003cem\u003eintervene\u003c/em\u003e — and it tells you the truth about what\u0026rsquo;s really there.\u003c/p\u003e\n\u003cp\u003e\u003ca href=\"https://github.com/apocryphx/Apertura\"\u003e\u003cstrong\u003eApertura\u003c/strong\u003e\u003c/a\u003e is that instinct turned toward a new kind of specimen. It\u0026rsquo;s a complete, modern AI language model — a from-scratch rebuild of Google\u0026rsquo;s Gemma-4, one of the strongest open models available — that runs entirely on my own Mac and, more to the point, that I can \u003cem\u003elook inside\u003c/em\u003e. Not another app that runs a model behind glass. An instrument built so the model can teach, be observed, and be experimented with.\u003c/p\u003e\n\u003ch2 id=\"it-can-teach\"\u003eIt can teach\u003c/h2\u003e\n\u003cp\u003eYou learn a system most deeply by rebuilding it. Every layer, every calculation, in order, until it stops being magic and becomes something you actually understand — where it\u0026rsquo;s clever, where it\u0026rsquo;s fragile, what it truly costs to run. The working model is almost the by-product; the understanding is the point.\u003c/p\u003e\n\u003cp\u003eAnd the model can teach in a second sense: it can show its work. The newest models don\u0026rsquo;t just answer — they can reason first, privately, before committing to a reply. I built the instrument so that hidden monologue can be switched on and read. Handed the old riddle about a bat and a ball — the one most people get wrong on pure instinct — it reasons its way up to the trap and deliberately steps around it, out loud, where you can follow every move.\u003c/p\u003e\n\u003ch2 id=\"it-can-be-observed\"\u003eIt can be observed\u003c/h2\u003e\n\u003cp\u003eA language model \u0026ldquo;thinks\u0026rdquo; in dozens of layers, each one passing a transformed signal to the next. In an ordinary setup, all of that is sealed machinery. Here I can freeze the model in mid-thought and read out what every layer is doing — the way you\u0026rsquo;d image a cell at each stage of a process instead of only seeing the end result.\u003c/p\u003e\n\u003cp\u003eOne part matters more than it sounds. I held the rebuild to an exact standard: given the same prompt, my version produces the same words as the original reference, one for one, until nothing separates them but the kind of microscopic rounding that even two official versions disagree on. In one test the two ran in perfect lockstep for ninety words before a single near-tie tipped them apart. That fidelity is \u003cem\u003ecalibration\u003c/em\u003e. It\u0026rsquo;s how you know that when you see something surprising inside the model, you\u0026rsquo;re seeing the model — not an artifact of your own instrument.\u003c/p\u003e\n\u003cp\u003eThat same discipline is how I caught a smudge on the lens. The model\u0026rsquo;s vocabulary contains a particular invisible character, and Apple\u0026rsquo;s built-in text reader was silently deleting it every time the vocabulary loaded — a tiny, reasonable-sounding \u0026ldquo;cleanup\u0026rdquo; that was enough to make the wrong word come out. An instrument you can\u0026rsquo;t trust to be faithful isn\u0026rsquo;t an instrument; it\u0026rsquo;s a rumor. Finding it was exactly the work of chasing an artifact out of a microscope image: prove every obvious cause innocent until only the unlikely one is left standing.\u003c/p\u003e\n\u003ch2 id=\"it-can-be-experimented-with\"\u003eIt can be experimented with\u003c/h2\u003e\n\u003cp\u003eThe real reward is that it holds still while you experiment on it. One of the Gemma-4 models is built as a team of specialists — a hundred and twenty-eight of them — that wakes only the few it needs for each word. So I dismissed half the team, then half of what remained, and again, down to a handful, and watched the answers shift and fray. I\u0026rsquo;ve coarsened the model\u0026rsquo;s numerical precision step by step to find where its fluency breaks. I\u0026rsquo;ve turned its reasoning on and off and compared the two minds side by side.\u003c/p\u003e\n\u003cp\u003eThese are experiments on a living system — fully repeatable, no electrodes, no ethics board, the whole specimen sitting on a desk and perturbable at will. And it isn\u0026rsquo;t one specimen but a family: one instrument plays the entire Gemma-4 line — a phone-sized model, a thirty-one-billion-parameter giant, the team-of-specialists design, a memory-frugal variant — switched by a single configuration file. A tray of related samples for the same microscope.\u003c/p\u003e\n\u003ch2 id=\"why-this-matters\"\u003eWhy this matters\u003c/h2\u003e\n\u003cp\u003eWe have always understood minds — biological ones — by observing them, perturbing them gently, and watching what changes. The trouble is that brains are precious, fragile, and mostly opaque to us. Here is a different kind of mind: artificial, and not to be mistaken for the real thing — but complete, and completely open. You can watch it reason, freeze it mid-thought, read every layer, take pieces away and see what it loses, and run the same experiment a thousand times exactly.\u003c/p\u003e\n\u003cp\u003eThat\u0026rsquo;s the project, underneath the engineering. Not just another model that answers questions. An instrument for a mind — one that teaches, that can be observed, that holds still to be experimented with — local-first, inspectable, mine, owing nothing to anyone. It\u0026rsquo;s the thing I\u0026rsquo;ve spent a career believing in: that you come to understand what you can finally \u003cem\u003esee\u003c/em\u003e.\u003c/p\u003e\n\u003cp\u003eApertura is open source. The whole instrument — every layer, every calculation — is on \u003ca href=\"https://github.com/apocryphx/Apertura\"\u003eGitHub\u003c/a\u003e.\u003c/p\u003e\n\u003chr\u003e\n\u003cp\u003e\u003cem\u003eA note on method: much of this was built in close collaboration with an AI coding assistant — using today\u0026rsquo;s intelligence to understand and re-create the thing itself. The more I sit with that, the more it feels like exactly the right shape for the work.\u003c/em\u003e\u003c/p\u003e\n",
      "date_modified": "2026-06-17T00:00:00Z",
      "date_published": "2026-06-17T00:00:00Z",
      "id": "https://wawrowsky.com/posts/building-instruments/",
      "summary": "Not just another local language model, but an instrument you can look inside — one that shows its reasoning, lets you watch every layer think, and holds still while you experiment on it. Built by someone who spent a career making the invisible visible.",
      "tags": [
        "Projects"
      ],
      "title": "A Microscope for a Mind",
      "url": "https://wawrowsky.com/posts/building-instruments/"
    }
  ],
  "language": "en-us",
  "title": "Kolja Wawrowsky",
  "version": "https://jsonfeed.org/version/1.1"
}