Run SmolVLM on Intel CPUs with OpenVINO in 3 Steps
TL;DR
Hugging Face demonstrates that the SmolVLM vision‑language model can be deployed on any Intel CPU in three simple steps—conversion to OpenVINO IR, optional INT8 quantization, and inference—delivering up to a 12× reduction in time‑to‑first‑token and a 65× increase in decoding throughput compared with the original PyTorch version.
1. Deploy the Model with Optimum‑Intel
Takeaway: Installing optimum-intel[openvino] and transformers provides a unified CLI and Python API that automatically handles OpenVINO export and runtime execution.
pip install optimum-intel[openvino] transformers==4.52.*
The optimum package abstracts away the low‑level OpenVINO details, letting you focus on model conversion and quantization.
2. Step‑by‑Step Guide
2.1 Convert to OpenVINO IR
Takeaway: The model must be converted to OpenVINO’s Intermediate Representation (IR) before it can be quantized or run on Intel hardware.
- CLI conversion
optimum-cli export openvino -m HuggingFaceTB/SmolVLM2-256M-Video-Instruct smolvlm_ov/ - Python on‑the‑fly conversion
from optimum.intel import OVModelForVisualCausalLM model_id = "HuggingFaceTB/SmolVLM2-256M-Video-Instruct" model = OVModelForVisualCausalLM.from_pretrained(model_id) model.save_pretrained("smolvlm_ov")
Both methods produce the same OpenVINO IR files (.xml and .bin).
2.2 Quantization Options
Takeaway: Post‑training quantization reduces model size and latency; weight‑only quantization (WOQ) is a low‑risk first step, while static quantization further speeds up the vision encoder at the cost of a small accuracy trade‑off.
Option 1 – Weight‑Only Quantization (WOQ)
- Quantizes only the weights to INT8, leaving activations in FP32.
- Minimal accuracy impact; modest speed gains.
- Since OpenVINO 2024.3, runtime activation quantization is automatically applied when weights are INT8, yielding additional speed.
from optimum.intel import OVModelForVisualCausalLM, OVWeightQuantizationConfig
q_config = OVWeightQuantizationConfig(bits=8)
q_model = OVModelForVisualCausalLM.from_pretrained(model_id, quantization_config=q_config)
q_model.save_pretrained("smolvlm_int8")
Or via CLI:
optimum-cli export openvino -m HuggingFaceTB/SmolVLM2-256M-Video-Instruct \
--weight-format int8 smolvlm_int8/
Option 2 – Static Quantization (Mixed)
- Quantizes both weights and activations after a calibration run on a representative dataset (e.g., 50 samples from the contextual dataset).
- Applies static INT8 to the vision encoder while keeping the language model weights at WOQ precision.
- Provides the greatest latency reduction for multi‑image or short‑answer scenarios.
from optimum.intel import (
OVModelForVisualCausalLM,
OVPipelineQuantizationConfig,
OVQuantizationConfig,
OVWeightQuantizationConfig,
)
q_config = OVPipelineQuantizationConfig(
quantization_configs={
"lm_model": OVWeightQuantizationConfig(bits=8),
"text_embeddings_model": OVWeightQuantizationConfig(bits=8),
"vision_embeddings_model": OVQuantizationConfig(bits=8),
},
dataset=dataset,
num_samples=num_samples,
)
q_model = OVModelForVisualCausalLM.from_pretrained(model_id, quantization_config=q_config)
q_model.save_pretrained("smolvlm_static_int8")
2.3 Run Inference
Takeaway: After conversion (and optional quantization), inference is a single generate call; adding device="gpu" enables Intel GPU acceleration when available.
generated_ids = q_model.generate(**inputs, max_new_tokens=100)
generated_texts = processor.batch_decode(generated_ids, skip_special_tokens=True)
print(generated_texts[0])
For GPU:
model = OVModelForVisualCausalLM.from_pretrained(model_id, device="gpu")
A public Hugging Face Space lets you experiment with the original, WOQ, and mixed‑quantized models on a 4th‑Gen Intel Xeon (Sapphire Rapids) system.
3. Performance Evaluation
Takeaway: OpenVINO conversion alone cuts the time‑to‑first‑token (TTFT) from 5.15 s to 0.42 s (≈12× faster) and raises decoding throughput from 0.72 tokens / s to 47 tokens / s (≈65×). Adding 8‑bit WOQ further reduces TTFT to 0.247 s and boosts throughput to 63.9 tokens / s.
| Configuration | TTFT (s) | TPOT (s) | End‑to‑End Latency (s) | Throughput (tokens/s) |
|---|---|---|---|---|
| PyTorch | 5.150 | 1.385 | 25.927 | 0.722 |
| OpenVINO | 0.420 | 0.021 | 0.738 | 47.237 |
| OpenVINO 8‑bit WOQ | 0.247 | 0.016 | 0.482 | 63.928 |
The benchmark used a single image input on an Intel Core Ultra 7 265K (20 threads, 64 GB DDR5) running Ubuntu 24.10 with OpenVINO 2025.2.0.
Platform configuration (excerpt): Intel Core Ultra 7 265K, 20 threads, 64 GB DDR5 @ 6400 MHz, OpenVINO 2025.2.0, optimum‑intel 1.25.2, transformers 4.53.3.
4. Resources
- Notebook: https://github.com/huggingface/optimum-intel/blob/main/notebooks/openvino/vision_language_quantization.ipynb
- Interactive Space: https://huggingface.co/spaces/echarlaix/vision-langage-openvino
- Webinar recording: https://web.cvent.com/event/d550a2a7-04f2-4a28-b641-3af228e318ca/regProcessStep1?utm_campaign=speakers4&utm_medium=organic&utm_source=Community
- Optimum‑Intel OpenVINO docs: https://huggingface.co/docs/optimum-intel/en/openvino/inference
Disclaimer: Performance varies by configuration and workload. Results reflect the hardware and software versions listed above and may not represent all future updates.