General
The SIP CANCEL Race Condition: Why 200 OK Glare Spawns Zombie Calls and Bleeds Carrier Budgets
calricon / field note
Article Metadata The SIP CANCEL Race Condition: Why 200 OK Glare Spawns Zombie Calls and Bleeds Carrier Budgets Slug sip-cancel-200-ok-race-condition-zombie-calls-telecom-billing Focus Keyword SIP CA
sip-cancel-200-ok-race-condition-zombie-calls-telecom-billingSIP CANCEL 200 OK race condition RFC 5407 zombie calls telecom billingThe SIP CANCEL Race Condition: Why 200 OK Glare Spawns Zombie Calls and Bleeds Carrier Budgets
When telecom engineers and contact center operators conduct monthly carrier billing audits, they routinely stumble upon a bizarre, infuriating anomaly: hundreds of outbound calls logged with identical, multi-hour durations (typically exactly 7,200 seconds / 2 hours), all terminated at the maximum carrier session threshold. When they inspect the audio recordings, they find thirty seconds of human hello followed by 119 minutes of dead air. These phantom charges are not toll fraud or carrier metering bugs; they are the direct consequence of the infamous SIP CANCEL vs. 200 OK race condition documented in RFC 5407. When a caller changes their mind and hangs up at the exact millisecond a callee answers, the outbound CANCEL request and the inbound 200 OK (INVITE) cross paths in the network. If your Session Border Controller (SBC), WebRTC gateway, or custom dialer state machine does not strictly implement the RFC-mandated "ACK-then-BYE" teardown sequence, the caller's interface displays "Call Cancelled" while the carrier's switch considers the call answered and active. The resulting "zombie call" silently bleeds wholesale trunking budgets and consumes vital concurrency channels.
"When a CANCEL and a 200 OK cross paths, failing to ACK and BYE leaves the carrier switch billing an active call for hours. In telecom, microsecond race conditions carry multi-thousand-dollar consequences."
The Microsecond Glare: Anatomy of RFC 5407 Race Condition 3.1.2
To understand why SIP systems fail during simultaneous hangup and answer events, one must understand how the Session Initiation Protocol handles transaction lifecycles under RFC 3261:
- The Initiator Sends INVITE: User Agent Client (Alice) sends an
INVITEto User Agent Server (Bob). Bob's phone rings and returns180 Ringing. - The Caller Aborts: Alice decides not to wait, clicks "End Call", and her client dispatches a
CANCELrequest to terminate the pending INVITE transaction. - The Callee Answers Simultaneously: At that precise millisecond, Bob picks up his handset. Bob's user agent generates a
200 OK(INVITE) response and transmits it back across the SIP proxy network. - The Packet Collision (Glare): The
CANCELrequest and the200 OKresponse pass each other on the wire.
Now, look at the disaster that unfolds across both endpoints:
- On Bob's End: Bob has already sent
200 OK, which formally completes the INVITE server transaction. When Bob receives Alice'sCANCEL, RFC 3261 dictates that a CANCEL cannot terminate an already-answered transaction! Bob's SIP stack correctly responds to the CANCEL with200 OK(meaning "I received your CANCEL, but it had no effect on the completed INVITE") and patiently waits for Alice to establish media. - On Alice's End: Alice's client receives
200 OKfor the INVITE after having already dispatchedCANCEL. In poorly engineered SIP stacks, dialer SDKs, and WebRTC clients, the application state machine throws an uncaught exception (InvalidStateErrororTransactionAlreadyCancelled). The client drops the transaction from memory, cleans up the UI, and never responds to the200 OK.
The Anatomy of a Zombie Call
Because Alice's client crashed or dropped the transaction from its state table, it fails to execute the fundamental rule of SIP session establishment: "Every 200 OK for an INVITE MUST be acknowledged with an ACK, and if the caller wishes to terminate the established dialog, they MUST immediately dispatch a BYE."
When Alice fails to send an ACK and subsequent BYE:
- The Intermediate Carrier Considers the Call Answered: The upstream telecom carrier's billing engine starts ticking the moment it forwards the
200 OK. To the carrier, the call is fully established. - The Callee Hears Dead Air: Bob says "Hello? Hello?" into his handset. Hearing nothing, Bob puts the phone down on his desk without pressing hangup, or a corporate IVR / voicemail box keeps the line held open.
- RTP Media Ports Remain Locked: The media gateway (FreeSWITCH, Asterisk, or Kamailio) reserves UDP ports for audio that never arrives.
- The Session Timer Clock Runs: Without an explicit
BYEpacket from either party, the call remains open until the carrier's default safety timer expires—typically 120 minutes. At international wholesale rates of $0.05 to $0.20 per minute, a single zombie call costs between $6.00 and $24.00.
The Three Hidden Multipliers Draining Enterprise VoIP Budgets
1. Runaway Trunk Concurrency Saturation
Enterprise SIP trunks are billed or capped based on Concurrent Call Capacity (Channels). If your business pays for 100 concurrent channels and your outbound dialer generates thirty zombie calls during a morning campaign, 30% of your total voice capacity is held hostage by ghost calls connected to dead air. Legitimate outbound calls begin failing with 503 Service Unavailable or 486 Busy Here.
2. Distorted Answer-Seizure and ACD Metrics
Contact center operations live by Key Performance Indicators: Answer-Seizure Ratio (ASR), Average Call Duration (ACD), and First Contact Resolution (FCR). Zombie calls artificially inflate Average Call Duration (turning 30-second abandoned calls into 2-hour metrics) while distorting agent utilization analytics, blinding management to systemic dialer inefficiencies.
3. Mobile WebRTC App Handoff Collisions
In modern WebRTC-based enterprise mobile applications, network jitter and Wi-Fi handoffs exacerbate CANCEL glare. When a mobile user clicks "Cancel Call" while walking out of Wi-Fi range, the CANCEL request is delayed in transit. The callee answers, but the mobile app tears down its peer connection without sending a proper signaling teardown, creating an orphaned carrier session on the PSTN bridge.
The Calricon Production Playbook: Eliminating Zombie Sessions
Step 1: Enforce Strict RFC 5407 "ACK-then-BYE" State Machines
Audit your client-side SIP stacks, WebRTC signaling engines, and CPaaS gateways. Ensure your session state machine explicitly handles Section 3.1.2 of RFC 5407:
- When a client issues a
CANCELand subsequently receives a200 OK(INVITE), it must NOT discard the packet. - The client MUST immediately transmit an
ACKto complete the three-way handshake and establish the SIP dialog. - Milliseconds later, the client MUST immediately generate and transmit a
BYErequest withReason: SIP ;cause=200 ;text="Call completed elsewhere / User cancelled". - This clean teardown signals the carrier switch to terminate billing within 150 milliseconds.
Step 2: Deploy RFC 4028 Session Timers with Aggressive Minimums
Never rely on default 2-hour carrier timeout fallbacks. Configure SIP Session Timers (RFC 4028) across your edge Session Border Controllers (Kamailio, OpenSIPS, or FreeSWITCH):
- Mandate Session Timers on all outbound trunks: Configure
Session-Expires: 1800(30 minutes) andMin-SE: 90(90 seconds). - Enable Periodic Session Refreshes: Require either party to send a periodic
UPDATEor re-INVITEevery 90 seconds. If an orphaned endpoint fails to acknowledge the session refresh within 32 seconds, the SBC automatically tears down the session with a forcedBYEto both legs.
Step 3: Implement In-Band RTP Silence Detection
If a zombie call slips through the signaling layer, catch it at the media plane. Enable Real-Time Silence Detection in your media engines (FreeSWITCH mod_dptools:wait_for_silence or Asterisk WaitForSilence). If an answered call exhibits zero bidirectional audio energy (RTP payload silence) for 20 consecutive seconds following answer supervision, trigger an automated event hook that dispatches an immediate BYE and frees the trunk channel.
Step 4: Use Edge B2BUA Normalization
Do not trust end-user mobile devices or third-party CRM softphone integrations to execute perfect SIP state machines. Place a Back-to-Back User Agent (B2BUA) at your network boundary. When the B2BUA receives a CANCEL from a softphone, it intercepts it. If the carrier upstream returns 200 OK (INVITE) before receiving the cancel, the B2BUA automatically generates the ACK and BYE on behalf of the client, completely insulating the carrier leg from client-side state machine bugs.
The Strategic Verdict: Real-Time Telecom Demands Edge-Case Precision
In asynchronous distributed telephony, assuming that network packets arrive in the order they were dispatched is an invitation to financial bleeding. Microsecond race conditions between user intent and network propagation are an inevitable physical reality of real-time communication.
If your enterprise VoIP logs reveal mysterious multi-hour calls ending at carrier timeouts, stop blaming ghost callers. Enforce RFC 5407 ACK-then-BYE compliance, tighten your session timers, and close the door on zombie billing once and for all.