rustdesk/rustdesk · error
Key mismatch
Error message
Key mismatch
What it means
The rendezvous server returned Failure::LICENSE_MISMATCH in the PunchHoleResponse, meaning the client's configured public key does not match the key the (pro) server expects. The client bails with 'Key mismatch'.
Source
Thrown at src/client.rs:955
crate::get_next_nonkeyexchange_msg(&mut socket, Some(timeout_ms)).await
else {
break;
};
match msg_in.union {
Some(rendezvous_message::Union::PunchHoleResponse(ph)) => {
if ph.socket_addr.is_empty() {
if !ph.other_failure.is_empty() {
bail!(ph.other_failure);
}
match ph.failure.enum_value() {
Ok(punch_hole_response::Failure::ID_NOT_EXIST) => {
bail!("ID does not exist");
}
Ok(punch_hole_response::Failure::OFFLINE) => {
bail!("Remote desktop is offline");
}
Ok(punch_hole_response::Failure::LICENSE_MISMATCH) => {
bail!("Key mismatch");
}
Ok(punch_hole_response::Failure::LICENSE_OVERUSE) => {
bail!("Key overuse");
}
_ => bail!("other punch hole failure"),
}
} else {
peer_nat_type = ph.nat_type();
is_local = ph.is_local();
signed_id_pk = ph.pk.into();
relay_server = ph.relay_server;
peer_addr = AddrMangle::decode(&ph.socket_addr);
feedback = ph.feedback;
webrtc_sdp_answer = ph.webrtc_sdp_answer;
let s = udp.0.take();
if udp_nat_port > 0 && ph.is_udp && s.is_some() {
if let Some(s) = s {
allow_err!(s.connect(peer_addr).await);View on GitHub (pinned to 91c9fccbb0)
Solutions
- Update the client's server 'key' setting to the current key exported from the pro server
- Re-deploy/re-import the server config (QR or config string) on clients after any server license change
- Verify the server's own license/key files are consistent and restarted cleanly
Example fix
// before "key": "OLD_SERVER_KEY" // after "key": "CURRENT_PRO_SERVER_KEY"
Defensive patterns
Strategy: validation
Validate before calling
// Ensure the client's configured key matches the pro server's expected key before connecting
if client_key != expected_server_key { eprintln!("Key mismatch: update client server key"); return; } Try / catch
match connect() {
Err(e) if e.to_string() == "Key mismatch" => {
prompt_admin_to_refresh_server_config();
}
r => handle(r),
} Prevention
- Re-deploy server config (QR/config string) to all clients whenever the server key/license changes
- Automate key distribution via MDM/config management instead of manual entry
- Keep one canonical source for the server public key
When it happens
Trigger: PunchHoleResponse with empty socket_addr and ph.failure == LICENSE_MISMATCH; the client's 'key' option doesn't match the server's license-bound public key.
Common situations: Self-hosted pro server whose license key differs from the key distributed in client configs; server license re-issued without updating clients; mixing public-server clients with a private pro server.
Related errors
AI-assisted analysis of rustdesk/rustdesk@91c9fccbb0 (2026-09-10).
Data as JSON: /api/errors/fe3625b489d68423.
Report an issue: GitHub.