[Fix] DP attention: correct the decode->extend prefix off-by-one (#37505)
This commit is contained in:
@@ -2886,10 +2886,18 @@ class ScheduleBatch(ScheduleBatchDisaggregationDecodeMixin):
|
||||
self.forward_mode = ForwardMode.MIXED
|
||||
running_bs = running_batch.batch_size()
|
||||
|
||||
for req in running_batch.reqs:
|
||||
# Same invariant as convert_decode_to_extend: the caller ran
|
||||
# prepare_for_decode, so a tail's prefix is its row length - 1.
|
||||
if self.spec_algorithm.is_none():
|
||||
running_prefix_lens = [s - 1 for s in running_batch.seq_lens_cpu.tolist()]
|
||||
else:
|
||||
# Spec rows sit at the committed base; seq_lens is rebuilt below.
|
||||
running_prefix_lens = [r.seqlen - 1 for r in running_batch.reqs]
|
||||
for req, prefix_len in zip(
|
||||
running_batch.reqs, running_prefix_lens, strict=True
|
||||
):
|
||||
req._refresh_fill_ids()
|
||||
full_len = len(req.full_untruncated_fill_ids)
|
||||
req.set_extend_range(full_len - 1, full_len)
|
||||
req.set_extend_range(prefix_len, prefix_len + 1)
|
||||
|
||||
# Decode tokens of the running portion live in future_map.output_tokens_buf.
|
||||
self.input_ids = None
|
||||
@@ -2937,18 +2945,8 @@ class ScheduleBatch(ScheduleBatchDisaggregationDecodeMixin):
|
||||
merged[-running_bs:] = tail_base + 1
|
||||
self.seq_lens = merged
|
||||
|
||||
# For overlap scheduler, the output_ids has one step delay;
|
||||
# spec tail request state carries no delay in either mode.
|
||||
if self.spec_algorithm.is_none():
|
||||
delta = 0 if self.enable_overlap else -1
|
||||
else:
|
||||
delta = -1
|
||||
|
||||
# NOTE: prefix_indices is what has been cached, but we don't cache each decode step
|
||||
self.prefix_lens = self.prefix_lens + [
|
||||
len(r.origin_input_ids) + len(r.output_ids) + delta
|
||||
for r in running_batch.reqs
|
||||
]
|
||||
self.prefix_lens = self.prefix_lens + running_prefix_lens
|
||||
self.extend_lens = self.extend_lens + [1] * running_bs
|
||||
self.extend_num_tokens = self.extend_num_tokens + running_bs
|
||||
# TODO (lianmin): Revisit this. It should be seq_len - 1
|
||||
@@ -2971,16 +2969,17 @@ class ScheduleBatch(ScheduleBatchDisaggregationDecodeMixin):
|
||||
# Also stale residue; None keeps the prefill result path from
|
||||
# re-reporting old prefill stats for what is decode work.
|
||||
self.prefill_stats = None
|
||||
for req in self.reqs:
|
||||
# A 1-token extend's position is arange(prefix, prefix + 1), so prefix
|
||||
# must be seq_len - 1; output_ids trails the row by one or zero and
|
||||
# cannot stand in for it. Rows past bs are a beam tail, not requests.
|
||||
seq_lens = self.seq_lens_cpu[:bs].tolist()
|
||||
for req, seq_len in zip(self.reqs, seq_lens, strict=True):
|
||||
req._refresh_fill_ids()
|
||||
full_len = len(req.full_untruncated_fill_ids)
|
||||
req.set_extend_range(full_len - 1, full_len)
|
||||
# end runs one past full_untruncated_fill_ids while output_ids
|
||||
# trails; safe only while decoding_reqs suppresses cache_unfinished_req.
|
||||
req.set_extend_range(seq_len - 1, seq_len)
|
||||
|
||||
# Same one-step output_ids delay handling as mix_with_running.
|
||||
delta = 0 if self.enable_overlap else -1
|
||||
self.prefix_lens = [
|
||||
len(r.origin_input_ids) + len(r.output_ids) + delta for r in self.reqs
|
||||
]
|
||||
self.prefix_lens = [seq_len - 1 for seq_len in seq_lens]
|
||||
self.extend_lens = [1] * bs
|
||||
self.extend_num_tokens = bs
|
||||
self.extend_logprob_start_lens = [0] * bs
|
||||
|
||||
@@ -309,6 +309,10 @@ def _local_prefill_cuda_graph_vote(
|
||||
and not local_batch.return_logprob
|
||||
# Grammar FSMs advance through the decode result path only.
|
||||
and not local_batch.has_grammar
|
||||
# A converted batch takes the prefill result path, which commits beam
|
||||
# requests per-req rather than through the batch decode fold; member
|
||||
# rows also have no req of their own for the reqs-aligned extend lists.
|
||||
and all(r.beam_group is None for r in local_batch.reqs)
|
||||
# Small-bucket BCG replays amplify the a2a EP logits drift (#30898)
|
||||
# into an accuracy loss.
|
||||
and get_moe_a2a_backend().is_none()
|
||||
|
||||
Reference in New Issue
Block a user