Merge pull request #215 from ToMe25/optimize_libs

Optimize devices lua and python lib
This commit is contained in:
Sangar
2022-07-24 13:45:55 +02:00
committed by GitHub
2 changed files with 60 additions and 27 deletions

View File

@@ -107,7 +107,6 @@ local function fillBuffer(bus)
return nil, "timeout"
else
bus.buffer = unistd.read(bus.fd, 1024)
bus.bufferLen = string.len(bus.buffer)
bus.bufferPos = 1
return true
end
@@ -126,7 +125,7 @@ local function readOne(bus)
end
local result = bus.buffer:byte(bus.bufferPos)
if bus.bufferPos >= bus.bufferLen then
if bus.bufferPos >= #bus.buffer then
bus.buffer = nil
else
bus.bufferPos = bus.bufferPos + 1
@@ -139,23 +138,39 @@ local function readMessage(bus)
local value
local message = ""
while true do
value, reason = readOne(bus)
if value == nil then -- error
return value, reason
if not bus.buffer then
local result, status = fillBuffer(bus)
if not result then
return result, status
end
end
value = bus.buffer:sub(bus.bufferPos, -1)
if #message == 0 and value:byte(1) == 0 then
bus.bufferPos = bus.bufferPos + 1
value = value:sub(2, -1)
end
if value:find(message_delimiter) then
value = value:sub(1, value:find(message_delimiter))
bus.bufferPos = bus.bufferPos + #value
if bus.bufferPos > #bus.buffer then
clearBuffer(bus)
end
else
if value == 0 then
if message:match("%S") ~= nil then
local ok, result = pcall(cjson.decode, message)
if ok then
return result
else
return nil, result
end
else
message = ""
end
clearBuffer(bus)
end
message = message .. value
if message:byte(-1) == 0 then
message = message:sub(1, -2)
local ok, result = pcall(cjson.decode, message)
if ok then
return result
else
message = message .. string.char(value)
return nil, result
end
end
end

View File

@@ -109,20 +109,36 @@ class DeviceBus:
def _read_message(self, expected_type):
message = ""
while True:
value = chr(self._read_one())
if value == self.MESSAGE_DELIMITER:
if message:
data = json.loads(message)
if data["type"] != expected_type:
raise Exception("unexpected message type: %s" % data["type"])
if self.buffer is None:
self._fill_buffer()
value = self.buffer.decode()[self.buffer_pos:]
if len(message) == 0 and value[0] == self.MESSAGE_DELIMITER:
self.buffer_pos += 1
value = value[1:]
if value.find(self.MESSAGE_DELIMITER) != -1:
value = value[:value.find(self.MESSAGE_DELIMITER) + 1]
self.buffer_pos += len(value)
if self.buffer_pos >= len(self.buffer):
self._clear_buffer()
else:
self._clear_buffer()
message += value
if message[-1] == self.MESSAGE_DELIMITER:
data = json.loads(message)
if data["type"] == expected_type:
if "data" in data:
return data["data"]
else:
return
elif data["type"] == "error":
raise Exception(data["data"])
else:
message = ""
else:
message += value
raise Exception("unexpected message type: %s" % data["type"])
def _read_one(self):
if self.buffer is None:
@@ -146,8 +162,10 @@ class DeviceBus:
# This is horrible, but don't know how to know how many bytes are available,
# so reading one by one is necessary to avoid blocking.
data = bytearray()
while len(data) < limit and len(self.poll.poll(0)) > 0:
bytesRead = 0
while bytesRead < limit and len(self.poll.poll(0)) > 0:
data.extend(self.file.read(1))
bytesRead += 1
return data
def _skip_input(self):