<p>fixeria <strong>merged</strong> this change.</p><p><a href="https://gerrit.osmocom.org/c/osmocom-bb/+/14576">View Change</a></p><div style="white-space:pre-wrap">Approvals:
Jenkins Builder: Verified
pespin: Looks good to me, but someone else must approve
fixeria: Looks good to me, approved
Hoernchen: Looks good to me, but someone else must approve
</div><pre style="font-family: monospace,monospace; white-space: pre-wrap;">trx_toolkit/data_msg.py: implement header version coding<br><br>It may be necessary to extend the message specific header with<br>more information. Since this is not a TLV-based protocol, we<br>need to include the header format version.<br><br> +-----------------+------------------------+<br> | 7 6 5 4 3 2 1 0 | bit numbers |<br> +-----------------+------------------------+<br> | X X X X . . . . | header version (0..15) |<br> +-----------------+------------------------+<br> | . . . . . X X X | TDMA TN (0..7) |<br> +-----------------+------------------------+<br> | . . . . X . . . | RESERVED (0) |<br> +-----------------+------------------------+<br><br>Instead of prepending an additional byte, it was decided to use<br>4 MSB bits of the first octet, which used to be zero-initialized<br>due to the value range of TDMA TN. Therefore, the current header<br>format has implicit version 0x00.<br><br>Otherwise Wireshark (or trx_sniff.py) would need to guess the<br>header version, or alternatively follow the control channel<br>looking for the version setting command.<br><br>The reserved bit number 3 can be used in the future to extend<br>the TDMA TN range to (0..15), in case anybody would need<br>to transfer UMTS bursts.<br><br>Change-Id: Idb0377d66290eb9c15d6998a5806a84fa2e5dd02<br>Related: OS#4006<br>---<br>M src/target/trx_toolkit/data_msg.py<br>1 file changed, 115 insertions(+), 15 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/src/target/trx_toolkit/data_msg.py b/src/target/trx_toolkit/data_msg.py</span><br><span>index 86d0827..5bd04ca 100644</span><br><span>--- a/src/target/trx_toolkit/data_msg.py</span><br><span>+++ b/src/target/trx_toolkit/data_msg.py</span><br><span>@@ -4,7 +4,7 @@</span><br><span> # TRX Toolkit</span><br><span> # DATA interface message definitions and helpers</span><br><span> #</span><br><span style="color: hsl(0, 100%, 40%);">-# (C) 2018 by Vadim Yanitskiy <axilirator@gmail.com></span><br><span style="color: hsl(120, 100%, 40%);">+# (C) 2018-2019 by Vadim Yanitskiy <axilirator@gmail.com></span><br><span> #</span><br><span> # All Rights Reserved</span><br><span> #</span><br><span>@@ -49,20 +49,55 @@</span><br><span> parent of both DATAMSG_L12TRX and DATAMSG_TRX2L2 (see below),</span><br><span> and has the following fields:</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">- +--------------+-------------------+</span><br><span style="color: hsl(0, 100%, 40%);">- | TN (1 octet) | FN (4 octets, BE) |</span><br><span style="color: hsl(0, 100%, 40%);">- +--------------+-------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+----------------+-------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+ | VER (1/2 octet) | TN (1/2 octet) | FN (4 octets, BE) |</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+----------------+-------------------+</span><br><span> </span><br><span> where:</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">- - TN is TDMA time-slot number (1 octet), and</span><br><span style="color: hsl(120, 100%, 40%);">+ - VER is the header version indicator (1/2 octet MSB),</span><br><span style="color: hsl(120, 100%, 40%);">+ - TN is TDMA time-slot number (1/2 octet LSB), and</span><br><span> - FN is TDMA frame number (4 octets, big endian).</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+ == Header version indication</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ It may be necessary to extend the message specific header</span><br><span style="color: hsl(120, 100%, 40%);">+ with more information. Since this is not a TLV-based</span><br><span style="color: hsl(120, 100%, 40%);">+ protocol, we need to include the header format version.</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+------------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+ | 7 6 5 4 3 2 1 0 | bit numbers |</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+------------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+ | X X X X . . . . | header version (0..15) |</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+------------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+ | . . . . . X X X | TDMA TN (0..7) |</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+------------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+ | . . . . X . . . | RESERVED (0) |</span><br><span style="color: hsl(120, 100%, 40%);">+ +-----------------+------------------------+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ Instead of prepending an additional byte, it was decided to use</span><br><span style="color: hsl(120, 100%, 40%);">+ 4 MSB bits of the first octet, which used to be zero-initialized</span><br><span style="color: hsl(120, 100%, 40%);">+ due to the value range of TDMA TN. Therefore, the legacy header</span><br><span style="color: hsl(120, 100%, 40%);">+ format has implicit version 0x00.</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ Otherwise Wireshark (or trx_sniff.py) would need to guess the</span><br><span style="color: hsl(120, 100%, 40%);">+ header version, or alternatively follow the control channel</span><br><span style="color: hsl(120, 100%, 40%);">+ looking for the version setting command.</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ The reserved bit number 3 can be used in the future to extend</span><br><span style="color: hsl(120, 100%, 40%);">+ the TDMA TN range to (0..15), in case anybody would need</span><br><span style="color: hsl(120, 100%, 40%);">+ to transfer UMTS bursts.</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> """</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+ # NOTE: up to 16 versions can be encoded</span><br><span style="color: hsl(120, 100%, 40%);">+ CHDR_VERSION_MAX = 0b1111</span><br><span style="color: hsl(120, 100%, 40%);">+ known_versions = [0x00]</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> # Common constructor</span><br><span style="color: hsl(0, 100%, 40%);">- def __init__(self, fn = None, tn = None, burst = None):</span><br><span style="color: hsl(120, 100%, 40%);">+ def __init__(self, fn = None, tn = None, burst = None, ver = 0):</span><br><span> self.burst = burst</span><br><span style="color: hsl(120, 100%, 40%);">+ self.ver = ver</span><br><span> self.fn = fn</span><br><span> self.tn = tn</span><br><span> </span><br><span>@@ -103,6 +138,9 @@</span><br><span> def desc_hdr(self):</span><br><span> result = ""</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+ if self.ver > 0:</span><br><span style="color: hsl(120, 100%, 40%);">+ result += ("ver=%u " % self.ver)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> if self.fn is not None:</span><br><span> result += ("fn=%u " % self.fn)</span><br><span> </span><br><span>@@ -156,6 +194,9 @@</span><br><span> </span><br><span> # Validates the message fields</span><br><span> def validate(self):</span><br><span style="color: hsl(120, 100%, 40%);">+ if not self.ver in self.known_versions:</span><br><span style="color: hsl(120, 100%, 40%);">+ return False</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> if self.burst is None:</span><br><span> return False</span><br><span> </span><br><span>@@ -185,10 +226,10 @@</span><br><span> # Allocate an empty byte-array</span><br><span> buf = bytearray()</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">- # Put timeslot index</span><br><span style="color: hsl(0, 100%, 40%);">- buf.append(self.tn)</span><br><span style="color: hsl(120, 100%, 40%);">+ # Put version (4 bits) and TDMA TN (3 bits)</span><br><span style="color: hsl(120, 100%, 40%);">+ buf.append((self.ver << 4) | (self.tn & 0x07))</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">- # Put frame number (4 octets, BE)</span><br><span style="color: hsl(120, 100%, 40%);">+ # Put TDMA FN (4 octets, BE)</span><br><span> buf += struct.pack(">L", self.fn)</span><br><span> </span><br><span> # Generate message specific header part</span><br><span>@@ -214,9 +255,12 @@</span><br><span> if length < (self.HDR_LEN + GSM_BURST_LEN):</span><br><span> raise ValueError("Message is to short")</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">- # Parse both fn and tn</span><br><span style="color: hsl(120, 100%, 40%);">+ # Parse version and TDMA TN</span><br><span style="color: hsl(120, 100%, 40%);">+ self.ver = (msg[0] >> 4)</span><br><span style="color: hsl(120, 100%, 40%);">+ self.tn = (msg[0] & 0x07)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Parse TDMA FN</span><br><span> self.fn = struct.unpack(">L", msg[1:5])[0]</span><br><span style="color: hsl(0, 100%, 40%);">- self.tn = msg[0]</span><br><span> </span><br><span> # Specific message part</span><br><span> self.parse_hdr(msg)</span><br><span>@@ -332,9 +376,10 @@</span><br><span> self.burst.append(ubit)</span><br><span> </span><br><span> # Transforms this message to TRX2L1 message</span><br><span style="color: hsl(0, 100%, 40%);">- def gen_trx2l1(self):</span><br><span style="color: hsl(120, 100%, 40%);">+ def gen_trx2l1(self, ver = None):</span><br><span> # Allocate a new message</span><br><span style="color: hsl(0, 100%, 40%);">- msg = DATAMSG_TRX2L1(fn = self.fn, tn = self.tn)</span><br><span style="color: hsl(120, 100%, 40%);">+ msg = DATAMSG_TRX2L1(fn = self.fn, tn = self.tn,</span><br><span style="color: hsl(120, 100%, 40%);">+ ver = self.ver if ver is None else ver)</span><br><span> </span><br><span> # Convert burst bits</span><br><span> if self.burst is not None:</span><br><span>@@ -501,9 +546,10 @@</span><br><span> self.burst.append(sbit)</span><br><span> </span><br><span> # Transforms this message to L12TRX message</span><br><span style="color: hsl(0, 100%, 40%);">- def gen_l12trx(self):</span><br><span style="color: hsl(120, 100%, 40%);">+ def gen_l12trx(self, ver = None):</span><br><span> # Allocate a new message</span><br><span style="color: hsl(0, 100%, 40%);">- msg = DATAMSG_L12TRX(fn = self.fn, tn = self.tn)</span><br><span style="color: hsl(120, 100%, 40%);">+ msg = DATAMSG_L12TRX(fn = self.fn, tn = self.tn,</span><br><span style="color: hsl(120, 100%, 40%);">+ ver = self.ver if ver is None else ver)</span><br><span> </span><br><span> # Convert burst bits</span><br><span> if self.burst is not None:</span><br><span>@@ -618,3 +664,57 @@</span><br><span> assert(msg_trx2l1_dec.burst == DATAMSG.ubit2sbit(msg_l12trx_ref.burst))</span><br><span> </span><br><span> log.info("Check L12TRX <-> TRX2L1 type transformations: OK")</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Test header version coding</span><br><span style="color: hsl(120, 100%, 40%);">+ for ver in DATAMSG.known_versions:</span><br><span style="color: hsl(120, 100%, 40%);">+ # Create messages of both types</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx = DATAMSG_L12TRX(ver = ver)</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1 = DATAMSG_TRX2L1(ver = ver)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Randomize message specific headers</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx.rand_hdr()</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1.rand_hdr()</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Randomize bursts</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx.rand_burst()</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1.rand_burst()</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Encode DATA messages</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx_enc = msg_l12trx.gen_msg()</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1_enc = msg_trx2l1.gen_msg()</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Parse generated DATA messages</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx_dec = DATAMSG_L12TRX()</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1_dec = DATAMSG_TRX2L1()</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx_dec.parse_msg(msg_l12trx_enc)</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1_dec.parse_msg(msg_trx2l1_enc)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Match the header version</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_l12trx_dec.ver == ver)</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_trx2l1_dec.ver == ver)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Match common TDMA fields</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_l12trx_dec.tn == msg_l12trx.tn)</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_trx2l1_dec.fn == msg_trx2l1.fn)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Compare bursts</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_l12trx_dec.burst == msg_l12trx.burst)</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_trx2l1_dec.burst == msg_trx2l1.burst)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ log.info("Check header version %u coding: OK" % ver)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_trx2l1_gen = msg_l12trx.gen_trx2l1()</span><br><span style="color: hsl(120, 100%, 40%);">+ msg_l12trx_gen = msg_trx2l1.gen_l12trx()</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_trx2l1_gen is not None)</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_l12trx_gen is not None)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Match the header version</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_trx2l1_gen.ver == ver)</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_l12trx_gen.ver == ver)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ # Match common TDMA fields</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_trx2l1_gen.tn == msg_l12trx.tn)</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(msg_l12trx_gen.fn == msg_trx2l1.fn)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ log.info("Verify direct transformation: OK")</span><br><span></span><br></pre><p>To view, visit <a href="https://gerrit.osmocom.org/c/osmocom-bb/+/14576">change 14576</a>. To unsubscribe, or for help writing mail filters, visit <a href="https://gerrit.osmocom.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://gerrit.osmocom.org/c/osmocom-bb/+/14576"/><meta itemprop="name" content="View Change"/></div></div>
<div style="display:none"> Gerrit-Project: osmocom-bb </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-Change-Id: Idb0377d66290eb9c15d6998a5806a84fa2e5dd02 </div>
<div style="display:none"> Gerrit-Change-Number: 14576 </div>
<div style="display:none"> Gerrit-PatchSet: 4 </div>
<div style="display:none"> Gerrit-Owner: fixeria <axilirator@gmail.com> </div>
<div style="display:none"> Gerrit-Reviewer: Hoernchen <ewild@sysmocom.de> </div>
<div style="display:none"> Gerrit-Reviewer: Jenkins Builder </div>
<div style="display:none"> Gerrit-Reviewer: fixeria <axilirator@gmail.com> </div>
<div style="display:none"> Gerrit-Reviewer: laforge <laforge@gnumonks.org> </div>
<div style="display:none"> Gerrit-Reviewer: pespin <pespin@sysmocom.de> </div>
<div style="display:none"> Gerrit-MessageType: merged </div>