Skip to content
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions crates/tama-cli/src/commands/model/create.rs
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ pub(super) async fn cmd_create(
model: Some(model_id_arg.to_string()),
quant: quant_name.clone(),
mmproj: None,
mtp_model: None,
port: None,
health_check: None,
enabled: true,
Expand Down
6 changes: 6 additions & 0 deletions crates/tama-cli/src/commands/model/pull.rs
Original file line number Diff line number Diff line change
Expand Up @@ -350,6 +350,7 @@ pub(crate) fn cmd_scan(config: &Config) -> Result<()> {
enabled: true,
selected_quant: None,
selected_mmproj: None,
selected_mtp_model: None,
context_length: None,
gpu_layers: None,
port: None,
Expand Down Expand Up @@ -510,6 +511,7 @@ mod tests {
enabled: true,
selected_quant: None,
selected_mmproj: None,
selected_mtp_model: None,
context_length: None,
gpu_layers: None,
port: None,
Expand Down Expand Up @@ -573,6 +575,7 @@ mod tests {
enabled: true,
selected_quant: None,
selected_mmproj: None,
selected_mtp_model: None,
context_length: None,
gpu_layers: None,
port: None,
Expand Down Expand Up @@ -628,6 +631,7 @@ mod tests {
enabled: true,
selected_quant: None,
selected_mmproj: None,
selected_mtp_model: None,
context_length: None,
gpu_layers: None,
port: None,
Expand Down Expand Up @@ -675,6 +679,7 @@ mod tests {
enabled: true,
selected_quant: None,
selected_mmproj: None,
selected_mtp_model: None,
context_length: None,
gpu_layers: None,
port: None,
Expand Down Expand Up @@ -714,6 +719,7 @@ mod tests {
enabled: true,
selected_quant: None,
selected_mmproj: None,
selected_mtp_model: None,
context_length: None,
gpu_layers: None,
port: None,
Expand Down
1 change: 1 addition & 0 deletions crates/tama-cli/src/handlers/server/add.rs
Original file line number Diff line number Diff line change
Expand Up @@ -145,6 +145,7 @@ pub async fn cmd_server_add(
model: extracted.model.clone(),
quant: quant_name,
mmproj: None,
mtp_model: None,
port: extracted.port,
health_check: None,
enabled: true,
Expand Down
1 change: 1 addition & 0 deletions crates/tama-cli/tests/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -256,6 +256,7 @@ async fn test_cmd_server_edit_valid_profile_succeeds() {
model: None,
quant: None,
mmproj: None,
mtp_model: None,
port: None,
health_check: None,
enabled: true,
Expand Down
43 changes: 43 additions & 0 deletions crates/tama-core/src/config/resolve/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -303,6 +303,49 @@ impl Config {
}
}

// Inject --spec-draft-model from model card, only if:
// 1. mtp_model is set
// 2. The referenced quant has kind = Mtp
// 3. draft-mtp is in spec_decoding.spec_types (user enabled it)
// No backend gate — mirrors --mmproj; silently ignored by non-llama.cpp
// backends if they don't recognise the flag.
if let (Some(ref model_id), Some(ref mtp_name)) = (&server.model, &server.mtp_model) {
let has_draft_mtp = server
.spec_decoding
.spec_types
.iter()
.any(|t| t == "draft-mtp");
if has_draft_mtp {
if let Some(mtp_entry) = server.quants.get(mtp_name.as_str()) {
if mtp_entry.kind == crate::config::QuantKind::Mtp {
let models_dir = self.models_dir()?;
let mtp_path = repo_path(&models_dir, model_id).join(&mtp_entry.file);
let already_has_draft = grouped.iter().any(|e| {
matches!(crate::config::flag_name(e), Some("--spec-draft-model"))
});
if !already_has_draft {
let path_str = mtp_path.to_string_lossy();
let quoted = crate::config::quote_value(&path_str);
grouped.push(format!("--spec-draft-model {}", quoted));
}
} else {
tracing::warn!(
"mtp_model '{}' for model '{}' has kind={:?}, expected Mtp",
mtp_name,
model_id,
mtp_entry.kind
);
}
} else {
tracing::warn!(
"mtp_model '{}' not found in ModelConfig for model '{}'",
mtp_name,
model_id
);
}
}
}
Comment on lines +306 to +347

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.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Guard --spec-draft-model injection by backend capability.

This block injects a llama.cpp-specific flag before backend gating. On non-llama backends, it can still resolve paths via self.models_dir()? and fail arg construction (or pass unsupported flags), which is a startup-risk path.

Suggested fix
-        // Inject --spec-draft-model from model card, only if:
+        let is_llama_cpp_backend = backend_is_llama_cpp(&server.backend);
+
+        // Inject --spec-draft-model from model card, only if:
         // 1. mtp_model is set
         // 2. The referenced quant has kind = Mtp
         // 3. draft-mtp is in spec_decoding.spec_types (user enabled it)
-        // No backend gate — mirrors --mmproj; silently ignored by non-llama.cpp
-        // backends if they don't recognise the flag.
-        if let (Some(ref model_id), Some(ref mtp_name)) = (&server.model, &server.mtp_model) {
+        // 4. backend is llama.cpp-compatible
+        if is_llama_cpp_backend
+            && let (Some(ref model_id), Some(ref mtp_name)) = (&server.model, &server.mtp_model)
+        {
             let has_draft_mtp = server
                 .spec_decoding
                 .spec_types
@@
-        let is_llama_cpp_backend = backend_is_llama_cpp(&server.backend);
+        // already computed above
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@crates/tama-core/src/config/resolve/mod.rs` around lines 306 - 347, The code
injects the llama.cpp-only "--spec-draft-model" flag without checking backend
capability; change the block that uses server.model and server.mtp_model so it
first checks the backend supports this flag (e.g. call a capability check like
self.backend.supports_spec_draft_model() or add a method
supports_spec_draft_model() and use it) and only then call self.models_dir(),
repo_path(...) and push the formatted "--spec-draft-model" into grouped; ensure
the existing checks (mtp kind == QuantKind::Mtp, existence in server.quants, and
duplicate flag detection via crate::config::flag_name) remain unchanged but are
nested under the new backend-capability guard so non-llama backends never
compute paths or inject the flag.


// Inject -c (context length) only if not already present.
let ctx = ctx_override.or(server.context_length).or_else(|| {
server
Expand Down
Loading
Loading