license: cc-by-nc-4.0
base_model:
- jinaai/jina-embeddings-v5-omni-nano
tags:
- axera
- ax650
- embeddings
- retrieval
- multimodal
- image
- audio
- video
jina-embeddings-v5-omni-nano-retrieval on AXERA NPU
This repository packages the retrieval-task AX650 deployment of jinaai/jina-embeddings-v5-omni-nano.
The package contains compiled AX650 runtime artifacts and runs with axllm serve on AX650 using the expected bidirectional text-embedding behavior.
It was rebuilt with the correct text RoPE base and passes the packaged text, image, audio, and frame-based video precision checks.
Current Validation Status
- Target platform: AX650 / NPU3
- Current service model id:
AXERA-TECH/jina-embeddings-v5-omni-nano-retrieval-AX650-P128-CTX2047 - Vision encoder static shape:
256x256 - Vision soft tokens per frame:
64 - Audio encoder static profiles:
- short audio:
8s,16kHz, mono,800mel frames,200soft tokens - long audio:
30s,16kHz, mono,3000mel frames,750soft tokens
- short audio:
- Audio request sequence length with the packaged
queryprompt:8saudio:200soft tokens, about220total LLM prefill tokens30saudio:750soft tokens, about772total LLM prefill tokens
- Current LLM prefill build:
prefill_len = 128- warm-prefill groups =
128 / 256 / 384 / 512 / 640 / 768 / 896 - effective
prefill_max_token_num = 1024
Board cold-start measurements from this package with both 8s and 30s audio profiles loaded:
| Item | Value |
|---|---|
/v1/models ready time |
25 s |
| CMM used before startup | 275004 KB |
| CMM used after startup | 2455548 KB |
| Cold-start CMM consumption | 2180544 KB |
| Process VmRSS after startup | 2011016 KB |
| Process PSS after startup | 2010169 KB |
| Process anonymous memory | 2006272 KB |
| Process VmSize after startup | 4191272 KB |
CMM means AXERA contiguous multimedia memory. RSS means resident set size in Linux process memory. PSS means proportional set size.
Functional Status
This package can:
- start
./bin/axllm serve .on AX650 - expose
/v1/modelsand/v1/embeddings - run text, image, audio, and frame-based video embedding requests without depending on Hugging Face
safetensorsat runtime
This package is retrieval-only. The upstream model family defines other task adapters, but this AX650 release contains the retrieval route and its cached retrieval reference cases only.
The packaged runtime files are:
llama_p128_l0_together.axmodel...llama_p128_l11_together.axmodelllama_post.axmodeljina_v5_omni_nano_vision_256x256.axmodeljina_v5_omni_nano_audio_8s.axmodeljina_v5_omni_nano_audio_30s.axmodelmodel.embed_tokens.weight.bfloat16.binjina_v5_omni_tokenizer.txtjina_v5_omni_tokenizer/bin/axllm
Performance
This package exposes /v1/embeddings rather than token streaming, so chat-style TTFT is not the right primary metric.
For an embedding model on AX650, the useful execution metric is:
- text:
LLM prefillonly - image / video:
encoder + LLM prefill - audio:
audio encoder + LLM prefill
There is no decode stage in the normal embedding path, so a TTFT-style number mostly collapses into prefill completion plus service overhead.
If you measure only the HTTP response time of axllm serve, lightweight text and image requests can look artificially similar because fixed server overhead dominates them.
All values below were re-measured on the validated AX650 / NPU3 board.
Each number is the average of 3 repeated direct-runtime runs after model initialization.
These measurements exclude network overhead and client-side preprocessing outside the packaged runtime path.
| Scenario | Prompt | Input tokens | Encoder avg | LLM prefill avg | Total avg |
|---|---|---|---|---|---|
| Text document | document |
19 text tokens |
- |
68.88 ms |
68.88 ms |
| Text query | query |
12 text tokens |
- |
61.59 ms |
61.59 ms |
| Image | query |
64 soft tokens, 91 total sequence |
17.24 ms |
65.66 ms |
82.91 ms |
Video (3 frames) |
query |
192 soft tokens, 219 total sequence |
52.49 ms |
148.40 ms |
200.89 ms |
Audio is different on this 3 GB board:
- the packaged
axllm servepath is validated and returns correct audio embeddings - but the current Python direct-benchmark implementation was OOM-killed during this measurement pass
- that failure is a board-side benchmark-method issue in Linux userspace memory, not a proof that the packaged AX650 runtime path cannot run audio embeddings
- because of that, this README does not publish a misleading direct audio split-latency number yet
Current Board Precision
Current board-side axllm serve precision against the packaged Hugging Face reference embeddings is:
| Modality | Case | Output shape | Cosine vs HF |
|---|---|---|---|
| Text | embedding_doc |
[1, 768] |
0.999655 |
| Text | red_planet_query |
[1, 768] |
0.999539 |
| Image | vision_sample |
[1, 768] |
0.993549 |
| Audio | audio_test_chunk0_8s_wav |
[1, 768] |
0.989344 |
| Audio | audio_test_chunk0_30s_wav |
[1, 768] |
0.994962 |
| Video | video_visual_red_panda_openai_mp4 |
[1, 768] |
0.997008 |
Key observations:
- The previous severe service mismatch is fixed.
- The previous
embedding_doc = 0.9604result was traced to an LLM build config issue, not to the OpenAI-compatible service wrapper. jina-embeddings-v5-omni-nanousestext_config.rope_parameters.rope_theta = 1000000.0; the earlierllamabuild path silently fell back to10000.0.- The current LLM AXModels were rebuilt after flattening
rope_thetaintotext_config.rope_thetaforpulsar2 llm_build. - With the corrected RoPE base, all non-audio-short packaged precision cases are in the
0.9935 ~ 0.9997cosine range. - The
8saudio profile is usable but lower than the30sprofile in this P128 build:0.989344cosine for the packagedaudio_test_chunk0_8s_wavcase. The previous5saudio profile produced only about0.94cosine after LLM prefill, so it is not used as a default packaged precision case.
Board Precision Validation Flow
The board-side comparison does not run the original Hugging Face model. The intended flow is:
- Run the original
jinaai/jina-embeddings-v5-omni-nanomodel once on the server for each fixed test case. - Save the resulting HF embedding as
torch_embedding.npyunder the matchingpython/testdata/service_cases/<case>/directory. - Package the same case metadata and assets used by the HF run.
- On AX650, start
axllm serve ., call/v1/embeddings, and compare the returned AXERA embedding with the packagedtorch_embedding.npy.
This guarantees that AX650 validation uses the same inputs as the server-side HF reference, while the board only needs the packaged .axmodel, .bin, tokenizer, assets, and cached reference .npy files.
The board package does not require upstream .safetensors files.
Run the packaged comparison on the board with:
python3 python/compare_openai_api_vs_hf_multimodal.py
The script fails if any packaged case is missing its cached torch_embedding.npy reference.
Conversion Note
If you rebuild the LLM AXModels from the original Hugging Face checkpoint, check the RoPE config before running pulsar2 llm_build.
The upstream nano config stores the text RoPE base as:
"text_config": {
"rope_parameters": {
"rope_theta": 1000000.0
}
}
The current AXERA llama llm_build route does not read text_config.rope_parameters.rope_theta.
It reads the flattened field text_config.rope_theta.
Before compilation, make sure the llm_build_input/config.json contains:
"text_config": {
"rope_theta": 1000000.0
}
The packaged conversion script handles this automatically.
If you prepare llm_build_input/config.json manually, copy the value yourself and confirm the build log prints rope_theta=1000000.0.
If the build silently uses the default 10000.0, the generated LLM AXModels will have noticeably worse embedding precision.
Runtime Compatibility Notes
The following compatibility details are required to reproduce the validated precision:
jina-embeddings-v5-omni-nanouses a bidirectional EuroBERT /LlamaModeltext tower, but the service embedding path was still building a decoder-style causal prefill mask.- The embedding path in
axllmmust use bidirectional masking throughprefill_mask_mode. - The service tokenizer path was also missing the final end-of-text token used by the Python reference route.
- For
Qwen3Omni, the correct end-of-text token id is not the older hard-coded151643; it must be resolved from the loaded tokenizer and is128001for this Jina nano package. - LLM precision depends on the
llamallm_buildpath receiving the flattenedtext_config.rope_thetavalue. The nano text model requires RoPE theta1000000.0, and the corrected package was rebuilt with that value.
With these settings, the service-side outputs match the direct board-side axmodel route.
Packaged Test Cases
The package includes cached Hugging Face reference embeddings under:
python/testdata/service_cases/
Current packaged cases:
embedding_docred_planet_queryvision_sampleaudio_test_chunk0_8s_wavaudio_test_chunk0_30s_wavvideo_visual_red_panda_openai_mp4
All cached reference embeddings use the upstream retrieval route and output shape [1, 768].
The packaged meta.json files define the exact text, prompt name, media asset path, and soft-token count used for both the server-side HF reference and the board-side API request.
Known Limitation
- Re-measure direct audio split latency if a low-memory benchmark implementation is needed; the packaged service audio path is already validated.
- Audio encoder loading is controlled by
filename_audio_encoder_axmodel_shortandfilename_audio_encoder_axmodel_longinconfig.json. If only one field is configured, only that audio profile is loaded; if both are configured, the runtime selects the short profile for short audio and falls back to the long profile for longer audio.