Posted June 18th 2025
This post is about generating signalling from scratch, allowing arbitrary packet generation. It's the third part in a series about different ways to put signalling on an E1/T1 line in the lab. The three parts are:
The post is based around Python code which transmits the packets, 'transmit_ss7.py', in the sample code which includes code in Python and C. The Python code transmits SS7 in all three of the major ways SS7 can be transmitted over an E1/T1 line: SS7 over ATM at 1536 kbit/s, SS7 over MTP-2 at 1536 kbit/s and then ordinary SS7 over 64 kbit/s MTP-2. Each one is transmitted for a few seconds.
We're using an E1/T1 Messenger 3.0 with a loopback cable between P4 and P5:
SS7 over ATM is specified in ITU-T Q.2110, Q.2111 and Q.2210. SS7 messages are sent from a lightly modified version of MTP-3 ("MTP-3b") over ATM AAL5. The Python code takes a couple of shortcuts: Instead of implementing AAL5, it uses hardcoded cells taken from unpublished test code. Instead of implementing the state machine from Q.2110 for link start-up, it just jumps in and starts transmitting.
To see the code running, set up some monitoring so we can observe the signalling we generate after it's taken a trip through the T1 cable. 'save_to_pcap' is in the same sample code repository as the Python code:
./save_to_pcap -l -p aal5 -a 0:5 172.16.1.10 4A 1-24 aal5_capture.pcapng monitoring 4A:1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24 interface_id=0 capturing packets, press ^C to abort
Leave that code running in a window, it's going to capture packets which we send later.
The -l switch means 'assume layer 1 is already set up'.
-p aal5 and -a 0:5 means we want to decode AAL5 on VPI:VCI 0:5.
172.16.1.10 is the IP of the Corelatus hardware.
4A identifies the T1 interface, and 1-24 the timeslots.
To enable the T1 interfaces and run the Python code to transmit the SS7 signalling:
./gth.py 172.16.1.10 enable pcm4A mode T1 ./gth.py 172.16.1.10 enable pcm5A mode T1 ./transmit_ss7.py 172.16.1.10 5A
The 'save_to_pcap' code we ran as the first step will show some status changes:
Mon Jun 23 15:15:14 2025 event: l1 message: name=pcm4A state=LFA Mon Jun 23 15:15:14 2025 event: l1 message: name=pcm5A state=LFA Mon Jun 23 15:15:14 2025 event: l1 message: name=pcm4A state=OK Mon Jun 23 15:15:14 2025 event: l1 message: name=pcm5A state=OK Mon Jun 23 15:22:10 2025 signalling job at5m4138 changed state to 'sync' Mon Jun 23 15:22:12 2025 signalling job at5m4138 changed state to 'hunt'
The signalling is now in 'aal5_capture.pcapng_00001'. Wireshark can display it in a GUI, tshark shows it as text:
tshark -r ../c/aal5_capture.pcapng_00001 1 0.000 DCE → DTE SSCOP 33 Resynchronization
MTP-2 (ITU-T Q.703) has two main variants. The classic version sends the signalling on one 64 kbit/s timeslot. Then, Annex A provides an option to use all timeslots and thus send 1536 kbit/s on T1 or 1984 kbit/s on E1.
The API command 'fr_layer' does the actual transmission work: bit-stuffing, appending the frame-check-sequence (CRC) and delimiting the packet with flags. It also automatically repeats FISUs or LSSUs when there's nothing else to send.
To capture the signalling, use one of these two commands:
./save_to_pcap -l 172.16.1.10 4A 1-24 mtp2_high_speed.pcapng ./save_to_pcap -l 172.16.1.10 4A 1 mtp2_64kbit.pcapng
To transmit the signalling:
./gth.py 172.16.1.10 enable pcm4A mode T1 ./gth.py 172.16.1.10 enable pcm5A mode T1 ./transmit_ss7.py 172.16.1.10 pcm5A
The Python code sends two LSSUs, two MSUs and finally a FISU. Like the ATM code, it takes some shortcuts, e.g. it doesn't implement the state machines for starting up the link ("alignment") and retransmitting packets ("signal units").
'save_to_pcap' shows the status changes which happen when layer 1 is enabled and the Python code sends layer 2 packets:
Mon Jun 23 15:33:26 2025 signalling job m2mo4139 changed state to 'out of service' Mon Jun 23 15:33:26 2025 signalling job m2mo4139 changed state to 'in service' Mon Jun 23 15:33:30 2025 signalling job m2mo4139 changed state to 'no signal units'
The resulting PCAP (Wireshark) file shows the five packets we sent:
tshark -r mtp2_high_speed.pcapng_00001 1 0.000 → MTP2 6 SIO 2 1.000 → MTP2 6 SIN 3 2.003 5577 → 12099 MTP3MG (Int. ITU) 25 Unknown 4 2.008 1 → 2 ISUP(ITU) 39 IAM (CIC 14) 5 2.008 → MTP2 5 FISU
Permalink | Tags: GTH, telecom-signalling