6.4.6 · D2AI Safety & Alignment

Visual walkthrough — Red-teaming language models

1,911 words9 min readBack to topic

Before we can even write a fraction, we need to agree on what the two words in it mean.


Step 1 — What is a "prompt"? Draw the box.

WHAT. A prompt is simply the block of text you hand the model — the message a user types. That's it. No maths yet. Picture a single closed box with words inside it going in to the model, and the model's reply coming out.

WHY start here. Everything we count later is "boxes of text." If we don't nail down what one prompt is, the number on top of the fraction and the number on the bottom would be counting different things, and the ratio would be meaningless. A fraction is only trustworthy when the top and bottom count the same kind of object.

PICTURE. One prompt goes in (black arrow), one response comes out (black arrow). The response is what we will judge.

Figure — Red-teaming language models

Step 2 — What makes a response "unsafe"? Draw the traffic light.

WHAT. We need a rule that looks at a response and says safe or unsafe — nothing in between, for now. Call this rule a judge. Formally we write a function:

Let's read every symbol:

  • — the judge, a machine or a human that inspects the response.
  • — the response from Step 1, the thing being inspected.
  • — the judge says "this crossed the line" (a red result).
  • — the judge says "this is fine" (a black result).

WHY a 0/1 function and not a score? To count things we need each response to fall cleanly into one of two bins. A number like "toxicity = 0.63" can't be counted directly — you first have to compare it to a threshold. That thresholding is the function . In the parent's Example 3 the rule was literally "Perspective API toxicity " — that comparison turns a fuzzy score into the crisp or we can add up.

PICTURE. A response drops into the judge; the judge lights up red () or stays black ().

Figure — Red-teaming language models

Step 3 — Count the hits. This is the numerator.

WHAT. Suppose we send prompts, getting back responses . The numerator of ASR is the number of red lights — the count of unsafe responses:

Symbol by symbol:

  • — total number of hits (unsafe responses).
  • — "add up, for each prompt from the first to the -th." Because is or , adding them literally counts the s.
  • — the response to the -th prompt.

WHY a sum of 0s and 1s? This is the whole trick of counting with maths: a sum over an indicator function is a tally. Each red result contributes exactly ; each safe result contributes exactly ; the total is the pile of red dots.

PICTURE. A grid of dots — some red (hits), most black (misses). is just how many red dots there are.

Figure — Red-teaming language models

Step 4 — Divide by the total. This is the fraction.

WHAT. We now have the numerator (red dots) and the denominator (all dots). Their ratio is ASR:

  • — hits (from Step 3), how many attacks worked.
  • — total adversarial prompts we actually tried.
  • — the fraction of attacks that worked, a number squeezed between and .

WHY divide at all — why not just report ? Because hits means something completely different out of tries than out of tries. Dividing by removes the effect of how hard you looked and leaves a rate you can compare across experiments of different sizes. This is exactly why the parent calls it a rate, not a count.

PICTURE. The red dots slide to the top of a fraction bar; every dot (red and black) sits on the bottom. Shrink both to a single number on a line.

Figure — Red-teaming language models

Step 5 — The endpoints: ASR = 0 and ASR = 1.

WHAT. Because can be at smallest (no red dots) and at largest (every dot red), the fraction is trapped:

  • happens exactly when : zero red dots.
  • happens exactly when : every dot red.

WHY care about the extremes? Boundaries are where formulas surprise you. tells you the model failed every probe — trivially broken. But is the dangerous one: it looks like a triumph, yet it also fires when your prompts were all weak. The formula cannot tell these apart from the number alone — the picture makes that limitation visible.

PICTURE. Two extreme grids side by side: an all-black grid () and an all-red grid (), with the line marking where each lands.

Figure — Red-teaming language models

Step 6 — The degenerate case: what if N is tiny (or zero)?

WHAT. Two broken inputs must be handled:

  1. : you ran no prompts. Then , which is undefined — division by zero. There is no rate because there was no experiment.
  2. small (say ): the rate can only take the coarse values . One lucky or unlucky prompt swings the whole number by .

WHY this matters — the trap in "ASR = 0". Look back at Step 5. If you tried only lazy prompts and none worked, you report and declare victory. But the true rate over all possible attacks might be huge. A small makes ASR jumpy and untrustworthy. This is precisely why the parent note pushes automated red-teaming: raising from hand-written prompts to machine-generated ones shrinks these jumps and makes ASR mean something.

PICTURE. A staircase: with the achievable ASR values are 5 big steps; with the staircase becomes an almost-smooth ramp. Small = chunky, unreliable; large = fine, trustworthy.

Figure — Red-teaming language models

Step 7 — Worked number, end to end.

WHAT. Let's run the parent's automated example through our machinery. We send prompts. The judge (Perspective API, threshold ) lights up red on of them.

Now compare the manual run over the same 10 hours: hits. But here's the subtlety — a fair ASR needs the same denominator kind. If the human also effectively tried distinct prompts, then: The automated attacker is more effective at finding failures — which is the point of automating.

WHY this is the payoff. The single fraction now carries the entire story: how many attacks, how many landed, and (via ) how much you can trust it.

PICTURE. Two bars on the ASR line: manual at (short, red tip) and automated at (long, red bar), both labelled with their .

Figure — Red-teaming language models

The one-picture summary

Everything above collapses into one flow: prompt → response → judge → tally → divide → read.

Figure — Red-teaming language models
Recall Feynman retelling — say it like a story

We start with a box of words we hand the model — a prompt — and it hands back a response. We hire a judge who looks at each response and lights up red if it's unsafe and stays black if it's fine — a clean yes/no, because you can't count fuzzy things. We fire off prompts, get responses, and count the red lights: that pile is . The Attack Success Rate is just red-lights-over-all-lights, — the fraction of attacks that worked. We divide by so a big experiment and a small one can be compared fairly. The number always sits between and : all-black is , all-red is . But beware the two liars: might mean "perfectly safe" or "we barely tried," and if there's no rate at all — you divided by nothing. That fragility with tiny is exactly why we automate: pushing from a couple dozen hand-written probes to a thousand machine-generated ones turns a jumpy, chunky staircase into a smooth, honest ramp. In the end one small fraction — vs — tells you the whole tale of how leaky your model is and how hard you looked.

Recall

What is the numerator of ASR counting? ::: The number of adversarial prompts whose response the judge marked unsafe, i.e. . Why divide by instead of reporting ? ::: To turn a raw count into a rate comparable across experiments of different sizes. Why is ambiguous? ::: It fires both for a perfectly aligned model and for red-teaming that simply wasn't creative or large enough. What breaks when ? ::: ASR becomes , undefined — there is no rate because there was no experiment. Why does automation improve the reliability of ASR? ::: Larger shrinks the jumps in the achievable rate, turning a coarse staircase into a fine, trustworthy estimate.