try: from pyb import CAN except ImportError: print('SKIP') raise SystemExit from array import array import micropython import pyb # test we can correctly create by id (2 handled in can2.py test) for bus in (-1, 0, 1, 3): try: CAN(bus, CAN.LOOPBACK) print("CAN", bus) except ValueError: print("ValueError", bus) CAN(1).deinit() CAN.initfilterbanks(14) can = CAN(1) print(can) # Test state when de-init'd print(can.state() == can.STOPPED) can.init(CAN.LOOPBACK) print(can) print(can.any(0)) # Test state when freshly created print(can.state() == can.ERROR_ACTIVE) # Test that restart can be called can.restart() # Test info returns a sensible value print(can.info()) # Catch all filter can.setfilter(0, CAN.MASK16, 0, (0, 0, 0, 0)) can.send('abcd', 123, timeout=5000) print(can.any(0), can.info()) print(can.recv(0)) can.send('abcd', -1, timeout=5000) print(can.recv(0)) can.send('abcd', 0x7FF + 1, timeout=5000) print(can.recv(0)) # Test too long message try: can.send('abcdefghi', 0x7FF, timeout=5000) except ValueError: print('passed') else: print('failed') # Test that recv can work without allocating memory on the heap buf = bytearray(10) l = [0, 0, 0, memoryview(buf)] l2 = None micropython.heap_lock() can.send('', 42) l2 = can.recv(0, l) assert l is l2 print(l, len(l[3]), buf) can.send('1234', 42) l2 = can.recv(0, l) assert l is l2 print(l, len(l[3]), buf) can.send('01234567', 42) l2 = can.recv(0, l) assert l is l2 print(l, len(l[3]), buf) can.send('abc', 42) l2 = can.recv(0, l) assert l is l2 print(l, len(l[3]), buf) micropython.heap_unlock() # Test that recv can work with different arrays behind the memoryview can.send('abc', 1) print(bytes(can.recv(0, [0, 0, 0, memoryview(array('B', range(8)))])[3])) can.send('def', 1) print(bytes(can.recv(0, [0, 0, 0, memoryview(array('b', range(8)))])[3])) # Test for non-list passed as second arg to recv can.send('abc', 1) try: can.recv(0, 1) except TypeError: print('TypeError') # Test for too-short-list passed as second arg to recv can.send('abc', 1) try: can.recv(0, [0, 0, 0]) except ValueError: print('ValueError') # Test for non-memoryview passed as 4th element to recv can.send('abc', 1) try: can.recv(0, [0, 0, 0, 0]) except TypeError: print('TypeError') # Test for read-only-memoryview passed as 4th element to recv can.send('abc', 1) try: can.recv(0, [0, 0, 0, memoryview(bytes(8))]) except ValueError: print('ValueError') # Test for bad-typecode-memoryview passed as 4th element to recv can.send('abc', 1) try: can.recv(0, [0, 0, 0, memoryview(array('i', range(8)))]) except ValueError: print('ValueError') del can # Testing extended IDs can = CAN(1, CAN.LOOPBACK, extframe = True) # Catch all filter can.setfilter(0, CAN.MASK32, 0, (0, 0)) print(can) try: can.send('abcde', 0x7FF + 1, timeout=5000) except ValueError: print('failed') else: r = can.recv(0) if r[0] == 0x7FF+1 and r[3] == b'abcde': print('passed') else: print('failed, wrong data received') # Test filters for n in [0, 8, 16, 24]: filter_id = 0b00001000 << n filter_mask = 0b00011100 << n id_ok = 0b00001010 << n id_fail = 0b00011010 << n can.clearfilter(0) can.setfilter(0, pyb.CAN.MASK32, 0, (filter_id, filter_mask)) can.send('ok', id_ok, timeout=3) if can.any(0): msg = can.recv(0) print((hex(filter_id), hex(filter_mask), hex(msg[0]), msg[3])) can.send("fail", id_fail, timeout=3) if can.any(0): msg = can.recv(0) print((hex(filter_id), hex(filter_mask), hex(msg[0]), msg[3])) del can # Test RxCallbacks can = CAN(1, CAN.LOOPBACK) can.setfilter(0, CAN.LIST16, 0, (1, 2, 3, 4)) can.setfilter(1, CAN.LIST16, 1, (5, 6, 7, 8)) def cb0(bus, reason): print('cb0') if reason == 0: print('pending') if reason == 1: print('full') if reason == 2: print('overflow') def cb1(bus, reason): print('cb1') if reason == 0: print('pending') if reason == 1: print('full') if reason == 2: print('overflow') def cb0a(bus, reason): print('cb0a') if reason == 0: print('pending') if reason == 1: print('full') if reason == 2: print('overflow') def cb1a(bus, reason): print('cb1a') if reason == 0: print('pending') if reason == 1: print('full') if reason == 2: print('overflow') can.rxcallback(0, cb0) can.rxcallback(1, cb1) can.send('11111111',1, timeout=5000) can.send('22222222',2, timeout=5000) can.send('33333333',3, timeout=5000) can.rxcallback(0, cb0a) can.send('44444444',4, timeout=5000) can.send('55555555',5, timeout=5000) can.send('66666666',6, timeout=5000) can.send('77777777',7, timeout=5000) can.rxcallback(1, cb1a) can.send('88888888',8, timeout=5000) print(can.recv(0)) print(can.recv(0)) print(can.recv(0)) print(can.recv(1)) print(can.recv(1)) print(can.recv(1)) can.send('11111111',1, timeout=5000) can.send('55555555',5, timeout=5000) print(can.recv(0)) print(can.recv(1)) del can # Testing asynchronous send can = CAN(1, CAN.LOOPBACK) can.setfilter(0, CAN.MASK16, 0, (0, 0, 0, 0)) while can.any(0): can.recv(0) can.send('abcde', 1, timeout=0) print(can.any(0)) while not can.any(0): pass print(can.recv(0)) try: can.send('abcde', 2, timeout=0) can.send('abcde', 3, timeout=0) can.send('abcde', 4, timeout=0) can.send('abcde', 5, timeout=0) except OSError as e: if str(e) == '16': print('passed') else: print('failed') pyb.delay(500) while can.any(0): print(can.recv(0)) # Testing rtr messages bus1 = CAN(1, CAN.LOOPBACK) while bus1.any(0): bus1.recv(0) bus1.setfilter(0, CAN.LIST16, 0, (1, 2, 3, 4)) bus1.setfilter(1, CAN.LIST16, 0, (5, 6, 7, 8), rtr=(True, True, True, True)) bus1.setfilter(2, CAN.MASK16, 0, (64, 64, 32, 32), rtr=(False, True)) bus1.send('',1,rtr=True) print(bus1.any(0)) bus1.send('',5,rtr=True) print(bus1.recv(0)) bus1.send('',6,rtr=True) print(bus1.recv(0)) bus1.send('',7,rtr=True) print(bus1.recv(0)) bus1.send('',16,rtr=True) print(bus1.any(0)) bus1.send('',32,rtr=True) print(bus1.recv(0)) # test HAL error, timeout can = pyb.CAN(1, pyb.CAN.NORMAL) try: can.send('1', 1, timeout=50) except OSError as e: print(repr(e))