From 9b207419105c5e07504b1b7bf380eda07c127bb2 Mon Sep 17 00:00:00 2001 From: Alexander Couzens Date: Mon, 27 May 2019 03:44:39 +0200 Subject: utils: add gsmtap_logread.py a gsmtap log reader Receive gsmtap logs and feeds it into the python logging framework. Allows to use generic logging features and further utilities. Change-Id: I24478d8e16066c6118e867bdba54c6418c15e170 --- utils/gsmtap.py | 75 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 75 insertions(+) create mode 100644 utils/gsmtap.py (limited to 'utils/gsmtap.py') diff --git a/utils/gsmtap.py b/utils/gsmtap.py new file mode 100644 index 00000000..b7211adf --- /dev/null +++ b/utils/gsmtap.py @@ -0,0 +1,75 @@ +#!/usr/bin/env python +# License: MIT +# Copyright 2019 by Sysmocom s.f.m.c. GmbH +# Author: Alexander Couzens + +import struct + +GSMTAP_VERSION = 0x02 + +GSMTAP_TYPE_OSMOCORE_LOG = 0x10 + +class TooSmall(RuntimeError): + pass + +# struct gsmtap_hdr { +# uint8_t version; /*!< version, set to 0x01 currently */ +# uint8_t hdr_len; /*!< length in number of 32bit words */ +# uint8_t type; /*!< see GSMTAP_TYPE_* */ +# uint8_t timeslot; /*!< timeslot (0..7 on Um) */ +# +# uint16_t arfcn; /*!< ARFCN (frequency) */ +# int8_t signal_dbm; /*!< signal level in dBm */ +# int8_t snr_db; /*!< signal/noise ratio in dB */ +# +# uint32_t frame_number; /*!< GSM Frame Number (FN) */ +# +# uint8_t sub_type; /*!< Type of burst/channel, see above */ +# uint8_t antenna_nr; /*!< Antenna Number */ +# uint8_t sub_slot; /*!< sub-slot within timeslot */ +# uint8_t res; /*!< reserved for future use (RFU) */ +# +# } + +class gsmtap_hdr(): + def __init__(self, data): + if len(data) < 2: + raise TooSmall() + self.version, self.hdr_len = struct.unpack('!BB', data[0:2]) + self.hdr_len *= 4 + + if self.hdr_len >= 3: + self.type = struct.unpack('!B', data[2:3])[0] + +# /*! Structure of the GSMTAP libosmocore logging header */ +# struct gsmtap_osmocore_log_hdr { +# struct { +# uint32_t sec; +# uint32_t usec; +# } ts; +# char proc_name[16]; /*!< name of process */ +# uint32_t pid; /*!< process ID */ +# uint8_t level; /*!< logging level */ +# uint8_t _pad[3]; +# /* TODO: color */ +# char subsys[16]; /*!< logging sub-system */ +# struct { +# char name[32]; /*!< source file name */ +# uint32_t line_nr;/*!< line number */ +# } src_file; +# } __attribute__((packed)); + +class gsmtap_log(): + def __init__(self, data): + packformat = '!II16sIBxxx16s32sI' + packlen = struct.calcsize(packformat) + if len(data) < packlen: + raise TooSmall() + self.sec, self.usec, \ + self.proc_name, self.pid, \ + self.level, self.subsys, \ + self.filename, self.fileline_nr = struct.unpack(packformat, data[:packlen]) + + message_len = len(data) - packlen + if message_len > 0: + self.message = data[packlen:].decode('utf-8') -- cgit v1.2.3