Description of the bug
With server-side (automatic) activity detection, a 1.0 s pause in the middle of one caller
sentence makes gemini-3.1-flash-live-preview mis-segment the turn, reproducibly, in a
minimal configuration: a one-line system instruction (158 characters), no tools, no session
resumption, and no automaticActivityDetection block at all — the server's own default VAD is
what segments the speech. Every measurement below has a control arm in the same session that
differs only by the 1.0 s of silence.
- The turn is closed while the caller is still speaking. The input transcription of the
first burst is delivered during the second burst — 24 TRIGGER trials out of 24, across
four configurations, 0 out of 24 in the control arm of the same sessions. The model starts
generating an answer to half a sentence, and in 21 of those 24 trials a turnComplete for
that generation arrives 0.13–0.50 s before the last audio chunk of the utterance is sent;
never in any control trial.
- The input transcription of the final burst is always slower than every control trial of the
same session — 24/24. 1.61–1.78 s against 1.14–1.39 s in the default configuration.
- With
thinkingConfig.thinkingLevel set, the generation on that boundary turn completes
with zero output tokens — usageMetadata with responseTokenCount absent (out_tokens=None
in the SDK). 12 of the 15 trials that requested a thinking level, 0 of the 9 that did not.
The caller gets no answer at all for that turn.
The same script, the same synthesised audio bytes and the same default configuration on
gemini-2.5-flash-native-audio-latest produce 0 empty generations out of 9 TRIGGER trials.
The 1.0 s pause costs about the same there — TRIGGER 0.56–0.64 s against CONTROL 0.03–0.17 s —
but it is added to a baseline an order of magnitude lower than 3.1's 1.14–1.39 s, and it never
empties a generation. The client is not what differs.
What this report is not. It is not a request to raise silenceDurationMs: we are aware the
value is capped at 2000 ms, and that committing a turn after a short silence has already been
described as expected behaviour
(forum 172306). This report is
about what happens after that commit: a turn closed while input audio is still arriving on the
wire, and — with a thinking level set — a generation billed with zero output tokens while the
caller is waiting.
Actual vs expected behavior
|
expected |
observed on gemini-3.1-flash-live-preview |
| turn boundary |
a turn is not committed, and no answer generated, while input audio for it is still being received |
first burst transcribed during the second burst: 24/24 TRIGGER, 0/24 CONTROL. turnComplete 0.13–0.50 s before the last audio chunk: 21/24 TRIGGER, 0/24 CONTROL |
| transcription of the final burst |
comparable to an uninterrupted utterance (1.14–1.39 s here) |
1.61–1.78 s, 24/24 slower than every control trial of the same session |
| boundary turn output |
a completed generation produces output, or no generation is completed |
usageMetadata with no responseTokenCount: 12/15 with thinkingLevel set, 0/9 without |
| control model, same bytes, same config |
— |
gemini-2.5-flash-native-audio-latest: 0/9 empty generations, TRIGGER delay 0.24–0.64 s |
Environment
|
|
| Model |
gemini-3.1-flash-live-preview (control: gemini-2.5-flash-native-audio-latest) |
| Transport |
google-genai Python SDK 1.73.1, client.aio.live.connect() |
| Endpoint / backend |
Gemini API — generativelanguage.googleapis.com, API key auth. Not Vertex AI. |
| Python / platform |
CPython 3.12.13, macOS 26.5.1 arm64 |
| Audio |
PCM s16le, 16 000 Hz, 1 channel, 16-bit; audio/pcm;rate=16000; 20 ms chunks (320 samples / 640 bytes) sent every 20 ms, continuously, silence included |
| Activity detection |
no automaticActivityDetection block is sent — server default |
| System instruction |
158 characters, one line (the --system-chars 60000 runs are a documented cross-check, not the default) |
| Sessions (UTC) |
11 Live sessions, started between 2026-08-18T10:39:54Z and 2026-08-18T11:16:11Z; the exact start of each is in the ENVIRONMENT block of that run in the gist output |
setup payload actually sent, verbatim and complete — this is the whole configuration under
test, nothing is elided:
{
"setup": {
"model": "models/gemini-3.1-flash-live-preview",
"response_modalities": ["AUDIO"],
"thinking_config": {"include_thoughts": false, "thinking_level": "MEDIUM"},
"system_instruction": {
"parts": [{"text": "Sei l'assistente telefonico di un servizio di consulenza. Parli solo italiano, con frasi brevi e cortesi. Rispondi sempre a voce a quello che dice il cliente."}],
"role": "user"
},
"input_audio_transcription": {},
"output_audio_transcription": {},
"realtime_input_config": {
"activity_handling": "START_OF_ACTIVITY_INTERRUPTS",
"turn_coverage": "TURN_INCLUDES_ONLY_ACTIVITY"
}
}
}
Per-trial UTC timestamps for server-side log lookup are in the gist output. Happy to provide
our Google Cloud project number privately through whichever intake form you prefer — it is
deliberately not in this public body.
Reproducer
gemini_live_repro.py is in this gist: https://gist.github.com/IngLP/124873f0574ada091ab4324e5ff12432 — together with gemini_live_repro_output.txt, the unedited output of all eleven runs cited below. It is self-contained: no audio file is
shipped, the two speech pieces are synthesised at run time with the system TTS (say on macOS,
espeak-ng elsewhere), resampled to 16 kHz mono 16-bit PCM and level-matched, so the speech
bytes are byte-identical between the two arms. The only difference between arms is 1.0 s of
PCM silence in the middle:
CONTROL [head][tail] 1.50 s, spoken back to back
TRIGGER [head][1.0 s of PCM silence][tail] 2.50 s
Both arms end with the same final burst, so the delay measured from the last audio chunk of that
burst is attributable to the pause and to nothing else. Arms alternate inside one session, same
config, same connection.
export GEMINI_API_KEY=...
pip install google-genai==1.73.1
mkdir repro && cd repro # put the script in a directory of its own; Python
# puts the script's directory first on sys.path, so a
# neighbouring types.py/enum.py shadows the stdlib
python gemini_live_repro.py --reps 3 --max-sessions 1 # RUNS 1, 2, 11
python gemini_live_repro.py --thinking omit --reps 3 --max-sessions 1 # RUNS 3-4
python gemini_live_repro.py --system-chars 60000 --reps 3 --max-sessions 1 # RUNS 6-7
python gemini_live_repro.py --system-chars 60000 --thinking omit \
--reps 3 --max-sessions 1 # RUN 5
python gemini_live_repro.py --model gemini-2.5-flash-native-audio-latest \
--reps 3 --max-sessions 1 # RUNS 8-9
python gemini_live_repro.py --model gemini-2.5-flash-native-audio-latest \
--system-chars 60000 --reps 3 --max-sessions 1 # RUN 10
python gemini_live_repro.py --dry # offline: synthesises the audio and audits the send cadence, spends nothing
One run is one Live session of ~50 s and 6 trials. --reps and --max-sessions only bound the
spend; no run in this report changes the configuration except where the flag says so, and
RUN 11 in the attached output is the script exactly as published, with no configuration flags at
all.
The audio stream is continuous — including during the pause
This is the first thing that gets asked (e.g.
dotnet-genai#269), so the script measures
it instead of asserting it. The "pause" is not a pause in sending: the caller leg pushes one
20 ms PCM frame every 20 ms for the whole session, and during the pause those frames are digital
zeros. Every trial prints chunks sent vs expected and the mean/max interval between consecutive
sends, for the whole utterance and separately for the pause window. From RUN 11:
TRIGGER #1 stream: 125 chunks sent during the utterance (expected ~125),
interval mean 20.0 ms / max 24.1 ms;
DURING THE 1.0 s PAUSE: 50 silence chunks (expected ~50), max interval 24.1 ms
[session1] stream continuity over the whole session: 2519 chunks in 50.6s (expected ~2529),
interval mean 20.0 ms / max 24.1 ms — the sender never stopped.
Worst inter-chunk interval anywhere in the eleven sessions in the gist: 25.0 ms (RUN 4), against
a 20 ms nominal period; the other ten stay under 24.2 ms. There is no gap in the stream for the
server to interpret as end of input.
Verbatim output
Full output of all eleven runs is in the gist as gemini_live_repro_output.txt (93 KB, unedited): https://gist.github.com/IngLP/124873f0574ada091ab4324e5ff12432.
The load-bearing part of one TRIGGER trial from RUN 11 — the script as published, no flags
except --reps 3 --max-sessions 1, which only bound the spend (t= is seconds from connect,
(+…) is seconds relative to the last audio chunk of the final burst):
--- TRIGGER #1 -------------------------------------------------
11:16:25.362Z t= 14.16s (+ -2.49s) caller speech starts
11:16:27.853Z t= 16.65s (+ -0.00s) [!] 1 transcription fragment(s) arrived DURING the caller's speech: 'Buongiorno.'
11:16:27.854Z t= 16.65s (+ 0.00s) last audio chunk of the FINAL burst sent
11:16:27.415Z t= 16.21s (+ -0.44s) server: interrupted
11:16:27.492Z t= 16.29s (+ -0.36s) server: turn_complete
11:16:27.492Z t= 16.29s (+ -0.36s) server: usage out_tokens=None
11:16:29.466Z t= 18.26s (+ 1.61s) FIRST TRANSCRIPTION OF THE FINAL BURST: 'Sì, grazie.'
11:16:30.256Z t= 19.05s (+ 2.40s) model audio starts
stream: 125 chunks sent during the utterance (expected ~125), interval mean 20.0 ms / max 24.1 ms;
DURING THE 1.0 s PAUSE: 50 silence chunks (expected ~50), max interval 24.1 ms
=> delay 1.61s, 1 EMPTY generation(s) (out_tokens=None)
Read the ordering: the server has committed the turn on the first burst and started answering it,
so the transcription 'Buongiorno.' is delivered at t=16.65 s — inside the second burst — the
half-sentence answer is interrupted by the rest of the same sentence at t=16.21 s, and its
turnComplete at t=16.29 s, still 0.36 s before the caller's last audio chunk, carries
usage out_tokens=None.
The identical trial with no thinkingConfig at all (RUN 4) shows the same broken segmentation
and a non-empty interrupted generation:
--- TRIGGER #2 -------------------------------------------------
11:01:24.067Z t= 27.18s (+ -2.49s) caller speech starts
11:01:26.553Z t= 29.67s (+ -0.00s) [!] 1 transcription fragment(s) arrived DURING the caller's speech: 'Buongiorno.'
11:01:26.554Z t= 29.67s (+ 0.00s) last audio chunk of the FINAL burst sent
11:01:26.130Z t= 29.25s (+ -0.42s) server: interrupted
11:01:26.166Z t= 29.28s (+ -0.39s) server: turn_complete
11:01:26.166Z t= 29.28s (+ -0.39s) server: usage out_tokens=43
11:01:28.260Z t= 31.38s (+ 1.71s) FIRST TRANSCRIPTION OF THE FINAL BURST: 'Sì, grazie.'
11:01:28.265Z t= 31.38s (+ 1.71s) model audio starts
=> delay 1.71s
Summary tables (as printed by the script)
RUNS 1, 2 and 11 — gemini-3.1-flash-live-preview, default configuration (one-line system
instruction, thinkingLevel: MEDIUM; RUN 11 is the script with no configuration flags at all,
only the two that bound the spend):
arm n min p50 max no transcript empty generations turn cut mid-speech
CONTROL 3 1.14 1.25 1.27 0/3 0/3 0/3 RUN 1
TRIGGER 3 1.61 1.61 1.61 0/3 3/3 3/3 RUN 1
CONTROL 3 1.21 1.31 1.35 0/3 0/3 0/3 RUN 2
TRIGGER 3 1.67 1.67 1.78 0/3 3/3 3/3 RUN 2
CONTROL 3 1.25 1.38 1.39 0/3 0/3 0/3 RUN 11
TRIGGER 3 1.61 1.72 1.77 0/3 2/3 3/3 RUN 11
RUN 8 and RUN 9 — gemini-2.5-flash-native-audio-latest, same script, same audio bytes, same
default configuration:
arm n min p50 max no transcript empty generations turn cut mid-speech
CONTROL 3 0.12 0.14 0.15 0/3 0/3 2/3 RUN 8
TRIGGER 3 0.56 0.57 0.62 0/3 0/3 3/3 RUN 8
CONTROL 3 0.03 0.15 0.17 0/3 0/3 2/3 RUN 9
TRIGGER 3 0.57 0.58 0.64 0/3 0/3 3/3 RUN 9
Read honestly, the 2.5 "turn cut mid-speech" column is 4/6 in the control arm too. Those four
are not closed turns: they are the incremental fragment 'Bu' of a transcription still being
streamed, while every TRIGGER case is the complete 'Buongiorno.' of a committed turn. On 2.5 the
pause costs ~0.45 s and never an empty generation; on 3.1 the same column is 0/9 control against
9/9 trigger in the same default configuration, and 0/24 against 24/24 over all configurations.
It is not the size of the system instruction — it is the thinking level
The obvious objection to any report like this is "it is your configuration, not the model". So the
same script was run over the 2×2 of system-instruction size and thinking level, one to three Live
sessions per cell, 3 TRIGGER trials per session:
| system instruction |
thinkingConfig |
TRIGGER trials |
turn cut mid-speech |
empty generations |
TRIGGER delay |
runs |
| 158 chars (default) |
thinkingLevel: MEDIUM |
9 |
9/9 |
8/9 |
1.61–1.78 s |
1, 2, 11 |
| 60 000 chars |
thinkingLevel: MEDIUM |
6 |
6/6 |
4/6 |
1.50–1.70 s |
6, 7 |
| 158 chars |
not sent |
6 |
6/6 |
0/6 |
1.61–2.08 s |
3, 4 |
| 60 000 chars |
not sent |
3 |
3/3 |
0/3 |
1.54–1.71 s |
5 |
The broken segmentation and the delay are the same in all four cells — the size of the system
instruction changes nothing, and the delay is if anything largest in the leanest cell. Only effect
3, the zero-token generation, tracks the thinking level: 12/15 when a thinkingLevel is requested,
0/9 when the field is absent. In every control arm of all four cells the turn is never cut: 0/24.
One precision, because the API has no "thinking off": not sent means no thinkingConfig field in
the setup message, so whatever the server's default is applies. The claim is therefore "an
explicit thinkingLevel is what accompanies the empty generation", not "thinking causes it".
Scope and limits of the claim
- What reproduces every time, in every configuration tested, is the mechanism: the turn is
closed while the caller is still speaking (24/24 TRIGGER trials, 0/24 CONTROL), and the
transcription of the final burst is slower than every control trial of the same session (24/24).
- The empty generation is 12/15 with an explicit
thinkingLevel and 0/9 without. It is
reproducible in the minimal configuration — RUNS 1, 2 and 11 are 8/9 — but it is not
configuration-independent, and this report does not claim it is.
- What does not reproduce at a fixed size is the magnitude of the delay. An earlier in-house
campaign with the same trigger (23 trials, two bursts separated by 1.0 s, same audio path)
measured the final-burst transcription at 2.46–7.11 s with a median of 3.45 s, and 11 of
those 23 above 5.8 s; in that campaign an empty generation accompanied 20 of the 27 turns
whose delay was ≥ 2 s and 0 of the 45 below 2 s. In the runs attached here the same trigger
produced 1.50–2.08 s. We are not claiming the large numbers are the norm — only that the
mechanism is deterministic and the delay varies with load.
- All measurements are clean 16 kHz PCM from a laptop straight to the API, not 8 kHz telephony.
- 3 trials per arm per session is a small n per cell. The per-trial separation is what makes it
readable: every one of the 24 TRIGGER trials is slower than every CONTROL trial of the same
session, and the trials are interleaved inside one connection, so arm and moment cannot be
confounded.
Related issues
Same underlying VAD segmentation, different symptom — none of them reports the empty generation
or the delay of the final burst's transcription:
- python-genai#2580 —
silence_duration_ms not honoured on 3.1 (reproduced by triage 2026-06-11)
- js-genai#1467 — same, with a public repro that splits
[speech][2.0 s silence][speech] into two turns
- cookbook#1263 §2–§3 — effective 2000 ms cap, VAD cutting users mid-sentence
- cookbook#1262 — VAD turn thrashing on 3.1, absent on 2.5 native audio
- forum 172306 — official answer describing the early commit as expected and the 2000 ms cap
We are filing two other reports on the same model. They may share a root cause with this one,
but we have not demonstrated that: cookbook#1329, and a comment with a voice_activity
repro on python-genai#1285.
Questions
- Is a
turnComplete emitted while input audio for that turn is still being received on the
socket the intended behaviour of the default VAD?
- Is a completed generation with no
responseTokenCount an expected outcome for a boundary turn
that gets interrupted, and is there a client-side signal that distinguishes it from a
generation that is still coming? Why does it appear only when thinkingLevel is set?
- Is there a supported way to keep the pre-3.1 segmentation behaviour on
gemini-3.1-flash-live-preview
short of disabling automatic activity detection entirely?
Description of the bug
With server-side (automatic) activity detection, a 1.0 s pause in the middle of one caller
sentence makes
gemini-3.1-flash-live-previewmis-segment the turn, reproducibly, in aminimal configuration: a one-line system instruction (158 characters), no tools, no session
resumption, and no
automaticActivityDetectionblock at all — the server's own default VAD iswhat segments the speech. Every measurement below has a control arm in the same session that
differs only by the 1.0 s of silence.
first burst is delivered during the second burst — 24 TRIGGER trials out of 24, across
four configurations, 0 out of 24 in the control arm of the same sessions. The model starts
generating an answer to half a sentence, and in 21 of those 24 trials a
turnCompleteforthat generation arrives 0.13–0.50 s before the last audio chunk of the utterance is sent;
never in any control trial.
same session — 24/24. 1.61–1.78 s against 1.14–1.39 s in the default configuration.
thinkingConfig.thinkingLevelset, the generation on that boundary turn completeswith zero output tokens —
usageMetadatawithresponseTokenCountabsent (out_tokens=Nonein the SDK). 12 of the 15 trials that requested a thinking level, 0 of the 9 that did not.
The caller gets no answer at all for that turn.
The same script, the same synthesised audio bytes and the same default configuration on
gemini-2.5-flash-native-audio-latestproduce 0 empty generations out of 9 TRIGGER trials.The 1.0 s pause costs about the same there — TRIGGER 0.56–0.64 s against CONTROL 0.03–0.17 s —
but it is added to a baseline an order of magnitude lower than 3.1's 1.14–1.39 s, and it never
empties a generation. The client is not what differs.
What this report is not. It is not a request to raise
silenceDurationMs: we are aware thevalue is capped at 2000 ms, and that committing a turn after a short silence has already been
described as expected behaviour
(forum 172306). This report is
about what happens after that commit: a turn closed while input audio is still arriving on the
wire, and — with a thinking level set — a generation billed with zero output tokens while the
caller is waiting.
Actual vs expected behavior
gemini-3.1-flash-live-previewturnComplete0.13–0.50 s before the last audio chunk: 21/24 TRIGGER, 0/24 CONTROLusageMetadatawith noresponseTokenCount: 12/15 withthinkingLevelset, 0/9 withoutgemini-2.5-flash-native-audio-latest: 0/9 empty generations, TRIGGER delay 0.24–0.64 sEnvironment
gemini-3.1-flash-live-preview(control:gemini-2.5-flash-native-audio-latest)google-genaiPython SDK 1.73.1,client.aio.live.connect()generativelanguage.googleapis.com, API key auth. Not Vertex AI.s16le, 16 000 Hz, 1 channel, 16-bit;audio/pcm;rate=16000; 20 ms chunks (320 samples / 640 bytes) sent every 20 ms, continuously, silence includedautomaticActivityDetectionblock is sent — server default--system-chars 60000runs are a documented cross-check, not the default)2026-08-18T10:39:54Zand2026-08-18T11:16:11Z; the exact start of each is in the ENVIRONMENT block of that run in the gist outputsetuppayload actually sent, verbatim and complete — this is the whole configuration undertest, nothing is elided:
{ "setup": { "model": "models/gemini-3.1-flash-live-preview", "response_modalities": ["AUDIO"], "thinking_config": {"include_thoughts": false, "thinking_level": "MEDIUM"}, "system_instruction": { "parts": [{"text": "Sei l'assistente telefonico di un servizio di consulenza. Parli solo italiano, con frasi brevi e cortesi. Rispondi sempre a voce a quello che dice il cliente."}], "role": "user" }, "input_audio_transcription": {}, "output_audio_transcription": {}, "realtime_input_config": { "activity_handling": "START_OF_ACTIVITY_INTERRUPTS", "turn_coverage": "TURN_INCLUDES_ONLY_ACTIVITY" } } }Per-trial UTC timestamps for server-side log lookup are in the gist output. Happy to provide
our Google Cloud project number privately through whichever intake form you prefer — it is
deliberately not in this public body.
Reproducer
gemini_live_repro.pyis in this gist: https://gist.github.com/IngLP/124873f0574ada091ab4324e5ff12432 — together withgemini_live_repro_output.txt, the unedited output of all eleven runs cited below. It is self-contained: no audio file isshipped, the two speech pieces are synthesised at run time with the system TTS (
sayon macOS,espeak-ngelsewhere), resampled to 16 kHz mono 16-bit PCM and level-matched, so the speechbytes are byte-identical between the two arms. The only difference between arms is 1.0 s of
PCM silence in the middle:
Both arms end with the same final burst, so the delay measured from the last audio chunk of that
burst is attributable to the pause and to nothing else. Arms alternate inside one session, same
config, same connection.
One run is one Live session of ~50 s and 6 trials.
--repsand--max-sessionsonly bound thespend; no run in this report changes the configuration except where the flag says so, and
RUN 11 in the attached output is the script exactly as published, with no configuration flags at
all.
The audio stream is continuous — including during the pause
This is the first thing that gets asked (e.g.
dotnet-genai#269), so the script measures
it instead of asserting it. The "pause" is not a pause in sending: the caller leg pushes one
20 ms PCM frame every 20 ms for the whole session, and during the pause those frames are digital
zeros. Every trial prints chunks sent vs expected and the mean/max interval between consecutive
sends, for the whole utterance and separately for the pause window. From RUN 11:
Worst inter-chunk interval anywhere in the eleven sessions in the gist: 25.0 ms (RUN 4), against
a 20 ms nominal period; the other ten stay under 24.2 ms. There is no gap in the stream for the
server to interpret as end of input.
Verbatim output
Full output of all eleven runs is in the gist as
gemini_live_repro_output.txt(93 KB, unedited): https://gist.github.com/IngLP/124873f0574ada091ab4324e5ff12432.The load-bearing part of one TRIGGER trial from RUN 11 — the script as published, no flags
except
--reps 3 --max-sessions 1, which only bound the spend (t=is seconds from connect,(+…)is seconds relative to the last audio chunk of the final burst):Read the ordering: the server has committed the turn on the first burst and started answering it,
so the transcription
'Buongiorno.'is delivered att=16.65 s— inside the second burst — thehalf-sentence answer is
interruptedby the rest of the same sentence att=16.21 s, and itsturnCompleteatt=16.29 s, still 0.36 s before the caller's last audio chunk, carriesusage out_tokens=None.The identical trial with no
thinkingConfigat all (RUN 4) shows the same broken segmentationand a non-empty interrupted generation:
Summary tables (as printed by the script)
RUNS 1, 2 and 11 —
gemini-3.1-flash-live-preview, default configuration (one-line systeminstruction,
thinkingLevel: MEDIUM; RUN 11 is the script with no configuration flags at all,only the two that bound the spend):
RUN 8 and RUN 9 —
gemini-2.5-flash-native-audio-latest, same script, same audio bytes, samedefault configuration:
Read honestly, the 2.5 "turn cut mid-speech" column is 4/6 in the control arm too. Those four
are not closed turns: they are the incremental fragment
'Bu'of a transcription still beingstreamed, while every TRIGGER case is the complete
'Buongiorno.'of a committed turn. On 2.5 thepause costs ~0.45 s and never an empty generation; on 3.1 the same column is 0/9 control against
9/9 trigger in the same default configuration, and 0/24 against 24/24 over all configurations.
It is not the size of the system instruction — it is the thinking level
The obvious objection to any report like this is "it is your configuration, not the model". So the
same script was run over the 2×2 of system-instruction size and thinking level, one to three Live
sessions per cell, 3 TRIGGER trials per session:
thinkingConfigthinkingLevel: MEDIUMthinkingLevel: MEDIUMThe broken segmentation and the delay are the same in all four cells — the size of the system
instruction changes nothing, and the delay is if anything largest in the leanest cell. Only effect
3, the zero-token generation, tracks the thinking level: 12/15 when a
thinkingLevelis requested,0/9 when the field is absent. In every control arm of all four cells the turn is never cut: 0/24.
One precision, because the API has no "thinking off": not sent means no
thinkingConfigfield inthe
setupmessage, so whatever the server's default is applies. The claim is therefore "anexplicit
thinkingLevelis what accompanies the empty generation", not "thinking causes it".Scope and limits of the claim
closed while the caller is still speaking (24/24 TRIGGER trials, 0/24 CONTROL), and the
transcription of the final burst is slower than every control trial of the same session (24/24).
thinkingLeveland 0/9 without. It isreproducible in the minimal configuration — RUNS 1, 2 and 11 are 8/9 — but it is not
configuration-independent, and this report does not claim it is.
campaign with the same trigger (23 trials, two bursts separated by 1.0 s, same audio path)
measured the final-burst transcription at 2.46–7.11 s with a median of 3.45 s, and 11 of
those 23 above 5.8 s; in that campaign an empty generation accompanied 20 of the 27 turns
whose delay was ≥ 2 s and 0 of the 45 below 2 s. In the runs attached here the same trigger
produced 1.50–2.08 s. We are not claiming the large numbers are the norm — only that the
mechanism is deterministic and the delay varies with load.
readable: every one of the 24 TRIGGER trials is slower than every CONTROL trial of the same
session, and the trials are interleaved inside one connection, so arm and moment cannot be
confounded.
Related issues
Same underlying VAD segmentation, different symptom — none of them reports the empty generation
or the delay of the final burst's transcription:
silence_duration_msnot honoured on 3.1 (reproduced by triage 2026-06-11)[speech][2.0 s silence][speech]into two turnsWe are filing two other reports on the same model. They may share a root cause with this one,
but we have not demonstrated that: cookbook#1329, and a comment with a
voice_activityrepro on python-genai#1285.
Questions
turnCompleteemitted while input audio for that turn is still being received on thesocket the intended behaviour of the default VAD?
responseTokenCountan expected outcome for a boundary turnthat gets interrupted, and is there a client-side signal that distinguishes it from a
generation that is still coming? Why does it appear only when
thinkingLevelis set?gemini-3.1-flash-live-previewshort of disabling automatic activity detection entirely?