|
|
| (23 intermediate revisions by the same user not shown) |
| Line 1: |
Line 1: |
| {{DISPLAYTITLE:Guide to Decrypting TLS and SRTP Traffic}} | | {{DISPLAYTITLE:TLS and SRTP Decryption}} |
| | [[Category:Configuration]] |
|
| |
|
| '''This guide provides a comprehensive overview of the methods used by VoIPmonitor to decrypt encrypted SIP over TLS and encrypted media (SRTP). It covers the two primary decryption approaches: using a static private key and using the dynamic SSL Key Logger.''' | | '''This guide covers how to decrypt encrypted SIP (TLS) and media (SRTP/DTLS-SRTP) traffic in VoIPmonitor.''' |
|
| |
|
| == Introduction to TLS Decryption == | | = Understanding TLS Decryption = |
| VoIPmonitor can decrypt SIP signaling encrypted with TLS (v1.2 and v1.3 supported) and media encrypted with SRTP. It is essential to understand that not all TLS traffic can be decrypted.
| |
|
| |
|
| '''Important Limitation:''' If the SIP session negotiates a cipher suite using a '''Perfect Forward Secrecy (PFS)''' algorithm, such as '''Diffie-Hellman (DHE/ECDHE)''', decryption using only the server's private key is mathematically impossible. In these cases, you '''must''' use the SSL Key Logger method to capture session-specific keys.
| | VoIPmonitor can decrypt TLS-encrypted SIP signaling and SRTP media. The method you choose depends on your TLS configuration. |
|
| |
|
| === TLS Version and Cipher Suite Impact === | | == Cipher Suite Impact == |
|
| |
|
| The feasibility of private key decryption depends entirely on the TLS version and cipher suite:
| | {| class="wikitable" |
| | ! TLS Version / Cipher !! Private Key Decryption !! SSL Key Logger |
| | |- |
| | | TLS 1.2 with RSA (no DH) || {{Yes}} Works || {{Yes}} Works |
| | |- |
| | | TLS 1.2 with DHE/ECDHE || {{No}} Impossible || {{Yes}} Required |
| | |- |
| | | TLS 1.3 (any cipher) || {{No}} Impossible || {{Yes}} Required |
| | |} |
|
| |
|
| * '''SSL/TLS 1.2 or older WITHOUT DH ciphers (e.g., RSA, AES256-SHA)''': Decryption IS possible using the server's private key. This is Method 1 configuration.
| | {{Warning|1=Modern VoIP services use TLS 1.3 or PFS ciphers. The SSL Key Logger (Method 2) is the '''only viable method''' for most deployments.}} |
|
| |
|
| * '''SSL/TLS 1.3 or any DH-based cipher (EDH, DHE, ECDHE)''': Decryption using the private key is IMPOSSIBLE. You must use the SSL Key Logger (Method 2) to obtain session-specific keys.
| | To check your cipher suite, capture the TLS handshake in Wireshark and look for "DHE" or "ECDHE" in the cipher negotiation. |
|
| |
|
| Modern VoIP services typically use_TLS 1.3 or strong PFS ciphers for security, making the SSL Key Logger the only viable decryption method.
| | == Method Overview == |
|
| |
|
| === Cloud Service Decryption Limitations === | | <kroki lang="mermaid"> |
| | %%{init: {'flowchart': {'nodeSpacing': 15, 'rankSpacing': 30}}}%% |
| | flowchart TD |
| | Q1{Can you control<br>PBX/SBC?} -->|Yes| Q2{Using DHE/ECDHE<br>or TLS 1.3?} |
| | Q1 -->|No - Cloud/Hosted| M4[Method 4: Vendor Tunneling<br>or Method 5: External Key Provider] |
| | Q2 -->|No - RSA only| M1[Method 1: Private Key] |
| | Q2 -->|Yes| M2[Method 2: SSL Key Logger] |
| | M2 -->|Distributed arch| M3[Method 3: Distributed Mode] |
| | </kroki> |
|
| |
|
| When monitoring SIP traffic between phones and cloud-based services (e.g., Cisco Webex Cloud, Microsoft Teams, Zoom Phone):
| | '''Quick Reference:''' |
| | * '''Method 1''' - Private Key: Simple, but only works for non-PFS ciphers |
| | * '''Method 2''' - SSL Key Logger: Universal, works for all ciphers (recommended) |
| | * '''Method 3''' - Distributed Mode: For client-server architecture with <code>packetbuffer_sender=yes</code> |
| | * '''Method 4''' - SBC/PBX Tunneling: Ribbon, AudioCodes, or other vendor solutions |
| | * '''Method 5''' - External Key Provider: Hosted platforms (NetSapiens, etc.) |
| | * '''Method 6''' - HEP Protocol: Alternative when SSL Key Logger isn't feasible |
|
| |
|
| * '''Direct hardware phone to cloud:''' Decryption is generally '''IMPOSSIBLE''' because:
| | == Cloud Service Limitations == |
| ** You do not have the cloud service's private key
| |
| ** Cloud services typically use TLS 1.3 or strong DH ciphers
| |
| ** You cannot inject an SSL keylogger into cloud infrastructure
| |
|
| |
|
| * '''Softphone to cloud:''' Decryption IS possible using the SSL Key Logger (Method 2) on the local machine where the softphone runs, as long as you control that host.
| | {| class="wikitable" |
| | ! Scenario !! Decryption Possible? |
| | |- |
| | | Hardware phone → Cloud (Teams, Webex) || {{No}} Not possible (no access to cloud keys) |
| | |- |
| | | Softphone on controlled host → Cloud || {{Yes}} Use SSL Key Logger on the host |
| | |- |
| | | Phone → Local SBC → Cloud || {{Yes}} Use SBC tunneling (Method 4) |
| | |} |
|
| |
|
| * '''Phone to local SBC to cloud:''' Use SBC-specific monitoring features (e.g., Ribbon SBC Monitoring Profile) to extract decrypted SIP signaling before it leaves your network.
| | = Method 1: Private Key Decryption = |
|
| |
|
| Decrypted SIP packets are stored in PCAP files as virtual UDP packets for consistent analysis within the GUI.
| | Works only for TLS 1.2 or older '''without''' Diffie-Hellman ciphers. |
|
| |
|
| == Method 1: Private Key Decryption == | | == Configuration == |
| This is the simpler method and works well for environments where you control the TLS cipher suites and can disable PFS.
| |
|
| |
|
| === Configuration === | | <syntaxhighlight lang="ini"> |
| To enable this method, add the following to `/etc/voipmonitor.conf`:
| |
| <pre>
| |
| # /etc/voipmonitor.conf | | # /etc/voipmonitor.conf |
|
| |
| # Enable the SSL decryption module
| |
| ssl = yes | | ssl = yes |
| | ssl_ipport = 10.0.0.1:5061 /etc/pki/tls/private/server.key |
| | </syntaxhighlight> |
|
| |
|
| # Provide the server's IP, TLS port, and the absolute path to its private key.
| | '''Multiple servers:''' |
| # The key must be in PEM format. You can have multiple lines for multiple servers.
| | <syntaxhighlight lang="ini"> |
| ssl_ipport = 10.0.0.1 : 5061 /etc/pki/tls/private/my_server.key | | ssl_ipport = 10.0.0.1:5061 /path/to/server1.key |
| </pre> | | ssl_ipport = 10.0.0.2:5061 /path/to/server2.key |
| | | </syntaxhighlight> |
| == Troubleshooting TLS Decryption Issues ==
| |
| | |
| If you have TLS/SRTP traffic that is not being decrypted in the VoIPmonitor GUI, follow this systematic approach to identify and resolve the issue.
| |
|
| |
|
| === Step 1: Verify Packet Capture (Using sip:history) === | | == GUI Configuration == |
|
| |
|
| Before adjusting configuration, first confirm that the sensor is actually capturing the problematic TLS leg of the call.
| | Navigate to '''Settings > Sensors > wrench icon''' and search for <code>ssl_</code>: |
| | * <code>ssl = yes</code> |
| | * <code>ssl_ipport = IP:PORT /path/to/key</code> |
|
| |
|
| '''Procedure:'''
| | = Method 2: SSL Key Logger (Recommended) = |
|
| |
|
| 1. In the VoIPmonitor GUI, navigate to the CDR detail view for a call where TLS should be decrypted
| | Works for '''all''' cipher suites including PFS. Captures session keys from your PBX/SBC using <code>LD_PRELOAD</code>. |
| 2. Click <code>sip:history (+)</code> to view the SIP packet flow
| |
| 3. Look for the missing TLS leg:
| |
| * If packets appear in the history but are shown as encrypted (TLS) rather than decrypted SIP, proceed to Step 2
| |
| * If packets are NOT in the history at all, this is a packet capture issue, not a decryption issue
| |
|
| |
|
| '''What this tells you:'''
| | == Step 1: Compile the Library == |
| * <code>sip:history (+)</code> shows all captured SIP packets for the call
| |
| * Present but encrypted = packets captured, decryption failed
| |
| * Not present at all = packets not captured (check interface configuration, capture rules)
| |
| | |
| === Step 2: Capture Packet Trace for Support Analysis ===
| |
| | |
| If packets are captured but not decrypted, gather the following packet captures for analysis:
| |
| | |
| '''Critical: What to Capture in the Packet Trace'''
| |
| | |
| Your packet capture from the VoIPmonitor probe MUST include three components:
| |
| | |
| 1. **TLS Traffic from Capture Interface**
| |
| * Capture the encrypted SIP packets from the main capture interface (e.g., <code>eno1</code>, <code>eth0</code>)
| |
| * Filter for the problematic SIP server IP address and TLS port (usually 5061)
| |
| | |
| 2. **Keylogger Traffic from Loopback Interface**
| |
| * Capture the UDP packets containing session keys from the loopback interface (<code>lo</code>)
| |
| * These are the packets sent by the SSL Key Logger to VoIPmonitor
| |
| * Filter for <code>ssl_sessionkey_udp_port</code> (default: 1234)
| |
| | |
| 3. **Complete TLS Handshake**
| |
| * The packet trace must include the full TLS handshake:
| |
| * Client Hello (first packet from client to server)
| |
| * Server Hello (first server response)
| |
| * These packets are essential for analyzing the encryption parameters and cipher negotiation
| |
| | |
| '''Packet Capture Command Example:'''
| |
|
| |
|
| <syntaxhighlight lang="bash"> | | <syntaxhighlight lang="bash"> |
| # Capture TLS traffic and keylogger simultaneously on a production probe | | # Install prerequisites |
| # Replace interfaces, IPs, and ports with your actual values
| | apt-get install libssl-dev build-essential git # Debian/Ubuntu |
| | | yum install openssl-devel make gcc git # RHEL/CentOS |
| # Run this command on the VoIPmonitor sensor machine
| |
| tcpdump -i eno1,lo \
| |
| -w /tmp/tls_debug_capture.pcap \ | |
| -s 0 \
| |
| "((host 192.168.1.50 and port 5061) or (port 1234))"
| |
| </syntaxhighlight>
| |
|
| |
|
| '''Explanation:'''
| | # Compile |
| * <code>-i eno1,lo</code> - Capture from both the network interface AND loopback
| |
| * <code>-s 0</code> - Capture full packets (not truncated)
| |
| * <code>host 192.168.1.50 and port 5061</code> - TLS traffic to/from the PBX
| |
| * <code>port 1234</code> - Session key logger traffic (must match <code>ssl_sessionkey_udp_port</code>)
| |
| | |
| === Step 3: Submit to Support Team ===
| |
| | |
| When providing the packet capture to the VoIPmonitor support team, include the following information:
| |
| | |
| * CDR ID or call time of the problematic call
| |
| * VoIPmonitor version: <code>voipmonitor --version</code>
| |
| * Output from <code>sip:history (+)</code> for the call (screenshot or text)
| |
| * The packet capture file from Step 2
| |
| * Configuration snippet from <code>/etc/voipmonitor.conf</code> showing ssl*, interface, and packetbuffer_sender settings
| |
| | |
| The support team will analyze:
| |
| * Whether session keys are present in the keylogger traffic
| |
| * Whether the keys match the TLS handshake parameters
| |
| * Whether the cipher suite is supported for decryption
| |
| * Any timing issues between key arrival and encrypted traffic
| |
| | |
| == Common Configuration Issues ==
| |
| | |
| Many TLS decryption failures are caused by configuration errors rather than lack of packet capture. Check these common issues first:
| |
| | |
| === Issue 1: Session Keys Not Being Captured (localhost/127.0.0.1) ===
| |
| | |
| '''Symptom:''' The SSL Key Logger appears to be running (you see "SSL KEYLOG: OK" messages), but TLS packets are not being decrypted.
| |
| | |
| '''Root Cause:''' When sending session keys via UDP to `127.0.0.1` or `localhost`, the VoIPmonitor sensor can only capture these packets if the loopback interface (`lo`) is included in the `interface` directive.
| |
| | |
| '''Solution:''' Add `lo` to the interface configuration in `/etc/voipmonitor.conf`:
| |
| | |
| <pre>
| |
| # Include the loopback interface to capture UDP packets sent to 127.0.0.1 | |
| interface = eth0,lo
| |
| </pre>
| |
| | |
| After making this change:
| |
| 1. Restart VoIPmonitor: `systemctl restart voipmonitor`
| |
| 2. Restart your TLS application (e.g., Asterisk, Kamailio) to generate a new SSL handshake with fresh session keys
| |
| | |
| '''Verification:''' The sensor should now see the UDP session key packets and decryption should work.
| |
| | |
| === Issue 2: ssl_ipport Syntax Error (Private Key Overrides Key Logger) ===
| |
| | |
| '''Symptom:''' Decryption fails with DHE/ECDHE ciphers even though the SSL Key Logger is configured.
| |
| | |
| '''Root Cause:''' If `ssl_ipport` contains a file path (e.g., `/path/to/private.key`), VoIPmonitor ignores the SSL Key Logger and tries to use Method 1 (Private Key), which fails for Perfect Forward Secrecy ciphers.
| |
| | |
| '''Solution:''' Remove the key file path from `ssl_ipport`:
| |
| | |
| <pre>
| |
| # INCORRECT - this forces Method 1 and ignores the key logger:
| |
| ssl_ipport = 192.168.0.1:5061 /path/to/private.key
| |
| | |
| # CORRECT - IP and port only, enables SSL Key Logger method:
| |
| ssl_ipport = 192.168.0.1:5061
| |
| </pre>
| |
| | |
| === Issue 3: Distributed Mode (packetbuffer_sender=yes) ===
| |
| | |
| '''Symptom:''' Decryption works with `packetbuffer_sender=no` but fails when `packetbuffer_sender=yes` is enabled.
| |
| | |
| '''Root Cause:''' Session keys are being sent to the local client sensor instead of the central server. Client sensors only forward raw packets to the central server; session keys are lost in transit.
| |
| | |
| '''Solution:''' Send session keys directly to the central server's IP address, not localhost or the client sensor:
| |
| | |
| <pre>
| |
| # On the PBX, set SSLKEYLOG_UDP to the central server's IP:
| |
| SSLKEYLOG_UDP='192.168.1.100:1234' # Central server IP and port
| |
| </pre>
| |
| | |
| See the "Method 3: TLS Decryption in Distributed/Client-Server Mode" section below for complete configuration details.
| |
| | |
| == Method 2: SSL Key Logger (Recommended & Universal) ==
| |
| This is the most powerful and recommended method. It works for '''all''' cipher suites, including those with Perfect Forward Secrecy, by dynamically capturing session keys directly from the application's memory.
| |
| | |
| It works by using the `LD_PRELOAD` mechanism to inject a small library (`sslkeylog.so`) into your SIP application (e.g., Asterisk, Kamailio, FreeSWITCH). This library intercepts the creation of new SSL/TLS session keys and sends them over the network (UDP or secure TCP) to the VoIPmonitor sensor.
| |
| | |
| === Step 1: Compile the SSL Key Logger Library ===
| |
| First, you need to compile the `sslkeylog.so` library on the same server as your SIP application.
| |
| | |
| ;1. Install prerequisites:
| |
| <pre>
| |
| # For Debian/Ubuntu
| |
| apt-get install libssl-dev build-essential git
| |
| | |
| # For CentOS/RHEL/AlmaLinux
| |
| yum install openssl-devel make gcc git
| |
| </pre>
| |
| | |
| ;2. Clone the repository and compile:
| |
| <pre>
| |
| cd /usr/local/src | | cd /usr/local/src |
| git clone https://github.com/voipmonitor/sniffer.git voipmonitor-git | | git clone https://github.com/voipmonitor/sniffer.git voipmonitor-git |
| cd voipmonitor-git/tools/ssl_keylogger/ | | cd voipmonitor-git/tools/ssl_keylogger/ |
| make | | make |
| </pre> | | </syntaxhighlight> |
| This will create the `sslkeylog.so` library in the current directory.
| |
|
| |
|
| ;3. Alternative: Compiling for WolfSSL:
| | {{Tip|For WolfSSL: <code>make ssl=wolf CXXFLAGS="-DHAVE_WOLFSSL" LDFLAGS="-lwolfssl"</code>}} |
| If your system uses WolfSSL instead of OpenSSL, you must use the appropriate flags during compilation:
| |
| <pre> | |
| cd /usr/local/src
| |
| git clone https://github.com/voipmonitor/sniffer.git voipmonitor-git
| |
| cd voipmonitor-git/tools/ssl_keylogger/
| |
| make ssl=wolf CXXFLAGS="-DHAVE_WOLFSSL" LDFLAGS="-lwolfssl" | |
| </pre> | |
| This ensures the sslkeylog library is built with WolfSSL compatibility.
| |
|
| |
|
| === Step 2: Configure Your SIP Application to Use the Key Logger ===
| | == Step 2: Configure Your PBX == |
| You must modify the startup script or service file of your SIP application to preload the library.
| |
|
| |
|
| ;General Test (works for any application using OpenSSL):
| | === Asterisk === |
| First, test that the library works correctly. This command should print "SSL KEYLOG : OK" messages.
| |
| <pre>
| |
| env SSLKEYLOG_UDP='127.0.0.1:1234' LD_PRELOAD="/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so" openssl
| |
| </pre>
| |
|
| |
|
| ==== Asterisk ==== | | <syntaxhighlight lang="bash"> |
| For `systemd`, create an environment file for the Asterisk service.
| | # Create environment file |
| ;1. Edit the service file: `systemctl edit asterisk.service` and add:
| | cat > /etc/default/asterisk-ssl << 'EOF' |
| <pre>
| |
| [Service]
| |
| EnvironmentFile=/etc/default/asterisk-ssl
| |
| </pre> | |
| ;2. Create the environment file `/etc/default/asterisk-ssl` with the following content:
| |
| <pre> | |
| # Destination IP and Port for sending session keys (UDP mode)
| |
| # IMPORTANT: For UDP mode, the sniffer does NOT listen on this port.
| |
| # Instead, the sniffer captures packets that are sent to this UDP port
| |
| # through its main interface (see Step 3 below).
| |
| SSLKEYLOG_UDP='127.0.0.1:1234' | | SSLKEYLOG_UDP='127.0.0.1:1234' |
| LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so' | | LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so' |
| </pre>
| | EOF |
| ;3. Reload and restart: `systemctl daemon-reload && systemctl restart asterisk`
| |
|
| |
|
| ==== Kamailio ====
| | # Add to service |
| Kamailio often loads OpenSSL dynamically, so you must preload both the key logger and the main SSL library.
| | systemctl edit asterisk.service |
| ;Modify your `/etc/init.d/kamailio` or systemd service file's `ExecStart` line:
| | </syntaxhighlight> |
| <pre>
| |
| # The path to libssl may vary. Find it with: find / -name "libssl.so*" | |
| env SSLKEYLOG_UDP='127.0.0.1:1234' LD_PRELOAD="/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so /usr/lib/x86_64-linux-gnu/libssl.so" /usr/sbin/kamailio ...
| |
| </pre> | |
|
| |
|
| ==== FreeSWITCH ====
| | Add: |
| FreeSWITCH can be sensitive to `systemd` settings. It's often necessary to modify the service file directly.
| | <syntaxhighlight lang="ini"> |
| ;Edit `/lib/systemd/system/freeswitch.service` and change `ExecStart` to:
| | [Service] |
| <pre> | | EnvironmentFile=/etc/default/asterisk-ssl |
| ExecStart=env SSLKEYLOG_UDP='10.0.0.1:1234' LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so' /usr/bin/freeswitch -u www-data -g www-data -nonat
| | </syntaxhighlight> |
| </pre> | |
| Then run `systemctl daemon-reload && systemctl restart freeswitch`.
| |
|
| |
|
| === Step 3: Configure VoIPmonitor to Receive Session Keys ===
| | Restart: <code>systemctl daemon-reload && systemctl restart asterisk</code> |
|
| |
|
| '''IMPORTANT: UDP vs TCP Mode Behavior'''
| | === FreeSWITCH === |
|
| |
|
| The SSL Key Logger supports two transport modes with **fundamentally different behavior**:
| | Edit <code>/lib/systemd/system/freeswitch.service</code>: |
|
| |
|
| * '''UDP Mode (default)''': The sniffer does '''NOT''' listen on a socket. Instead, the sniffer captures packets on its main interface (configured with `interface=`) and processes any UDP packets on `ssl_sessionkey_udp_port` as TLS session keys.
| | {{Warning|1='''Critical for DTLS+SRTP decryption:''' systemd must start the service as <code>root</code> so <code>LD_PRELOAD</code> can inject the keylogger before FreeSWITCH drops privileges. Set <code>User=root</code> in the service file and use <code>-u</code>/<code>-g</code> flags in <code>ExecStart</code> for FreeSWITCH to drop privileges internally.}} |
|
| |
|
| * '''TCP Mode''': The sniffer actively listens on a TCP port for incoming session key connections. Use `ssl_sessionkey_bind` and `ssl_sessionkey_bind_port` for TCP mode.
| | <syntaxhighlight lang="ini"> |
| | [Service] |
| | User=root |
| | Group=root |
| | ExecStart=env SSLKEYLOG_UDP='127.0.0.1:1234' LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so' /usr/bin/freeswitch -u freeswitch -g freeswitch -nonat |
| | </syntaxhighlight> |
|
| |
|
| '''=== UDP Mode Configuration ==='''
| | Then reload and restart: |
| | <syntaxhighlight lang="bash"> |
| | systemctl daemon-reload |
| | systemctl restart freeswitch |
| | </syntaxhighlight> |
|
| |
|
| For UDP delivery, ensure your VoIPmonitor sensor's main `interface` is configured to capture traffic from the network where the PBX sends UDP session key packets.
| | === Kamailio === |
|
| |
|
| '''IMPORTANT: Capturing Keys from Localhost''' | | {{Warning|1=Kamailio requires '''all three libraries''' in LD_PRELOAD to avoid crashes:}} |
|
| |
|
| If your PBX and VoIPmonitor sensor are on the same server, and you are sending keys to `127.0.0.1` (localhost), you '''must''' add the loopback interface (`lo`) to the `interface` directive, or the sensor will never see the UDP packets containing the session keys.
| | <syntaxhighlight lang="bash"> |
| | # Find library paths |
| | find /usr/lib -name "libssl.so*" -o -name "libjson-c.so*" |
| | </syntaxhighlight> |
|
| |
|
| In `/etc/voipmonitor.conf`:
| | Edit service file: |
| | <syntaxhighlight lang="ini"> |
| | ExecStart=env SSLKEYLOG_UDP='127.0.0.1:1234' LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so:/usr/lib/x86_64-linux-gnu/libssl.so.3:/usr/lib/x86_64-linux-gnu/libjson-c.so.5' /usr/sbin/kamailio ... |
| | </syntaxhighlight> |
|
| |
|
| <pre>
| | == Step 3: Configure VoIPmonitor == |
| # Include loopback interface when SSLKEYLOG_UDP points to 127.0.0.1
| |
| interface = eth0,lo
| |
| </pre>
| |
|
| |
|
| If you do not add `lo`, the sensor will appear to run correctly, but decryption will fail because the session key packets are never captured.
| | <syntaxhighlight lang="ini"> |
| | |
| In `/etc/voipmonitor.conf`:
| |
| | |
| <pre> | |
| # /etc/voipmonitor.conf | | # /etc/voipmonitor.conf |
| | | ssl = yes |
| # UDP MODE: Tell sniffer to process captured UDP packets on this port as session keys
| |
| # The sniffer does NOT bind/listen on this port - it passively captures packets.
| |
| # The sniffer's main 'interface' must capture traffic from the network where
| |
| # the PBX sends these UDP packets.
| |
| ssl_sessionkey_udp = yes | | ssl_sessionkey_udp = yes |
|
| |
| # The port must match the one set in the SSLKEYLOG_UDP environment variable
| |
| ssl_sessionkey_udp_port = 1234 | | ssl_sessionkey_udp_port = 1234 |
|
| |
|
| # Optional: Only accept session keys from specific IP/subnet | | # CRITICAL: No key file path when using SSL Key Logger! |
| # ssl_sessionkey_udp_ip = 192.168.0.0/24
| | ssl_ipport = 192.168.0.1:5061 |
|
| |
|
| # Enable the SSL decryption module globally | | # Include loopback if sending keys to 127.0.0.1 |
| ssl = yes
| | interface = eth0,lo |
| | </syntaxhighlight> |
|
| |
|
| # CORRECT SYNTAX for the Key Logger Method:
| | {{Warning|1='''WRONG:''' <code>ssl_ipport = IP:PORT /path/to/key</code> — This forces Method 1 and ignores the key logger!<br>'''CORRECT:''' <code>ssl_ipport = IP:PORT</code> — No key file path.}} |
| # Tell the sensor which IP:Port to apply the received session keys to.
| |
| # Notice there is NO path to a key file.
| |
| ssl_ipport = 192.168.0.1:5061 | |
|
| |
|
| # --------------------------------------------------------------------
| | == Secure Key Transport (TCP Mode) == |
|
| |
|
| # INCORRECT SYNTAX for the Key Logger Method:
| | For production environments, use TCP instead of UDP: |
| # The following line will IGNORE the key logger and try to use the key file,
| |
| # which will fail for DHE/ECDHE ciphers. DO NOT USE THIS SYNTAX WITH THE KEY LOGGER.
| |
| # ssl_ipport = 192.168.0.1:5061 /path/to/my_server.key
| |
| </pre>
| |
|
| |
|
| '''CRITICAL CONFIGURATION NOTE:'''
| | <syntaxhighlight lang="bash"> |
| When using the SSL Key Logger method, the `ssl_ipport` directive '''must only''' specify the IP address and port. It '''must not''' include a path to a key file.
| | # Recompile with TCP support |
| | cd /usr/local/src/voipmonitor-git/tools/ssl_keylogger/ |
| | make clean && make with_tcp |
| | </syntaxhighlight> |
|
| |
|
| Including a key file path forces VoIPmonitor to use Method 1 (Private Key) for that specific IP:Port, which will override the key logger and cause decryption to fail if PFS ciphers are in use.
| | On PBX: Change <code>SSLKEYLOG_UDP</code> to <code>SSLKEYLOG_TCP</code> |
|
| |
|
| === Securing Key Transport (TCP Mode) ===
| | On VoIPmonitor: |
| By default, keys are sent unencrypted over UDP. For production environments where the sensor and PBX are on different hosts, it is recommended to use the secure TCP mode.
| | <syntaxhighlight lang="ini"> |
| ;1. Compile the keylogger with TCP support:
| |
| <pre>
| |
| cd /usr/local/src/voipmonitor-git/tools/ssl_keylogger/
| |
| make with_tcp
| |
| </pre>
| |
| ;2. Change the environment variable on your PBX from `SSLKEYLOG_UDP` to `SSLKEYLOG_TCP`.
| |
| ;3. Change the VoIPmonitor sensor configuration to listen on TCP:
| |
| <pre> | |
| # In voipmonitor.conf
| |
| ssl_sessionkey_udp = no | | ssl_sessionkey_udp = no |
| ssl_sessionkey_bind = 0.0.0.0 # IP for the sniffer to listen on | | ssl_sessionkey_bind = 0.0.0.0 |
| ssl_sessionkey_bind_port = 1234 | | ssl_sessionkey_bind_port = 1234 |
| </pre> | | </syntaxhighlight> |
| | |
| == Method 3: TLS Decryption in Distributed/Client-Server Mode ==
| |
| When using VoIPmonitor's client-server architecture (<code>packetbuffer_sender=yes</code>), remote sensors forward raw packets to a central server. In this configuration, TLS/SRTP decryption '''must''' occur on the central server. This requires special configuration for the SSL Key Logger to send session keys to the correct destination.
| |
|
| |
|
| === Architecture Overview === | | = Method 3: Distributed Mode = |
|
| |
|
| When a client sensor forwards packets with <code>packetbuffer_sender=yes</code>: | | When using <code>packetbuffer_sender=yes</code>, session keys '''must''' go to the central server. |
| * The client sensor sends raw packet stream to the central server
| |
| * The central server performs packet analysis and decryption
| |
| * Session keys from the PBX must be sent to the '''central server''', not the remote client sensor
| |
|
| |
|
| <kroki lang="plantuml"> | | <kroki lang="plantuml"> |
| @startuml | | @startuml |
| skinparam shadowing false | | skinparam shadowing false |
| skinparam defaultFontName Arial
| | rectangle "PBX" as PBX |
| | |
| rectangle "PBX Server" as PBX | |
| rectangle "Client Sensor" as Client | | rectangle "Client Sensor" as Client |
| rectangle "Central Server" as Central | | rectangle "Central Server" as Central |
|
| |
|
| PBX --(1)--> Central : Session Keys\n(SSLKEYLOG to Central IP) | | PBX --> Central : Session Keys (direct) |
| Client --(2)--> Central : Raw Packets\n(packetbuffer_sender=yes) | | Client --> Central : Raw Packets |
| | | note right of PBX: SSLKEYLOG_UDP must\\npoint to Central IP |
| note right of Client | |
| Client does NOT\nreceive session keys
| |
| end note
| |
| | |
| note right of PBX
| |
| Send keys to\nCentral Server IP
| |
| NOT to localhost
| |
| or client sensor
| |
| end note
| |
| @enduml | | @enduml |
| </kroki> | | </kroki> |
|
| |
|
| === Configuration for Distributed Mode === | | '''On PBX:''' |
| | <syntaxhighlight lang="ini"> |
| | # Send keys to CENTRAL SERVER, not localhost! |
| | SSLKEYLOG_UDP='192.168.1.100:1234' # Central server IP |
| | </syntaxhighlight> |
|
| |
|
| '''Step 1: Configure Client Sensor''' | | '''On Central Server:''' |
| <code>/etc/voipmonitor.conf</code> on the remote client sensor:
| |
| <syntaxhighlight lang="ini"> | | <syntaxhighlight lang="ini"> |
| id_sensor = 2
| | ssl = yes |
| server_destination = central.server.ip
| | ssl_sessionkey_udp = yes |
| server_destination_port = 60024
| | ssl_sessionkey_udp_port = 1234 |
| server_password = your_strong_password
| | ssl_ipport = 192.168.1.50:5061 # PBX IP (no key file) |
| | </syntaxhighlight> |
| | |
| | = Method 4: SBC/PBX Tunneling = |
|
| |
|
| packetbuffer_sender = yes # Forward raw packets to central server
| | Some SBCs decrypt internally and forward unencrypted traffic via tunneling protocols. |
| interface = eth0
| | |
| # NO ssl_* configuration needed on client | | {| class="wikitable" |
| | ! Vendor !! Protocol !! Documentation |
| | |- |
| | | Ribbon/Oracle || Monitoring Profile || [[Ribbon7k_monitoring_profiles]] |
| | |- |
| | | AudioCodes || Proprietary tunnel || [[Audiocodes_tunneling]] |
| | |- |
| | | Generic || IPinIP || Auto-decoded by VoIPmonitor |
| | |} |
| | |
| | {{Note|1=When using vendor tunneling, '''no SSL configuration''' is needed in VoIPmonitor—traffic arrives unencrypted.}} |
| | |
| | = Method 5: External Key Providers = |
| | |
| | Some hosted platforms (e.g., NetSapiens) can export TLS session keys to VoIPmonitor. Configure VoIPmonitor to receive keys via UDP/TCP as in Method 2. |
| | |
| | = Method 6: HEP Protocol = |
| | |
| | Alternative when SSL Key Logger doesn't work. The SIP proxy decrypts traffic and sends it via HEP. |
| | |
| | <syntaxhighlight lang="ini"> |
| | # /etc/voipmonitor.conf |
| | receiver_mode = yes |
| | hep = yes |
| | hep_bind_ip = 0.0.0.0 |
| | hep_bind_port = 9060 |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| '''Step 2: Configure PBX sslkeylog to Send Keys to Central Server''' | | {{Note|1=HEP is just transport. Your SIP proxy must decrypt TLS '''before''' encapsulating in HEP. See [[Sniffing_modes#HEP_(Homer_Encapsulation_Protocol)|HEP documentation]].}} |
| On your PBX server, the <code>SSLKEYLOG_UDP</code> or <code>SSLKEYLOG_TCP</code> variable '''MUST'' point to the central server's IP address, '''NOTlocalhost or the client sensor'''.
| | |
| | = SRTP/DTLS Decryption = |
| | |
| | == Recommended Configuration == |
|
| |
|
| <syntaxhighlight lang="ini"> | | <syntaxhighlight lang="ini"> |
| # /etc/default/asterisk-ssl (example) | | # Enables best-practice DTLS settings |
| | | ssl_dtls_boost = yes |
| # CRITICAL: Send keys to CENTRAL SERVER IP and port
| |
| # NOT to localhost, NOT to client sensor
| |
| SSLKEYLOG_UDP='192.168.1.100:1234' # Central Server IP : ssl_sessionkey_udp_port
| |
| LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so'
| |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| '''Step 3: Configure Central Server'''
| | == RTP Proxy Issues (rtpengine) == |
| <code>/etc/voipmonitor.conf</code> on the central server:
| |
| <syntaxhighlight lang="ini">
| |
| # Server mode configuration
| |
| server_bind = 0.0.0.0
| |
| server_bind_port = 60024
| |
| server_password = your_strong_password
| |
|
| |
|
| mysqlhost = localhost
| | If SRTP decryption fails with SDES keys visible in SDP, your RTP proxy may be stripping keys. |
| mysqldb = voipmonitor
| |
| mysqluser = voipmonitor
| |
| mysqlpassword = db_password
| |
|
| |
|
| # Enable SSL decryption on central server
| | '''Fix for rtpengine (Kamailio):''' |
| ssl = yes
| | <syntaxhighlight lang="javascript"> |
| | rtpengine_manage("replace-origin DTLS=no SDES-nonew SDES-pad"); |
| | </syntaxhighlight> |
| | |
| | == Garbled Audio == |
|
| |
|
| # UDP MODE: Process captured UDP packets on this port as session keys
| | Garbled/distorted audio usually means SRTP is encrypted but not decrypted—'''not''' a codec issue. |
| # The central server's interface must capture traffic where PBX sends keys
| |
| ssl_sessionkey_udp = yes
| |
| ssl_sessionkey_udp_port = 1234 # Must match SSLKEYLOG_UDP port on PBX
| |
|
| |
|
| # Apply keys to the PBX's TLS/IP address
| | '''Solution:''' Configure SSL Key Logger as described in Method 2, then verify keys are being received: |
| ssl_ipport = 192.168.1.50:5061 # PBX IP and TLS port (no key file path)
| | <syntaxhighlight lang="bash"> |
| | tcpdump -i any -n port 1234 # Check for UDP key packets |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| === Common Configuration Error === | | = Troubleshooting = |
| | |
| | == Decryption Not Working == |
|
| |
|
| '''Symptom:''' TLS/SRTP decryption fails when <code>packetbuffer_sender=yes</code> is enabled, but works with <code>packetbuffer_sender=no</code>. | | '''Step 1: Verify packets are captured''' |
| | * Check <code>sip:history (+)</code> in CDR detail |
| | * Packets visible but encrypted → decryption issue |
| | * Packets missing → capture issue (check interface config) |
|
| |
|
| '''Root Cause:''' The PBX's <code>SSLKEYLOG_UDP</code> is pointing to <code>127.0.0.1</code> (localhost) instead of the central server's IP address. Session keys are received by the client sensor, but the client sensor forwards only raw packets to the central server - the keys are lost in transit. | | '''Step 2: Check configuration''' |
|
| |
|
| '''Fix:''' Change the PBX environment variable:
| | {| class="wikitable" |
| ;Wrong (causes decryption failure in distributed mode):
| | ! Issue !! Solution |
| <pre> | | |- |
| SSLKEYLOG_UDP='127.0.0.1:1234'
| | | Keys sent to localhost but not captured || Add <code>lo</code> to interface: <code>interface = eth0,lo</code> |
| </pre> | | |- |
| | | TCP/TLS packets not captured || Remove/fix BPF filter: <code>filter = udp or tcp or (vlan and (udp or tcp))</code> |
| | |- |
| | | <code>ssl_ipport</code> has key file path || Remove key path when using SSL Key Logger |
| | |- |
| | | <code>packetbuffer_sender=yes</code> fails || Send keys to central server IP, not localhost |
| | |- |
| | | FreeSWITCH not capturing DTLS+SRTP keys || Set <code>User=root</code> in systemd service file, use <code>-u</code>/<code>-g</code> flags in <code>ExecStart</code> |
| | |} |
|
| |
|
| ;Correct (send keys directly to central server):
| | == Compilation/Startup Issues == |
| <pre>
| |
| SSLKEYLOG_UDP='192.168.1.100:1234' # Central server's IP address
| |
| </pre>
| |
|
| |
|
| === Using TCP Mode in Distributed Deployments === | | {| class="wikitable" |
| | ! Error !! Platform !! Solution |
| | |- |
| | | <code>undefined symbol: dlsym</code> || RHEL/CentOS/VitalPBX || Recompile: <code>g++ -shared -o sslkeylog.so sslkeylog.o -ldl</code> (library flags after objects) |
| | |- |
| | | FreeSWITCH stuck in "activating" || Any || Recompile without TCP: <code>make clean && make</code>; set <code>DEBUG 0</code> and <code>WRITE_THREAD 0</code> |
| | |- |
| | | Kamailio <code>receive_fd(): EOF</code> || Debian 12 || Add libjson-c.so to LD_PRELOAD (see Kamailio section) |
| | |- |
| | | Environment variables not loaded || Any || Use <code>asterisk -r</code> then <code>core stop now</code> instead of systemctl restart |
| | |} |
|
| |
|
| For secure key transport in distributed architectures, use TCP mode.
| | == High Traffic Issues == |
|
| |
|
| On the PBX:
| | '''Symptom:''' Packet drops, TLS calls not decrypted under load |
| <syntaxhighlight lang="bash">
| |
| # Use TCP instead of UDP
| |
| SSLKEYLOG_TCP='192.168.1.100:1234'
| |
| LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so'
| |
| </syntaxhighlight>
| |
|
| |
|
| On the Central Server:
| | '''Solution 1:''' Increase wait time: |
| <syntaxhighlight lang="ini"> | | <syntaxhighlight lang="ini"> |
| ssl_sessionkey_udp = no
| | ssl_sessionkey_maxwait_ms = 5000 |
| ssl_sessionkey_bind = 0.0.0.0 # Accept connections on all interfaces
| |
| ssl_sessionkey_bind_port = 1234
| |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| === Summary Checklist === | | '''Solution 2:''' Switch to TCP mode (see "Secure Key Transport" above) |
| | |
| | == Capture for Support == |
| | |
| | <syntaxhighlight lang="bash"> |
| | # Capture TLS traffic + keylogger packets |
| | tcpdump -i eth0,lo -w /tmp/debug.pcap \ |
| | "((host PBX_IP and port 5061) or (port 1234))" |
| | </syntaxhighlight> |
|
| |
|
| For successful TLS/SRTP decryption with <code>packetbuffer_sender=yes</code>:
| | Provide to support: |
| | * CDR ID |
| | * <code>voipmonitor --version</code> |
| | * Config snippet (ssl*, interface, packetbuffer_sender) |
| | * The PCAP file |
|
| |
|
| * Client sensor: Enable <code>packetbuffer_sender=yes</code>, forward raw packets
| | = See Also = |
| * Central server: Enable <code>ssl=1</code> and configure SSL key listener
| |
| * PBX: Set <code>SSLKEYLOG_UDP</code> to '''central server IP''', not localhost or client sensor
| |
| * Central server's <code>ssl_ipport</code> must match PBX IP:port (no key file path)
| |
| * Central server's <code>ssl_sessionkey_udp_port</code> must match PBX's <code>SSLKEYLOG_UDP</code> port
| |
|
| |
|
| == Decrypting SRTP (DTLS) ==
| | * [[Audiocodes_tunneling]] - AudioCodes SBC tunneling |
| Decrypting SRTP requires capturing both the DTLS handshake packets (which happen before RTP) and the session keys from the key logger. VoIPmonitor uses a sophisticated queueing system to hold DTLS packets until the corresponding session key arrives.
| | * [[Ribbon7k_monitoring_profiles]] - Ribbon/Oracle SBC monitoring |
| | * [[WebRTC]] - WebRTC/WSS decryption |
| | * [[Sniffer_configuration]] - Full configuration reference |
| | * [[Sniffer_distributed_architecture]] - Client-server architecture |
|
| |
|
| ;Recommended Configuration:
| | = AI Summary for RAG = |
| The <code>ssl_dtls_boost</code> pseudo-parameter enables a set of recommended defaults for robust decryption. It is enabled by default in recent versions.
| |
| <pre>
| |
| # This single parameter enables the best-practice settings below it.
| |
| ssl_dtls_boost = yes
| |
|
| |
|
| # --- Settings enabled by ssl_dtls_boost ---
| | '''Summary:''' Guide to decrypting TLS-encrypted SIP and SRTP media in VoIPmonitor. Six methods: (1) Private Key - only for TLS 1.2 without DHE/ECDHE, configure <code>ssl_ipport=IP:PORT /path/to/key</code>; (2) SSL Key Logger (recommended) - universal for all ciphers, inject <code>sslkeylog.so</code> via LD_PRELOAD into Asterisk/Kamailio/FreeSWITCH, keys sent via UDP or TCP; (3) Distributed Mode - with <code>packetbuffer_sender=yes</code>, send keys to central server IP not localhost; (4) SBC Tunneling - Ribbon/AudioCodes decrypt internally; (5) External Key Providers - hosted platforms export keys; (6) HEP - SIP proxy decrypts then sends via HEP. Critical: when using SSL Key Logger, <code>ssl_ipport</code> must NOT include key file path. For localhost keys, add <code>lo</code> to interface. Kamailio requires three libraries in LD_PRELOAD. FreeSWITCH requires <code>User=root</code> in systemd service file with <code>-u</code>/<code>-g</code> flags in ExecStart for DTLS+SRTP decryption to work. High traffic: use TCP mode or increase <code>ssl_sessionkey_maxwait_ms</code>. Garbled audio = SRTP encryption not codec issue. |
| # ssl_dtls_queue_expiration = 30
| |
| # ssl_sessionkey_keep = yes
| |
| # ssl_dtls_queue_keep = yes
| |
| # ssl_dtls_handshake_safe = ext
| |
| # srtp_rtp_local_instances = yes
| |
| </pre> | |
|
| |
|
| == AI Summary for RAG ==
| | '''Keywords:''' tls, ssl, srtp, dtls, decryption, sslkeylog, ld_preload, session key, asterisk, kamailio, freeswitch, ssl_ipport, ssl_sessionkey_udp, packetbuffer_sender, distributed mode, ribbon sbc, audiocodes, hep, rtpengine, pfs, perfect forward secrecy, garbled audio, dlsym error |
| '''Summary:''' This guide details the methods for decrypting TLS-encrypted SIP and SRTP media in VoIPmonitor. Method 1, Private Key Decryption, uses `ssl=yes` with `ssl_ipport=IP:PORT /path/to/key`; this method works ONLY for TLS 1.2 or older WITHOUT Diffie-Hellman ciphers (non-PFS). For all other cases (TLS 1.3 or any DH cipher like DHE/ECDHE/EDH), private key decryption is IMPOSSIBLE due to Perfect Forward Secrecy. Method 2, the SSL Key Logger, is the universal solution working with all ciphers including PFS. It injects `sslkeylog.so` into SIP applications (Asterisk, Kamailio, FreeSWITCH) via `LD_PRELOAD`, which intercepts and sends session keys to the VoIPmonitor sensor via UDP (default) or TCP. The critical syntax rule for Method 2: `ssl_ipport` must NOT include a key file path. CLOUD SERVICE LIMITATIONS: Direct hardware phone to cloud decryption is IMPOSSIBLE because you lack the cloud's private key, cloud uses TLS 1.3/DH, and you cannot inject keylogger. Softphone to cloud is possible via SSL Key Logger on the local host. Phone to local SBC to cloud is possible using SBC monitoring features (e.g., Ribbon SBC Monitoring Profile to export decrypted SIP). IMPORTANT: UDP mode does NOT make the sniffer listen on a port; the sniffer passively captures UDP packets on `ssl_sessionkey_udp_port` through its main interface. CRITICAL ISSUE: When sending keys to `127.0.0.1`, the loopback interface (`lo`) MUST be added to `interface` directive (e.g., `interface = eth0,lo`), otherwise keys won't be captured and decryption fails. After adding `lo`, restart VoIPmonitor and the TLS application. Method 3 describes TLS decryption in distributed client-server architecture with `packetbuffer_sender=yes`. The common issue in distributed mode is that PBX's `SSLKEYLOG_UDP` points to `127.0.0.1` instead of the central server's IP; session keys sent to localhost are captured by the client sensor but never forwarded. The fix is to send session keys directly to the central server (e.g., `SSLKEYLOG_UDP='192.168.1.100:1234'`). TCP mode is recommended for secure key transport using `SSLKEYLOG_TCP`, `ssl_sessionkey_bind`, and `ssl_sessionkey_bind_port`. The guide also covers DTLS-SRTP decryption with the recommended `ssl_dtls_boost` parameter. TROUBLESHOOTING WORKFLOW: When TLS traffic is not being decrypted, first verify packet capture using `sip:history (+)` in the CDR detail view. If packets are present but encrypted, create a packet capture from the VoIPmonitor probe that includes: (1) TLS traffic from capture interface (e.g., eno1) filtering for PBX IP and TLS port 5061, (2) keylogger traffic from loopback interface (lo) on the `ssl_sessionkey_udp_port` (default 1234), and (3) complete TLS handshake including Client Hello and Server Hello packets. Example tcpdump command captures both interfaces simultaneously: `tcpdump -i eno1,lo -w /tmp/tls_debug_capture.pcap -s 0 "((host 192.168.1.50 and port 5061) or (port 1234))"`. Provide this capture to support team with CDR ID, version, and configuration. COMMON SYMPTOMS AND FIXES: (1) Key logger running but decryption not working → add `lo` to interface, (2) DHE/ECDHE decryption fails despite key logger → remove key file path from `ssl_ipport`, (3) Works with `packetbuffer_sender=no` but fails with `yes` → send keys to central server IP not localhost, (4) Cloud service decryption impossible → need local SBC or softphone.
| |
| '''Keywords:''' tls, ssl, srtp, dtls, decryption, decrypt, encrypted, pfs, perfect forward secrecy, diffie-hellman, private key, sslkeylog, ld_preload, session key, asterisk, kamailio, freeswitch, `ssl_ipport`, `ssl_sessionkey_udp`, `ssl_dtls_boost`, `make with_tcp`, syntax, distributed architecture, client-server, `packetbuffer_sender`, central server, remote sensor, `SSLKEYLOG_UDP`, `SSLKEYLOG_TCP`, `ssl_sessionkey_bind`, `ssl_sessionkey_bind_port`, localhost, `127.0.0.1`, loopback, `lo`, `interface`, not decrypting, not working, key logger not decrypting, troubleshooting, cloud service, webex, teams, zoom phone, tls 1.3, ciphersuite, ecdhe, dhe, edh, softphone hardware phone sbc ribbon monitoring profile, `sip:history`, packet capture, tcpdump, client hello, server hello, tls handshake, support analysis | |
| '''Key Questions:'''
| |
| * How do I decrypt TLS encrypted SIP calls between phones and a cloud VoIP service like Webex?
| |
| * Can I decrypt SIP traffic between hardware phones and cloud services without a local SBC?
| |
| * Why is VoIPmonitor not decrypting my TLS packets when SSL key logger is running?
| |
| * What is the correct syntax for `ssl_ipport` when using the SSL Key Logger?
| |
| * What is the SSL Key Logger and how does it work?
| |
| * How to configure Asterisk or FreeSWITCH to send TLS session keys to VoIPmonitor?
| |
| * How do I decrypt calls that use Diffie-Hellman (DHE/ECDHE) ciphers?
| |
| * What is `LD_PRELOAD` and how is it used for decryption?
| |
| * How can I decrypt SRTP and DTLS media streams?
| |
| * What does the `ssl_dtls_boost` parameter do?
| |
| * How to configure TLS decryption with `packetbuffer_sender=yes` in distributed mode?
| |
| * Why does TLS decryption work with `packetbuffer_sender=no` but fail with `packetbuffer_sender=yes`?
| |
| * Where should I send SSL session keys in a VoIPmonitor client-server architecture?
| |
| * Do I need to add loopback `lo` to interface when sending SSL keys to 127.0.0.1?
| |
| * Why is SSL key logger not capturing session keys from localhost?
| |
| * How do I fix TLS decryption that fails with the key logger method?
| |
| * What should I do if TLS traffic is not being decrypted in the VoIPmonitor GUI?
| |
| * How do I use `sip:history (+)` to troubleshoot TLS decryption issues?
| |
| * How to create a packet capture for TLS decryption debugging?
| |
| * What should be included in a TLS packet trace for support analysis?
| |
| * Should I capture from both the network interface and loopback for TLS debugging?
| |
This guide covers how to decrypt encrypted SIP (TLS) and media (SRTP/DTLS-SRTP) traffic in VoIPmonitor.
Understanding TLS Decryption
VoIPmonitor can decrypt TLS-encrypted SIP signaling and SRTP media. The method you choose depends on your TLS configuration.
Cipher Suite Impact
| TLS Version / Cipher |
Private Key Decryption |
SSL Key Logger
|
| TLS 1.2 with RSA (no DH) |
✓ Yes Works |
✓ Yes Works
|
| TLS 1.2 with DHE/ECDHE |
✗ No Impossible |
✓ Yes Required
|
| TLS 1.3 (any cipher) |
✗ No Impossible |
✓ Yes Required
|
⚠️ Warning: Modern VoIP services use TLS 1.3 or PFS ciphers. The SSL Key Logger (Method 2) is the only viable method for most deployments.
To check your cipher suite, capture the TLS handshake in Wireshark and look for "DHE" or "ECDHE" in the cipher negotiation.
Method Overview
Quick Reference:
- Method 1 - Private Key: Simple, but only works for non-PFS ciphers
- Method 2 - SSL Key Logger: Universal, works for all ciphers (recommended)
- Method 3 - Distributed Mode: For client-server architecture with
packetbuffer_sender=yes
- Method 4 - SBC/PBX Tunneling: Ribbon, AudioCodes, or other vendor solutions
- Method 5 - External Key Provider: Hosted platforms (NetSapiens, etc.)
- Method 6 - HEP Protocol: Alternative when SSL Key Logger isn't feasible
Cloud Service Limitations
| Scenario |
Decryption Possible?
|
| Hardware phone → Cloud (Teams, Webex) |
✗ No Not possible (no access to cloud keys)
|
| Softphone on controlled host → Cloud |
✓ Yes Use SSL Key Logger on the host
|
| Phone → Local SBC → Cloud |
✓ Yes Use SBC tunneling (Method 4)
|
Method 1: Private Key Decryption
Works only for TLS 1.2 or older without Diffie-Hellman ciphers.
Configuration
# /etc/voipmonitor.conf
ssl = yes
ssl_ipport = 10.0.0.1:5061 /etc/pki/tls/private/server.key
Multiple servers:
ssl_ipport = 10.0.0.1:5061 /path/to/server1.key
ssl_ipport = 10.0.0.2:5061 /path/to/server2.key
GUI Configuration
Navigate to Settings > Sensors > wrench icon and search for ssl_:
ssl = yes
ssl_ipport = IP:PORT /path/to/key
Method 2: SSL Key Logger (Recommended)
Works for all cipher suites including PFS. Captures session keys from your PBX/SBC using LD_PRELOAD.
Step 1: Compile the Library
# Install prerequisites
apt-get install libssl-dev build-essential git # Debian/Ubuntu
yum install openssl-devel make gcc git # RHEL/CentOS
# Compile
cd /usr/local/src
git clone https://github.com/voipmonitor/sniffer.git voipmonitor-git
cd voipmonitor-git/tools/ssl_keylogger/
make
Step 2: Configure Your PBX
Asterisk
# Create environment file
cat > /etc/default/asterisk-ssl << 'EOF'
SSLKEYLOG_UDP='127.0.0.1:1234'
LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so'
EOF
# Add to service
systemctl edit asterisk.service
Add:
[Service]
EnvironmentFile=/etc/default/asterisk-ssl
Restart: systemctl daemon-reload && systemctl restart asterisk
FreeSWITCH
Edit /lib/systemd/system/freeswitch.service:
⚠️ Warning: Critical for DTLS+SRTP decryption: systemd must start the service as root so LD_PRELOAD can inject the keylogger before FreeSWITCH drops privileges. Set User=root in the service file and use -u/-g flags in ExecStart for FreeSWITCH to drop privileges internally.
[Service]
User=root
Group=root
ExecStart=env SSLKEYLOG_UDP='127.0.0.1:1234' LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so' /usr/bin/freeswitch -u freeswitch -g freeswitch -nonat
Then reload and restart:
systemctl daemon-reload
systemctl restart freeswitch
Kamailio
⚠️ Warning: Kamailio requires all three libraries in LD_PRELOAD to avoid crashes:
# Find library paths
find /usr/lib -name "libssl.so*" -o -name "libjson-c.so*"
Edit service file:
ExecStart=env SSLKEYLOG_UDP='127.0.0.1:1234' LD_PRELOAD='/usr/local/src/voipmonitor-git/tools/ssl_keylogger/sslkeylog.so:/usr/lib/x86_64-linux-gnu/libssl.so.3:/usr/lib/x86_64-linux-gnu/libjson-c.so.5' /usr/sbin/kamailio ...
Step 3: Configure VoIPmonitor
# /etc/voipmonitor.conf
ssl = yes
ssl_sessionkey_udp = yes
ssl_sessionkey_udp_port = 1234
# CRITICAL: No key file path when using SSL Key Logger!
ssl_ipport = 192.168.0.1:5061
# Include loopback if sending keys to 127.0.0.1
interface = eth0,lo
⚠️ Warning: WRONG: ssl_ipport = IP:PORT /path/to/key — This forces Method 1 and ignores the key logger!
CORRECT: ssl_ipport = IP:PORT — No key file path.
Secure Key Transport (TCP Mode)
For production environments, use TCP instead of UDP:
# Recompile with TCP support
cd /usr/local/src/voipmonitor-git/tools/ssl_keylogger/
make clean && make with_tcp
On PBX: Change SSLKEYLOG_UDP to SSLKEYLOG_TCP
On VoIPmonitor:
ssl_sessionkey_udp = no
ssl_sessionkey_bind = 0.0.0.0
ssl_sessionkey_bind_port = 1234
Method 3: Distributed Mode
When using packetbuffer_sender=yes, session keys must go to the central server.
On PBX:
# Send keys to CENTRAL SERVER, not localhost!
SSLKEYLOG_UDP='192.168.1.100:1234' # Central server IP
On Central Server:
ssl = yes
ssl_sessionkey_udp = yes
ssl_sessionkey_udp_port = 1234
ssl_ipport = 192.168.1.50:5061 # PBX IP (no key file)
Method 4: SBC/PBX Tunneling
Some SBCs decrypt internally and forward unencrypted traffic via tunneling protocols.
ℹ️ Note: When using vendor tunneling, no SSL configuration is needed in VoIPmonitor—traffic arrives unencrypted.
Method 5: External Key Providers
Some hosted platforms (e.g., NetSapiens) can export TLS session keys to VoIPmonitor. Configure VoIPmonitor to receive keys via UDP/TCP as in Method 2.
Method 6: HEP Protocol
Alternative when SSL Key Logger doesn't work. The SIP proxy decrypts traffic and sends it via HEP.
# /etc/voipmonitor.conf
receiver_mode = yes
hep = yes
hep_bind_ip = 0.0.0.0
hep_bind_port = 9060
ℹ️ Note: HEP is just transport. Your SIP proxy must decrypt TLS before encapsulating in HEP. See HEP documentation.
SRTP/DTLS Decryption
Recommended Configuration
# Enables best-practice DTLS settings
ssl_dtls_boost = yes
RTP Proxy Issues (rtpengine)
If SRTP decryption fails with SDES keys visible in SDP, your RTP proxy may be stripping keys.
Fix for rtpengine (Kamailio):
rtpengine_manage("replace-origin DTLS=no SDES-nonew SDES-pad");
Garbled Audio
Garbled/distorted audio usually means SRTP is encrypted but not decrypted—not a codec issue.
Solution: Configure SSL Key Logger as described in Method 2, then verify keys are being received:
tcpdump -i any -n port 1234 # Check for UDP key packets
Troubleshooting
Decryption Not Working
Step 1: Verify packets are captured
- Check
sip:history (+) in CDR detail
- Packets visible but encrypted → decryption issue
- Packets missing → capture issue (check interface config)
Step 2: Check configuration
| Issue |
Solution
|
| Keys sent to localhost but not captured |
Add lo to interface: interface = eth0,lo
|
| TCP/TLS packets not captured |
Remove/fix BPF filter: filter = udp or tcp or (vlan and (udp or tcp))
|
ssl_ipport has key file path |
Remove key path when using SSL Key Logger
|
packetbuffer_sender=yes fails |
Send keys to central server IP, not localhost
|
| FreeSWITCH not capturing DTLS+SRTP keys |
Set User=root in systemd service file, use -u/-g flags in ExecStart
|
Compilation/Startup Issues
| Error |
Platform |
Solution
|
undefined symbol: dlsym |
RHEL/CentOS/VitalPBX |
Recompile: g++ -shared -o sslkeylog.so sslkeylog.o -ldl (library flags after objects)
|
| FreeSWITCH stuck in "activating" |
Any |
Recompile without TCP: make clean && make; set DEBUG 0 and WRITE_THREAD 0
|
Kamailio receive_fd(): EOF |
Debian 12 |
Add libjson-c.so to LD_PRELOAD (see Kamailio section)
|
| Environment variables not loaded |
Any |
Use asterisk -r then core stop now instead of systemctl restart
|
High Traffic Issues
Symptom: Packet drops, TLS calls not decrypted under load
Solution 1: Increase wait time:
ssl_sessionkey_maxwait_ms = 5000
Solution 2: Switch to TCP mode (see "Secure Key Transport" above)
Capture for Support
# Capture TLS traffic + keylogger packets
tcpdump -i eth0,lo -w /tmp/debug.pcap \
"((host PBX_IP and port 5061) or (port 1234))"
Provide to support:
- CDR ID
voipmonitor --version
- Config snippet (ssl*, interface, packetbuffer_sender)
- The PCAP file
See Also
AI Summary for RAG
Summary: Guide to decrypting TLS-encrypted SIP and SRTP media in VoIPmonitor. Six methods: (1) Private Key - only for TLS 1.2 without DHE/ECDHE, configure ssl_ipport=IP:PORT /path/to/key; (2) SSL Key Logger (recommended) - universal for all ciphers, inject sslkeylog.so via LD_PRELOAD into Asterisk/Kamailio/FreeSWITCH, keys sent via UDP or TCP; (3) Distributed Mode - with packetbuffer_sender=yes, send keys to central server IP not localhost; (4) SBC Tunneling - Ribbon/AudioCodes decrypt internally; (5) External Key Providers - hosted platforms export keys; (6) HEP - SIP proxy decrypts then sends via HEP. Critical: when using SSL Key Logger, ssl_ipport must NOT include key file path. For localhost keys, add lo to interface. Kamailio requires three libraries in LD_PRELOAD. FreeSWITCH requires User=root in systemd service file with -u/-g flags in ExecStart for DTLS+SRTP decryption to work. High traffic: use TCP mode or increase ssl_sessionkey_maxwait_ms. Garbled audio = SRTP encryption not codec issue.
Keywords: tls, ssl, srtp, dtls, decryption, sslkeylog, ld_preload, session key, asterisk, kamailio, freeswitch, ssl_ipport, ssl_sessionkey_udp, packetbuffer_sender, distributed mode, ribbon sbc, audiocodes, hep, rtpengine, pfs, perfect forward secrecy, garbled audio, dlsym error