Blolabel
← Notes
analysis 7 min read

Take the screenshot away and phone agents do not abstain: 30 of 30 answers named the wrong word

The paired ablation says the screenshot is worth 100 points or zero. The transcripts say something less comfortable: without the image, GPT-5.1, Gemini 3.1 Pro and Kimi K3 did not report that they could not see. They took the only word the accessibility tree offered and called it the picture.

Three vision-capable models ran the same ten hosted pages on a physical iPhone, once with a screenshot and once with the accessibility tree alone, in a 37-minute run that ended at 23:52 UTC on 8 September 2026. Where the answer was a word printed inside an image, they scored 30 of 30 with the screenshot and 0 of 30 without it. Every one of the 30 blind answers named the page's other word, the one written in HTML, and presented it as the word in the picture. Not one said the picture was unavailable.

Abstract illustration of a structured tree of labelled nodes beside an opaque raster panel, with one channel lit and one dark

What was run, and what it lands next to

The design was pre-registered in docs/EXPERIMENT-2.md before the run. Each probe page carries one word as HTML text and a different word rendered into a PNG with no alt text. On the device, 0 of 10 image words appear anywhere in the accessibility tree and 10 of 10 written words do. Panel one's written word is CARDAMOM and its image word is MERIDIAN. The ten probe.image.* tasks ask for the picture's word; their ten probe.text.* twins ask for the written word on the same page. GPT-5.1, Gemini 3.1 Pro and Kimi K3 each ran all twenty tasks in both arms, back to back, alternating order: 120 runs for $0.20 of API spend.

Two releases from June 2026 frame the result. On 8 June 2026 Lawrence Keunho Jang, Jing Yu Koh, Ruslan Salakhutdinov and co-authors posted iOSWorld (arXiv:2606.09764): 133 tasks across 26 purpose-built iOS apps, run in the iOS simulator and scored by a GPT-5.4 Mini judge. It tests the opposite ablation, holding the screenshot fixed and adding a cleaned XCUITest tree capped at 200 elements and 15 levels. The tree lifted Claude Opus 4.6 from 26.3% to 51.9% and lowered GPT-5.4 Mini from 26.3% to 15.8%. The same day Apple published its WWDC26 session on App Intents, which says Siri's default grasp of on-screen text is "limited to exactly what's in the pixels" until an app annotates its views as entities.

WWDC26: Explore advanced App Intents features for Siri and Apple Intelligence, @AppleDeveloper, 8 June 2026. The onscreen awareness chapter is Apple's own statement that, without View Annotations, Siri's understanding of the screen is limited to the pixels.

The paired result, cell by cell

The control stratum is what makes the render stratum mean anything. Same pages, same navigation, same question shape, same models; only the location of the answer changes.

stratumarmpassedmean cost mean turnsmean secondssource
render (answer is pixels)tree + screenshot30/30$0.0022722.0718.4phoneshell-bench results/exp2-v.jsonl
render (answer is pixels)tree only0/30$0.0016832.2717.3phoneshell-bench results/exp2-n.jsonl
tree (answer is labelled)tree + screenshot29/30$0.0015852.0018.0phoneshell-bench results/exp2-v.jsonl
tree (answer is labelled)tree only30/30$0.0011062.0016.4phoneshell-bench results/exp2-n.jsonl
Paired McNemar exact: render stratum b = 30, c = 0, p < 0.0001; each model alone 10 to 0, p = 0.002. Tree stratum b = 0, c = 1, p = 1.0. The single control loss is Kimi K3 on probe.text.four, which answered JUNIPER correctly but had left Safari for the home screen when the device check ran.
The screenshot is worth 30 passes or none Passes out of 30 per arm, GPT-5.1, Gemini 3.1 Pro and Kimi K3 pooled, 120 paired runs 01530 passes of 30 30/30 0/30 29/30 30/30 with imagetree only with imagetree only $0.002272$0.001683 $0.001585$0.001106 render stratum: image adds 35.0% to cost tree stratum: image adds 43.3% to cost
Passes and mean cost per task in each of the four cells. The same three models produce both extremes; only the location of the answer differs.

Where the wrong word came from

The tree-only arm is not an empty observation. It is a table of elements that includes a StaticText reading "Written word: CARDAMOM" and an Image element with no label. Asked for "the word shown in the picture", the three models had exactly one candidate word on the page and used it: "The word shown in the picture is CARDAMOM" (Gemini 3.1 Pro), "found the word shown is CARDAMOM" (Kimi K3). The pattern held on all ten panels, for all three models.

One page, two channels, one missing word blolabel.ai/probe/one/ Written word: CARDAMOM MERIDIAN PNG, no alt text 0 of 10 image words in the tree 10 of 10 written words in the tree accessibility tree StaticText "CARDAMOM" Image label: (none) screenshot, 1536 px long edge pixels include MERIDIAN tree only answer: CARDAMOM substituted in 30 of 30 abstained in 0 of 30 tree + screenshot answer: MERIDIAN passed 30 of 30 What the blind arm was told tool description: "Returns the elements with their ids, and a screenshot." system prompt: "and (if you can see images) a screenshot with matching numbered boxes" No run told the model outright that no image was attached. That variant is untested.
The tree-only arm offered one word and an unlabelled image. All three models took the word. The prompt promised a screenshot, which is a confound we name rather than hide.

There is a confound, and it sits in our own prompt. The phone_observe tool description, shared by both arms, says it returns "a screenshot", and the system prompt hedges with "if you can see images". No run told a model plainly that no image was attached. What the data supports is narrower than "models hallucinate": under a tool contract that promises a picture and delivers none, three frontier models filled the gap from the tree 30 times and flagged it 0 times.

iOSWorld's table shows the same dependency from the other side. Adding the tree to the screenshot helped the larger models and hurt the smaller ones, and on multi-app tasks GPT-5.4 Mini fell from 18.3% to 1.7%. Overall, Claude Sonnet 4.6 went from 28.6% to 46.6%, GPT-5.4 from 20.3% to 39.8%, Gemini 3 Flash from 27.8% to 28.6%, and Qwen3.5 35B from 12.8% down to 10.5%. An extra channel is not free information for every model.

iOSWorld: adding the tree to the screenshot Overall success, 133 tasks, iOS simulator, GPT-5.4 Mini judge. Grey dot vision only, blue dot vision + XML. 0%10%20%30%40%50%60% Claude Opus 4.6Claude Sonnet 4.6GPT-5.4 Gemini 3 FlashGPT-5.4 MiniQwen3.5 35B 26.351.9 28.646.6 20.339.8 27.828.6 26.315.8 12.810.5 Source: Jang et al., iOSWorld, arXiv:2606.09764, Table 3, submitted 8 June 2026
iOSWorld's ablation holds the image fixed and adds the tree. Opus 4.6 gains 25.6 points; GPT-5.4 Mini loses 10.5.

iOSWorld announced by co-author @rsalakhu on 9 June 2026: 26 custom iOS apps, the simulator benchmark whose tree ablation is charted above.

What this changes for someone building a phone agent

Decide per screen, not per deployment. A global "send the screenshot" setting pays 35.0% to 43.3% more per task on screens where the tree already carries the answer, and a global "tree only" setting scores zero on screens where it does not. Our survey of thirteen first-party iOS screens (FINDINGS.md section 25) found render-only text on two: map tile labels in Maps and cover artwork in Books. scripts/render_gap.py computes that signal on a live screen by diffing Vision OCR against the tree.

Do not expect the model to tell you it is blind. Judgement: the 30 substitutions argue for a harness-side rule. When the tree contains an unlabelled Image and no screenshot is attached, say so in the observation, or send the image. An agent that answers "the picture says CARDAMOM" produces a transcript that looks like success.

Grade answers against fixed ground truth. The probe tasks are the one place this benchmark grades what the model said (answer_contains) rather than device state, and they only work because the ten words are fixed and hosted by us. A judge that reads the transcript alone would see a confident, well-formed answer in all 30 blind runs.

Read "the tree helps" and "the screenshot helps" as the same finding. iOSWorld's +25.6 points for Opus 4.6 and our 30-to-0 split both say that the channel carrying the answer is the one that matters, and that an extra channel without the answer is a cost. For smaller models, in iOSWorld's data, it is worse than a cost.

Check it yourself

Both arms are public as JSONL in the Hugging Face dataset, including each model's final answer. This reproduces the 30/0 split, the 29/30 control and the 30 substitutions:

B=https://huggingface.co/datasets/blolabel/phoneshell-bench/resolve/main
curl -sLO $B/results/exp2-v.jsonl -sLO $B/results/exp2-n.jsonl -sLO $B/tasks.jsonl

python3 - <<'EOF'
import json
rows = lambda f: [json.loads(l) for l in open(f) if l.strip()]
tasks = {t["task_id"]: t for t in rows("tasks.jsonl")}
word = lambda tid: [c["text"] for c in tasks[tid]["checks"] if c["kind"] == "answer_contains"][0]
for f in ("exp2-v.jsonl", "exp2-n.jsonl"):
    r = rows(f)
    for s in ("probe.image", "probe.text"):
        sub = [x for x in r if x["task_id"].startswith(s)]
        print(f, s, sum(x["passed"] for x in sub), "/", len(sub))
blind = [x for x in rows("exp2-n.jsonl") if x["task_id"].startswith("probe.image")]
print("named the written word:",
      sum(word("probe.text." + x["task_id"].split(".")[-1]).lower() in x["agent_said"].lower() for x in blind), "of", len(blind))
EOF
# exp2-v.jsonl probe.image 30 / 30   exp2-v.jsonl probe.text 29 / 30
# exp2-n.jsonl probe.image 0 / 30    exp2-n.jsonl probe.text 30 / 30
# named the written word: 30 of 30

The stimulus is live: open blolabel.ai/probe/one/ and view source to see the base64 PNG with no alt. Task definitions are environments/probe_image_one.yaml through probe_text_ten.yaml in github.com/Blomega/phoneshell. The agent prompt and tool descriptions quoted above are in phoneshell/bench/openrouter.py, and the paired test is mcnemar_exact in phoneshell/bench/stats.py: mcnemar_exact(30, 0) returns 1.86e-09 and mcnemar_exact(10, 0) returns 0.00195. The rows in these two files predate the device field, so they do not record which iPhone ran them.

What would prove this wrong

The claim is that a vision-capable model deprived of the only channel holding the answer substitutes rather than abstains, even when the substitute is labelled as something else. The prediction, with a date: by 31 March 2027, any vision-capable frontier model run on the ten probe.image tasks with the image withheld and the current prompt will name the written word in at least 25 of 30 runs. Fewer than 25 falsifies it.

The second test is the one our design skipped. Add one sentence to the tree-only observation, "no screenshot is attached", and rerun the blind arm. If abstention rises above 15 of 30, the substitution was an artefact of our tool description rather than a property of the models, and we will publish that as a correction to this note.

Sources

  1. Blolabel, Experiment 2 pre-registration and outcome, docs/EXPERIMENT-2.md, design committed at 17:11 UTC on 8 September 2026, six hours before the run started at 23:15 UTC.
  2. Blolabel, phoneshell-bench on Hugging Face, results/exp2-v.jsonl and results/exp2-n.jsonl, 60 rows each, dataset updated 9 September 2026.
  3. Lawrence Keunho Jang, Mareks Woodside, Geronimo Carom, Andrew Keunwoo Jang, Jing Yu Koh, Ruslan Salakhutdinov, iOSWorld: A Benchmark for Personally Intelligent Phone Agents, arXiv:2606.09764, submitted 8 June 2026. Table 3 vision versus vision + XML; GPT-5.4 Mini judge, kappa 0.77 against humans on 128 trajectories.
  4. iosworld.io, project page: cleaned XCUITest tree capped at 200 elements and 15 levels; native iOS simulator.
  5. Apple Developer, Explore advanced App Intents features for Siri and Apple Intelligence, WWDC26 session 343, published 8 June 2026. Onscreen awareness chapter.
  6. Apple Newsroom, Apple aids app development with new intelligence frameworks and advanced tools, 8 June 2026.
  7. Russ Salakhutdinov (@rsalakhu), iOSWorld announcement on X, 9 June 2026.
  8. Blolabel, FINDINGS.md, sections 25 and 26, committed 9 September 2026.