Reputation: 1
I am part of a student organization called "Formula Electric Belgium". As part of my project, I must establish communication between two modules. While researching my options, I stumbled upon ESPNOW, a communication protocol developed for the ESP32. So I bought myself two ESP32 WROOM developerboards and started experimenting. After a while, I had working communication. However, every once in a while I had a ValueError (ValueError: ESPNow.recv(): buffer error). This error is unpredictable and almost seems random.
At first, I tried to directly solve the problem and take a look in the espnow library code. However, this code was too complex and I couldn't find anything concerning a buffer. So I tried to solve the problem by simply avoiding it. This tactic works 99% of the time. But the more I work on the project, the more the error keeps returning. I think it would be more efficient to solve the problem instead of avoiding it. Following you'll find the code I've written for both microcontrollers.
ESP32-1:
### set-up ###
import network
from machine import Pin, Timer, reset
import espnow
from time import sleep
sta = network.WLAN(network.STA_IF)
sta.active(True)
esp = espnow.ESPNow()
esp.active(True)
peer = b'\xa0\xb7e\xdd\x13\x14'
esp.add_peer(peer)
### variables ###
time_now = 0
time_start = 0
time_stop = 0
time_delta = 0
timer = Timer(1)
button = Pin(13, Pin.IN)
x = False
### functions ###
def time(timer):
global time_now
time_now += 1
### main ###
timer.init(period=1,mode=Timer.PERIODIC, callback=time)
while True:
if button.value():
sleep(0.2)
if not button.value():
esp.send(peer, 'start')
time_start = time_now
Pin(2, Pin.OUT).on()
x = True
try:
while x:
_, msg = esp.irecv()
if msg == b'stop':
time_stop = time_now
Pin(2, Pin.OUT).off()
x = False
time_delta = float((time_stop - time_start)/1000)
esp.send(peer, str(time_delta))
except ValueError:
print("ValueError")
reset()
ESP32-2:
### set-up ###
import network
from machine import Pin, Timer, SoftI2C
import espnow
from time import sleep
import sh1106
sta = network.WLAN(network.STA_IF)
sta.active(True)
esp = espnow.ESPNow()
esp.active(True)
peer = b'|\x9e\xbda\x81\xcc'
esp.add_peer(peer)
i2c = SoftI2C(scl=Pin(22), sda=Pin(21))
oled = sh1106.SH1106_I2C(128, 64, i2c, Pin(16), 0x3c)
### variables ###
time_now = 0
time_start = 0
time_stop = 0
time_delta = 0
timer = Timer(1)
button = Pin(13, Pin.IN)
x = True
a = 0
### functions ###
def time(timer):
global time_now
time_now += 1
def display(time, a, error):
oled.sleep(False)
oled.fill(0)
if error:
oled.text("ValueError", 0, 32, 1)
oled.text('time:'+ str(time)+"s", 0, 0, 1)
oled.text('acc:'+ str(a)+" m/s^2", 0, 16, 1)
oled.show()
### main ###
timer.init(period=1,mode=Timer.PERIODIC, callback=time)
while True:
while x:
_, msg = esp.irecv()
if msg == b'start':
time_start = time_now
Pin(2,Pin.OUT).on()
x = False
while not x:
if button.value():
sleep(0.2)
if not button.value():
esp.send(peer, 'stop')
time_stop = time_now
Pin(2,Pin.OUT).off()
x = True
time_delta = round(float((time_stop - time_start)/1000),3)
_, msg = esp.irecv(1000)
if msg:
time_delta = round((time_delta + float(msg))/2,3)
a = round(float(150/((time_delta)**2)),2)
display(time_delta, a, False)
else:
a = round(float(150/(time_delta**2)),2)
display(time_delta, a, True)
print("ValueError")
print(round(time_delta,3))
print(round(a, 2), 'm/s²')
EDIT: I wrote a program that constantly sends ping messages and added a function that it prints the message when the error occurs. The last message was: "b'ping_back\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'"
While it should've just been 'ping_back'. Also note that once this error occurs, the error is given on all the next messages until the microcontroller is rebooted.
Upvotes: 0
Views: 174