Multiple Data length receive from Socket streaming Server - PYTHON3 - sockets

I'm intermittent to python, I'm using socket module to receive market data and Order data from Broker Application via API. I'm still confusing how to code for receiving the multiple data length and header, based on the header info, I will treat the data.
How to receive multiple Data length and decide to unpack with correct struct format function?
while True:
try:
"""
continously receive data from Server API (stock Market data streaming)
"""
brecvd = self.sock.recv(1024)
self.brecvdsize = len(brecvd)
# Unpack the header for correct struct formate to unpack
unpkr = self.struct.Struct('<lh')
recvd =self.struct.Struct.unpack_from(unpkr, brecvd)
Marketdepth = recvd[0] == 284 and recvd[1] == 26
Indices = recvd[0] == 228 and recvd[1] == 27
Feed = recvd[0] == 384 and recvd[1] == 22
BidOffer = recvd[0] == 145 and recvd[1] == 28
Msg = recvd[0] == 360 and recvd[1] == 99
#Msg to be checked for 260 or 360
if Marketdepth:
self.Marketdepthresponse(brecvd)
Marketdepth = False
elif Indices:
self.Indicesresponse(brecvd)
Indices = False
elif Feed:
self.feedresponse(brecvd)
Feed = False
elif BidOffer:
self.Bidoffer(brecvd)
BidOffer = False
elif Msg:
self.GeneralMsg(brecvd)
Msg = False
else:
Marketdepth = False
Indices = False
Feed = False
BidOffer = False
Msg = False
pass
except Exception as e:
self.errorcount += 1
print('***Run Loop Receive Issue: {0}'.format(str(e)))

When you call self.sock.recv(1024) you could recieve anywhere from 0 (socket was closed) to 1024 bytes of data. You may not receive enough data to unpack a complete message, may have to continue receiving and buffering the data until you have a complete message to unpack, and may receive part of the next message as well. TCP is a streaming protocol with no message boundary indicators. A protocol using TCP has to define what a complete message looks like.
Without more details of the protocol, I can only make up a protocol and give an example. This is completely untested but should give you an idea.
Protocol: 4 byte length (big-endian) followed by data bytes.
def get_message(self):
# read the 4-byte length
data = self.get_bytes(4)
if not data:
return None # indicates socket closed
if len(data) < 4:
raise IncompleteMessageError
# process the length and fetch the data
length = struct.unpack('>L',data)
data = self.get_bytes(length)
if len(data) < length:
raise IncompleteMessageError
return data
def get_bytes(self,count):
# buffer data until the requested size is present
while len(self.buffer) < count:
new_data = self.sock.recv(1024)
if not new_data: # socket closed
remaining,self.buffer = self.buffer,b''
return remaining # return whatever is left.
self.buffer += new_data
# split off the requested data from the front of the buffer
data,self.buffer = self.buffer[:count],self.buffer[count:]
return data

Related

dht11 sensor only retuning unexpected number of pulse often

I am trying to make a simple water pump controller using a dth11 to make the pump turn on more frequently when the temperature is higher. i have it working but every 4th or 5th time i call measure on the dht11 sensor i get an error saying "InvalidPulseCount: Expected 82 but got 0 pulses" or "InvalidPulseCount: Got more than 82 pulses". I have added try block that is stopping the program from crashing but would really like to figure out why it is happening. I also had to edit the dht.py lib to have 82 instead of 84 as the default expected pulses because that was what was commonly returned.
here is my main.py file
from machine import Pin
from time import sleep_ms
import dht
import I2C_LCD_driver
sensor = dht.DHT11(Pin(28))
lcd = I2C_LCD_driver.lcd()
pump = Pin(7, machine.Pin.OUT)
counter = 0
pumpTime = 30
normalTime = 60
hotTime = 30
lowTemp = 19
# sensor variables only updated every 3 loops
lastMesure = 1
temp = 0
humid = 0
first = True
while True:
# sensor.messure can only be called ever 3 seconds
# start at 1 and set to zero in the first loop for our first messurement
lastMesure += -1
if lastMesure <= 0:
try:
sensor.measure()
lastMesure = 3
temp = round((sensor.temperature), 0)
humid = sensor.humidity
except:
print("something went wrong")
print("Counter: {:.0f} pumpping:{:0.f}".format(counter, pump.value()))
print("Temp: {:.0f}℃ HUMIDITY: {:.0F}% ".format(temp, humid))
# if the pump is running
if pump.value() == 1:
if counter >= pumpTime: # if it has been the set pump run time
pump.value(0) # turn off pump
counter = 0 # reset counter
else:
counter += 1
else:
# check current temp
# if warmer then {lowTemp} check for {hotTime} else check for {normalTime}
if (temp > lowTemp and counter >= hotTime) or counter >= normalTime:
pump.value(1) # turn on pump
counter = 0 # reset counter
else:
counter += 1
# print current data to the screen
lcd.lcd_clear()
lcd.lcd_display_string("T: {:.0f}C H:{:.0f}%".format(temp, humid), 1)
if pump.value() == 1:
status = f'Pumping {pumpTime - counter}s'
lcd.lcd_display_string(status, 2);
else:
lcd.lcd_display_string("Pump off ", 2)
sleep_ms(1000)
here is a picture of my breadboard set up. I have run it both with and without a 1k pull up resistor on the data pin

how to extract information from a ipv6 packet

I am writing my own packet sniffer using python sockets by retrieving the
packet information such as source ip, source port, destination ip,
destion port, TTL, Flags (SYN, ACK, FIN, RST, PSH, URG) etc.
For IPv4, I am able to unpack the packet based on the respective positions, and the result is similar to what I see with tshark. See code below:
IPv4_UNPACK_PATTERN = '!BBHHHBBH4s4s'
IPv6_UNPACK_PATTERN = '!4sHBB16s16s'
IPv4_HDR_LEN = 20
IPv6_HDR_LEN = 40
TCP_HDR_LEN = 20
ETH_HDR_LEN = 14
# IP ATTRIBUTES
IP_VERSION_POS = 0
IP_TOS_POS = 1
IP_LENGTH_POS = 2
IP_IDENTIFICATION_POS = 3
IP_FRAGMENT_OFFSET_POS = 4
IP_TTL_POS = 5
IP_PROTOCOL_POS = 6
IP_HDR_CHCKSUM_POS = 7
IP_SRC_ADDR_POS = 8
IP_DST_ADDR_POS = 9
TCP_FLAG_POS = 5
TCP_WINDOW_POS = 6
# main program:
s = socket.socket(socket.AF_PACKET, socket.SOCK_RAW, socket.ntohs(0x0003))
packet = s.recvfrom(SOCKET_BUFF_SIZE)
pkt_type = extract_type(packet)
ip_header(packet, pkt_type)
# this function extracts the information from pkt
def ip_header(pkt, pkt_type):
if pkt_type=='ipv4':
data = unpack(IPv4_UNPACK_PATTERN, pkt[ETH_HDR_LEN:ETH_HDR_LEN + IPv4_HDR_LEN])
version = data[IP_VERSION_POS]
total_length = data[IP_LENGTH_POS]
ttl = data[IP_TTL_POS]
protocol = data[IP_PROTOCOL_POS]
ip_header = (version & 0xF) * 4
start_pos = ETH_HDR_LEN + IPv4_HDR_LEN
# Unpacking TCP
tcp_obj = unpack(TCP_UNPACK_PATTERN, data[start_pos:start_pos + TCP_HDR_LEN])
tcp_flag = tcp_obj[TCP_FLAG_POS]
window = str(tcp_obj[TCP_WINDOW_POS])
else: # ipv6
data = unpack(IPv6_UNPACK_PATTERN, pkt[ETH_HDR_LEN:ETH_HDR_LEN + IPv6_HDR_LEN])
# what bit positions to be used here for ipv6?
But for the IPv6 packet, I do not know the correct bit positions for ipv6 fields.
Can anybody point me to the document which describes the bit positions for ipv6 packets for the following fields:
version
ip total length
TTL
protocol
ip header
TCP flags
Window size
Don't fragment bit
More fragment bit

control timeout valus in udp communication matlab

How can I chane the "timeout" value in UDP communication?
I get this warning:
Warning: Unsuccessful read: The specified amount of data was not returned within the Timeout period.
and I want to increase the timeout value so I will not expireance this warning...
To set a timeout, you can use:
u.Timeout=99;
In this case the timeout property is not documented, at least I am unable to find any documentation. When working with unknown or not fully documented objects, I typically try get methods and properties to examine them:
>> methods(x)
Methods for class udp:
Contents eq fscanf instrhelp ne size
binblockread fclose fwrite instrhwinfo obj2mfile stopasync
binblockwrite fgetl get instrnotify open subsasgn
class fgets horzcat instrument openvar subsref
close fieldnames icinterface isa propinfo udp
ctranspose flushinput igetfield isequal query vertcat
delete flushoutput inspect isetfield readasync
disp fopen instrcallback isvalid record
display fprintf instrfind length scanstr
end fread instrfindall methods set
>> properties(x)
No properties for class udp or no class udp.
>> get(x)
ByteOrder = bigEndian
BytesAvailable = 0
BytesAvailableFcn =
BytesAvailableFcnCount = 48
BytesAvailableFcnMode = terminator
BytesToOutput = 0
ErrorFcn =
InputBufferSize = 512
Name = UDP-127.0.0.1
ObjectVisibility = on
OutputBufferSize = 512
OutputEmptyFcn =
RecordDetail = compact
RecordMode = overwrite
RecordName = record.txt
RecordStatus = off
Status = open
Tag =
Timeout = 3
TimerFcn =
TimerPeriod = 1
TransferStatus = idle
Type = udp
UserData = []
ValuesReceived = 0
ValuesSent = 0
UDP specific properties:
DatagramAddress =
DatagramPort = []
DatagramReceivedFcn =
DatagramTerminateMode = on
InputDatagramPacketSize = 512
LocalHost =
LocalPort = 52148
LocalPortMode = auto
OutputDatagramPacketSize = 512
ReadAsyncMode = continuous
RemoteHost = 127.0.0.1
RemotePort = 9090
Terminator = LF
Note that get is not always supported. In case you receive Error using get Conversion to double from A is not possible. the other two methods display everything accessible.

Lua Raw Socket Example

I'm having a hard time finding some example code for Raw Sockets in Lua. Ideally they should look something like they do in Python:
#create a raw socket
try:
s = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.IPPROTO_RAW)
except socket.error , msg:
print 'Socket could not be created. Error Code : ' + str(msg[0]) + ' Message ' + msg[1]
sys.exit()
# tell kernel not to put in headers, since we are providing it, when using IPPROTO_RAW this is not necessary
# s.setsockopt(socket.IPPROTO_IP, socket.IP_HDRINCL, 1)
# now start constructing the packet
packet = '';
source_ip = '192.168.1.101'
dest_ip = '127.0.0.1' # or socket.gethostbyname('www.google.com')
# ip header fields
ip_ihl = 5
ip_ver = 4
ip_tos = 0
ip_tot_len = 0 # kernel will fill the correct total length
ip_id = 54321 #Id of this packet
ip_frag_off = 0
ip_ttl = 255
ip_proto = socket.IPPROTO_TCP
ip_check = 0 # kernel will fill the correct checksum
ip_saddr = socket.inet_aton ( source_ip ) #Spoof the source ip address if you want to
ip_daddr = socket.inet_aton ( dest_ip )
ip_ihl_ver = (ip_ver << 4) + ip_ihl
# the ! in the pack format string means network order
ip_header = pack('!BBHHHBBH4s4s' , ip_ihl_ver, ip_tos, ip_tot_len, ip_id, ip_frag_off, ip_ttl, ip_proto, ip_check, ip_saddr, ip_daddr)
# tcp header fields
tcp_source = 1234 # source port
tcp_dest = 80 # destination port
tcp_seq = 454
tcp_ack_seq = 0
tcp_doff = 5 #4 bit field, size of tcp header, 5 * 4 = 20 bytes
#tcp flags
tcp_fin = 0
tcp_syn = 1
tcp_rst = 0
tcp_psh = 0
tcp_ack = 0
tcp_urg = 0
tcp_window = socket.htons (5840) # maximum allowed window size
tcp_check = 0
tcp_urg_ptr = 0
tcp_offset_res = (tcp_doff << 4) + 0
tcp_flags = tcp_fin + (tcp_syn << 1) + (tcp_rst << 2) + (tcp_psh <<3) + (tcp_ack << 4) + (tcp_urg << 5)
# the ! in the pack format string means network order
tcp_header = pack('!HHLLBBHHH' , tcp_source, tcp_dest, tcp_seq, tcp_ack_seq, tcp_offset_res, tcp_flags, tcp_window, tcp_check, tcp_urg_ptr)
user_data = 'Hello, how are you'
If you guyshave some laying around or know where to find some. I haven't seen much from my google searching.
Thanks,
LuaSocket is not made for this. Maybe look at libpcap and libnet?

Raw Sockets in TCL

I would like to use raw socket implentation in TCl as it is used in Python and C, is this possible? Does the TCL socket library even support raw sockets?
Python Raw Socket Example:
#create a raw socket
try:
s = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.IPPROTO_RAW)
except socket.error , msg:
print 'Socket could not be created. Error Code : ' + str(msg[0]) + ' Message ' + msg[1]
sys.exit()
# tell kernel not to put in headers, since we are providing it, when using IPPROTO_RAW this is not necessary
# s.setsockopt(socket.IPPROTO_IP, socket.IP_HDRINCL, 1)
# now start constructing the packet
packet = '';
source_ip = '192.168.1.101'
dest_ip = '127.0.0.1' # or socket.gethostbyname('www.google.com')
# ip header fields
ip_ihl = 5
ip_ver = 4
ip_tos = 0
ip_tot_len = 0 # kernel will fill the correct total length
ip_id = 54321 #Id of this packet
ip_frag_off = 0
ip_ttl = 255
ip_proto = socket.IPPROTO_TCP
ip_check = 0 # kernel will fill the correct checksum
ip_saddr = socket.inet_aton ( source_ip ) #Spoof the source ip address if you want to
ip_daddr = socket.inet_aton ( dest_ip )
ip_ihl_ver = (ip_ver << 4) + ip_ihl
# the ! in the pack format string means network order
ip_header = pack('!BBHHHBBH4s4s' , ip_ihl_ver, ip_tos, ip_tot_len, ip_id, ip_frag_off, ip_ttl, ip_proto, ip_check, ip_saddr, ip_daddr)
# tcp header fields
tcp_source = 1234 # source port
tcp_dest = 80 # destination port
tcp_seq = 454
tcp_ack_seq = 0
tcp_doff = 5 #4 bit field, size of tcp header, 5 * 4 = 20 bytes
#tcp flags
tcp_fin = 0
tcp_syn = 1
tcp_rst = 0
tcp_psh = 0
tcp_ack = 0
tcp_urg = 0
tcp_window = socket.htons (5840) # maximum allowed window size
tcp_check = 0
tcp_urg_ptr = 0
tcp_offset_res = (tcp_doff << 4) + 0
tcp_flags = tcp_fin + (tcp_syn << 1) + (tcp_rst << 2) + (tcp_psh <<3) + (tcp_ack << 4) + (tcp_urg << 5)
# the ! in the pack format string means network order
tcp_header = pack('!HHLLBBHHH' , tcp_source, tcp_dest, tcp_seq, tcp_ack_seq, tcp_offset_res, tcp_flags, tcp_window, tcp_check, tcp_urg_ptr)
user_data = 'Hello, how are you'
I cut out some parts but you get the idea. Is this possible?
I did some more looking, ceptcl was written to add some Raw socket functionality to Tcl. I will use it if I can't find anything better. http://wiki.tcl.tk/11140