def bytes_to_status(bytes_, status_type): """Convert bytes to trip and digital input statuses """ # The 4 bits for a state is contained i 4 bytes, gather them up into one list all_states = [] for byte_ in bytes_: pay = BinaryPayloadDecoder(byte_) bits_ = pay.decode_bits() # 8 booleans all_states.extend([bits_[:4], bits_[4:]]) # The 3 bit indicates whether status is used, sort out the rest all_states = [state for state in all_states if state[3]] states = {} for state_num, state_bits in enumerate(all_states, start=1): # Enumeration starts at 1 # The first 3 bits has 3 different meanings: on, inhibit and override # First make sure only one is set if sum(state_bits[:3]) > 1: raise ValueError('Bad state: {}'.format(state_bits)) # Then translate, if none is set, default to off for bit_num, bit_meaning in enumerate(['on', 'inhibit', 'override']): if state_bits[bit_num]: states[status_type + str(state_num)] = bit_meaning break else: states[status_type + str(state_num)] = 'off' return states
def bytes_to_status(bytes_, status_type): """Convert bytes to trip and digital input statuses """ # The 4 bits for a state is contained i 4 bytes, gather them up into one list all_states = [] for byte_ in bytes_: pay = BinaryPayloadDecoder(byte_) bits_ = pay.decode_bits() # 8 booleans all_states.extend([bits_[:4], bits_[4:]]) # The 3 bit indicates whether status is used, sort out the rest all_states = [state for state in all_states if state[3]] states = {} for state_num, state_bits in enumerate(all_states, start=1): # Enumeration starts at 1 # The first 3 bits has 3 different meanings: on, inhibit and override # First make sure only one is set if sum(state_bits[:3]) > 1: raise ValueError('Bad state: {}'.format(state_bits)) # Then translate, if none is set, default to off for bit_num, bit_meaning in enumerate(['on', 'inhibit', 'override']): if state_bits[bit_num]: states[status_type + str(state_num)] = bit_meaning break else: states[status_type + str(state_num)] = 'off' return states
def testBigEndianPayloadDecoder(self): ''' Test basic bit message encoding/decoding ''' decoder = BinaryPayloadDecoder(self.big_endian_payload, endian=Endian.Big) self.assertEqual(1, decoder.decode_8bit_uint()) self.assertEqual(2, decoder.decode_16bit_uint()) self.assertEqual(3, decoder.decode_32bit_uint()) self.assertEqual(4, decoder.decode_64bit_uint()) self.assertEqual(-1, decoder.decode_8bit_int()) self.assertEqual(-2, decoder.decode_16bit_int()) self.assertEqual(-3, decoder.decode_32bit_int()) self.assertEqual(-4, decoder.decode_64bit_int()) self.assertEqual(1.25, decoder.decode_32bit_float()) self.assertEqual(6.25, decoder.decode_64bit_float()) self.assertEqual(b'test', decoder.decode_string(4)) self.assertEqual(self.bitstring, decoder.decode_bits())
def testLittleEndianPayloadDecoder(self): """ Test basic bit message encoding/decoding """ decoder = BinaryPayloadDecoder(self.little_endian_payload, endian=Endian.Little) self.assertEqual(1, decoder.decode_8bit_uint()) self.assertEqual(2, decoder.decode_16bit_uint()) self.assertEqual(3, decoder.decode_32bit_uint()) self.assertEqual(4, decoder.decode_64bit_uint()) self.assertEqual(-1, decoder.decode_8bit_int()) self.assertEqual(-2, decoder.decode_16bit_int()) self.assertEqual(-3, decoder.decode_32bit_int()) self.assertEqual(-4, decoder.decode_64bit_int()) self.assertEqual(1.25, decoder.decode_32bit_float()) self.assertEqual(6.25, decoder.decode_64bit_float()) self.assertEqual("test", decoder.decode_string(4)) self.assertEqual(self.bitstring, decoder.decode_bits())
def testLittleEndianPayloadDecoder(self): ''' Test basic bit message encoding/decoding ''' decoder = BinaryPayloadDecoder(self.little_endian_payload, endian=Endian.Little) self.assertEqual(1, decoder.decode_8bit_uint()) self.assertEqual(2, decoder.decode_16bit_uint()) self.assertEqual(3, decoder.decode_32bit_uint()) self.assertEqual(4, decoder.decode_64bit_uint()) self.assertEqual(-1, decoder.decode_8bit_int()) self.assertEqual(-2, decoder.decode_16bit_int()) self.assertEqual(-3, decoder.decode_32bit_int()) self.assertEqual(-4, decoder.decode_64bit_int()) self.assertEqual(1.25, decoder.decode_32bit_float()) self.assertEqual(6.25, decoder.decode_64bit_float()) self.assertEqual(None, decoder.skip_bytes(2)) self.assertEqual('test', decoder.decode_string(4).decode()) self.assertEqual(self.bitstring, decoder.decode_bits())
def testLittleEndianPayloadDecoder(self): """ Test basic bit message encoding/decoding """ decoder = BinaryPayloadDecoder(self.little_endian_payload, byteorder=Endian.Little, wordorder=Endian.Little) self.assertEqual(1, decoder.decode_8bit_uint()) self.assertEqual(2, decoder.decode_16bit_uint()) self.assertEqual(3, decoder.decode_32bit_uint()) self.assertEqual(4, decoder.decode_64bit_uint()) self.assertEqual(-1, decoder.decode_8bit_int()) self.assertEqual(-2, decoder.decode_16bit_int()) self.assertEqual(-3, decoder.decode_32bit_int()) self.assertEqual(-4, decoder.decode_64bit_int()) self.assertEqual(1.25, decoder.decode_32bit_float()) self.assertEqual(6.25, decoder.decode_64bit_float()) self.assertEqual(None, decoder.skip_bytes(2)) self.assertEqual('test', decoder.decode_string(4).decode()) self.assertEqual(self.bitstring, decoder.decode_bits())
def decode(self, raw, size, mb_type, mb_funcall=3): log.debug('decode param (raw=%s, size=%s, mb_type=%s, mb_funcall=%s)' % (raw, size, mb_type, mb_funcall)) if mb_funcall == 1: # Read Coil Status (FC=01) log.debug("decoder FC1 (raw: %s)" % raw) decoder = BinaryPayloadDecoder.fromCoils(raw, endian=self.endian) elif mb_funcall == 2: # Read Discrete Input (FC=02) log.debug("decoder FC2 (raw: %s)" % raw) decoder = BinaryPayloadDecoder(raw, endian=self.endian) elif mb_funcall == 3: # Read Holding Registers (FC=03) log.debug("decoder FC3 (raw: %s)" % raw) decoder = BinaryPayloadDecoder.fromRegisters(raw, endian=self.endian) elif mb_funcall == 4: # Read Input Registers (FC=04) log.debug("decoder stub FC4 (raw: %s)" % raw) decoder = BinaryPayloadDecoder(raw, endian=self.endian) else: log.debug("Function call not supported: %s" % mb_funcall) decoder = None result = "" if mb_type == 'bitmap': if size == 1: mb_type = 'int8' elif size == 2: mb_type = 'int16' elif size == 2: mb_type = 'int32' elif size == 4: mb_type = 'int64' if decoder is None: log.debug("decode none") result = raw else: try: if mb_type == 'string' or mb_type == 'utf8': result = decoder.decode_string(size) #elif mb_type == 'bitmap': # result = decoder.decode_string(size) elif mb_type == 'datetime': result = decoder.decode_string(size) elif mb_type == 'uint8': result = int(decoder.decode_8bit_uint()) elif mb_type == 'int8': result = int(decoder.decode_8bit_int()) elif mb_type == 'uint16': result = int(decoder.decode_16bit_uint()) elif mb_type == 'int16': result = int(decoder.decode_16bit_int()) elif mb_type == 'uint32': result = int(decoder.decode_32bit_uint()) elif mb_type == 'int32': result = int(decoder.decode_32bit_int()) elif mb_type == 'uint64': result = int(decoder.decode_64bit_uint()) elif mb_type == 'int64': result = int(decoder.decode_64bit_int()) elif mb_type == 'float32' or mb_type == 'float': result = float(decoder.decode_32bit_float()) elif mb_type == 'float64': result = float(decoder.decode_64bit_float()) elif mb_type == 'bit': result = int(decoder.decode_bits()) elif mb_type == 'bool': result = bool(raw[0]) elif mb_type == 'raw': result = raw[0] else: result = raw except ValueError as e: log.exception(e) result = raw return result