Skip to content

Cache visual features in the VLM eval decode loop - #166

Open
camilobrownpinilla wants to merge 4 commits into
refactor/vlm-modalitystrategyfrom
feat/image-encode-cache
Open

Cache visual features in the VLM eval decode loop#166
camilobrownpinilla wants to merge 4 commits into
refactor/vlm-modalitystrategyfrom
feat/image-encode-cache

Conversation

@camilobrownpinilla

Copy link
Copy Markdown
Collaborator

Summary

Encodes frames once per request via model.encode_visual and reuses the projected embeds each step instead of re-running the vision tower.

Testing

  • uv run ruff check kempnerforge/ tests/ passes
  • uv run ruff format --check kempnerforge/ tests/ scripts/ passes
  • uv run pyright kempnerforge/ passes (0 errors)
  • uv run pytest tests/unit/ -v --timeout=60 passes

Closes #126

Encode the clip once per request via model.encode_visual and reuse the projected embeds each step instead of re-running the vision tower.
Pass only the cache to forward (never both), skip the vision tower when
max_new_tokens is 0, drop finished rows from the batch, and write tokens
into a preallocated buffer. Tests now assert the cache reaches forward
and pin the mock to the real forward signature.

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR optimizes the VLM eval adapter’s autoregressive decode loop by encoding visual inputs once per request (via model.encode_visual) and reusing the projected visual embeddings across decode steps, eliminating redundant vision-tower work during generation.

Changes:

  • Cache projected visual embeddings once per batch/request and pass them through the decode loop via visual_embeds instead of re-encoding per step.
  • Refactor the decode loop to use a preallocated token buffer and to drop finished rows from subsequent forwards (including compacting frame_mask and visual_embeds).
  • Add focused unit tests to pin: single visual-encode per request, correct forwarding of cached embeds, signature alignment with VLMWrapper.forward, and correct behavior under batch compaction.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated no comments.

File Description
examples/vlm-evaluation/adapter.py Encodes visuals once and reuses cached embeddings during decoding; adds token buffer + active-row compaction in the batched decode loop.
examples/vlm-evaluation/tests/unit/test_adapter.py Expands decode-loop tests to assert visual caching behavior, forbid pixel+cache dual passing, pin mock/real forward signature parity, and validate compaction correctness.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

VLM inference: encode the image once per request instead of per decode step

2 participants