すいません、
昨日のこれ、修正します。
何が問題なのかというと、複数のスレッドが同じデバイスにアクセスしている、と言うことです。
デバイスにアクセスするときには「一連のアクセス処理」が発生します。
温湿度計にアクセスする場合は、I2Cインターフェースを使用しているので、データの要求・応答に2つの端子にパルスパターンを送受信しているはずです。
この処理を複数のスレッドで同時に行った場合、正しくアクセス処理が行われない場合があります。
アクセス処理が競合しちゃうんですね。
これを防ぐために、こういったマルチスレッドのプログラミングでは「待ち合わせ処理」(一方の処理が完了するまで、もう一方の処理を待つ)というのが必要なのですが、
今回は規模が小さいので、アクセスを行うスレッドを一つだけ(メインのスレッドのみ)にして、他のスレッドからはデバイスにアクセスしないようにします。
Humidity = 0
Temperature = 0
def __main__():
global sw
global Humidity
global Temperature
GPIO.setmode(GPIO.BCM)
GPIO.setup(22,GPIO.IN)
GPIO.add_event_detect(22, GPIO.FALLING, callback=callback, bouncetime=300)
GLCD.PinsInit(20, 7, 8, 9, 18, 19, 10, 11, 12, 13, 14, 15, 16, 17)
GLCD.GLCDInit()
GLCD.GLCDDisplayClear()
roop = 10 * 60 * 60
mode = 1
thread = threading.Thread(target=httpServe)
thread.start()
try:
while True:
Humidity = AM2320.GetHum()
Temperature = AM2320.GetTemp()
if sw == True:
GLCD.GLCDDisplayClear()
mode += 1
if mode > 4:
mode = 1
sw = False
if mode == 1:
if roop >= 10 * 60 * 60:
GLCD.GLCDDisplayClear()
Weather.RequestAPI()
weather = Weather.GetWeather()
temp = Weather.GetTemp()
roop = 0
GLCD.GLCDPuts(1, 0, "Date :")
GLCD.GLCDPuts(5, 8, datetime.datetime.now().strftime('%Y:%m:%d %A '))
GLCD.GLCDPuts(1, 16, "Weather :")
GLCD.GLCDPuts(10,24, weather)
GLCD.GLCDPuts(10,32, "Temp : " + format(temp) + 'C')
GLCD.GLCDPuts(1, 40, "Time : " + datetime.datetime.now().strftime('%H:%M'))
GLCD.GLCDPuts(1, 48, "Humidity : " + Humidity + '%')
GLCD.GLCDPuts(1, 56, "Temperature : " + Temperature + 'C')
roop += 1
#中略
time.sleep(1)
except KeyboardInterrupt:
GLCD.GLCDDisplayClear()
GPIO.cleanup()
#中略
class StubHttpRequestHandler(BaseHTTPRequestHandler):
server_version = "HTTP Stub/0.1"
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
def do_GET(self):
enc = sys.getfilesystemencoding()
data = {
'datetime' : datetime.datetime.now().strftime('%Y:%m:%d %H:%M:%S'),
'temperature': Temperature,
'humidity': Humidity,
}
encoded = json.dumps(data).encode()
self.send_response(HTTPStatus.OK)
self.send_header("Content-type", "text/html; charset=%s" % enc)
self.send_header("Content-Length", str(len(encoded)))
self.end_headers()
self.wfile.write(encoded)
__main__()
これで競合は回避できるはず。
「【ラズパイ】【いろいろ計測モニター】HTTPサーバを実装する(修正)」への1件のフィードバック