mirror of
https://github.com/openmv/openmv.git
synced 2025-11-04 14:49:50 +08:00
226 lines
5.2 KiB
Python
Executable File
226 lines
5.2 KiB
Python
Executable File
#!/usr/bin/env python
|
|
# This file is part of the OpenMV project.
|
|
# Copyright (c) 2013/2014 Ibrahim Abdelkader <i.abdalkader@gmail.com>
|
|
# This work is licensed under the MIT license, see the file LICENSE for details.
|
|
#
|
|
# Openmv module.
|
|
import struct
|
|
import sys
|
|
import usb.core
|
|
import usb.util
|
|
from usb.core import USBError
|
|
|
|
__dev = None
|
|
|
|
# VID/PID
|
|
__VID = 0xf055
|
|
__PID = 0x9800
|
|
|
|
# Debug __INTERFACE
|
|
__INTERFACE = 0
|
|
__ALTSETTING = 1
|
|
__IN_EP = 0x81
|
|
__OUT_EP = 0x01
|
|
__TIMEOUT = 3000
|
|
__FB_HDR_SIZE = 12
|
|
|
|
# USB Debug commands
|
|
__USBDBG_FRAME_SIZE = 1
|
|
__USBDBG_FRAME_DUMP = 2
|
|
__USBDBG_FRAME_LOCK = 3
|
|
__USBDBG_FRAME_UPDATE = 4
|
|
__USBDBG_SCRIPT_EXEC = 5
|
|
__USBDBG_SCRIPT_STOP = 6
|
|
__USBDBG_SCRIPT_SAVE = 7
|
|
__USBDBG_TEMPLATE_SAVE = 8
|
|
__USBDBG_DESCRIPTOR_SAVE = 9
|
|
__USBDBG_ATTR_READ = 10
|
|
__USBDBG_ATTR_WRITE = 11
|
|
__USBDBG_SYS_RESET = 12
|
|
__USBDBG_SYS_BOOT = 13
|
|
|
|
ATTR_CONTRAST = 0
|
|
ATTR_BRIGHTNESS = 1
|
|
ATTR_SATURATION = 2
|
|
ATTR_GAINCEILING = 3
|
|
|
|
FORMAT_UNKNOWN = 0
|
|
FORMAT_RGB565 = 1
|
|
FORMAT_JPEG = 2
|
|
FORMAT_GRAY = 3
|
|
|
|
|
|
def init():
|
|
global __dev
|
|
# find USB __device
|
|
print('OpenMV Cam init()')
|
|
try:
|
|
__dev = usb.core.find(idVendor=__VID, idProduct=__PID)
|
|
|
|
if __dev is None:
|
|
raise ValueError('__device not found')
|
|
|
|
# detach kernel driver
|
|
if __dev.is_kernel_driver_active(__INTERFACE):
|
|
__dev.detach_kernel_driver(__INTERFACE)
|
|
|
|
# claim __INTERFACE
|
|
usb.util.claim_interface(__dev, __INTERFACE)
|
|
|
|
# set FB debug alt setting
|
|
__dev.set_interface_altsetting(__INTERFACE, __ALTSETTING)
|
|
except Exception as e:
|
|
pass
|
|
print('Error while searching for OpenMV Cam: %s' % e.message)
|
|
|
|
|
|
def find():
|
|
found = False
|
|
try:
|
|
dev = usb.core.find(idVendor=__VID, idProduct=__PID)
|
|
except USBError:
|
|
pass
|
|
found = False
|
|
else:
|
|
if dev:
|
|
found = True
|
|
finally:
|
|
return found
|
|
|
|
|
|
def release():
|
|
try:
|
|
# Release device resources, interface, etc.
|
|
usb.util.dispose_resources(__dev)
|
|
|
|
# reattach kernel driver
|
|
#__dev.attach_kernel_driver(__INTERFACE)
|
|
except USBError as e:
|
|
print('error disposing resources %s' % e)
|
|
pass
|
|
|
|
|
|
def fb_size():
|
|
# read fb header
|
|
buf = __dev.ctrl_transfer(0xC1, __USBDBG_FRAME_SIZE, 0, __INTERFACE, __FB_HDR_SIZE, __TIMEOUT)
|
|
size = struct.unpack("III", buf)
|
|
return size
|
|
|
|
|
|
def fb_lock():
|
|
try:
|
|
buf = __dev.ctrl_transfer(0xC1, __USBDBG_FRAME_LOCK, 0, __INTERFACE, 1, __TIMEOUT)
|
|
except USBError:
|
|
pass
|
|
return 0
|
|
else:
|
|
return struct.unpack("B", buf)[0]
|
|
|
|
|
|
def fb_get():
|
|
if fb_lock() == 0:
|
|
return None
|
|
|
|
buf = __dev.ctrl_transfer(0xC1, __USBDBG_FRAME_SIZE, 0, __INTERFACE, __FB_HDR_SIZE, __TIMEOUT)
|
|
|
|
size = struct.unpack("III", buf)
|
|
|
|
w = size[0]
|
|
h = size[1]
|
|
bpp = size[2]
|
|
|
|
if bpp > 2:
|
|
# bpp is actually image size and data is in JPEG format
|
|
num_bytes = bpp
|
|
fmt = FORMAT_JPEG
|
|
else:
|
|
num_bytes = w * h * bpp
|
|
if bpp == 1:
|
|
fmt = FORMAT_GRAY
|
|
elif bpp == 2:
|
|
fmt = FORMAT_RGB565
|
|
else:
|
|
fmt = None
|
|
w = None
|
|
h = None
|
|
|
|
if fmt:
|
|
# read fb data
|
|
try:
|
|
__dev.ctrl_transfer(0xC1, __USBDBG_FRAME_DUMP, num_bytes/4, __INTERFACE, 0, __TIMEOUT)
|
|
except USBError:
|
|
pass
|
|
else:
|
|
buff = __dev.read(__IN_EP, num_bytes, __INTERFACE, __TIMEOUT)
|
|
else:
|
|
buff = None
|
|
|
|
return fmt, w, h, buff
|
|
|
|
|
|
def fb_update():
|
|
__dev.ctrl_transfer(0x41, __USBDBG_FRAME_UPDATE, 0, __INTERFACE, None, __TIMEOUT)
|
|
|
|
|
|
def exec_script(buf):
|
|
__dev.ctrl_transfer(0x41, __USBDBG_SCRIPT_EXEC, len(buf), __INTERFACE, None, __TIMEOUT)
|
|
__dev.write(__OUT_EP, buf, __INTERFACE, __TIMEOUT)
|
|
|
|
|
|
def stop_script():
|
|
try:
|
|
__dev.ctrl_transfer(0x41, __USBDBG_SCRIPT_STOP, 0, __INTERFACE, None, __TIMEOUT)
|
|
except USBError:
|
|
pass
|
|
|
|
def save_template(x, y, w, h, path):
|
|
buf = struct.pack("IIII", x, y, w, h) + path
|
|
__dev.ctrl_transfer(0x41, __USBDBG_TEMPLATE_SAVE, len(buf), __INTERFACE, None, __TIMEOUT)
|
|
__dev.write(__OUT_EP, buf, __INTERFACE, __TIMEOUT)
|
|
|
|
|
|
def save_descriptor(x, y, w, h, path):
|
|
buf = struct.pack("IIII", x, y, w, h) + path
|
|
__dev.ctrl_transfer(0x41, __USBDBG_DESCRIPTOR_SAVE, len(buf), __INTERFACE, None, __TIMEOUT)
|
|
__dev.write(__OUT_EP, buf, __INTERFACE, __TIMEOUT)
|
|
|
|
|
|
def set_attr(attr, value):
|
|
buf = struct.unpack(">H", struct.pack("bb", attr, value))[0]
|
|
__dev.ctrl_transfer(0x41, __USBDBG_ATTR_WRITE, buf, __INTERFACE, None, __TIMEOUT)
|
|
|
|
|
|
def get_attr(attr):
|
|
return 0
|
|
|
|
|
|
def enter_dfu():
|
|
try:
|
|
# This will timeout.
|
|
__dev.ctrl_transfer(0x41, __USBDBG_SYS_BOOT, 0, __INTERFACE, None, __TIMEOUT)
|
|
except USBError as e:
|
|
pass
|
|
|
|
|
|
def reset():
|
|
try:
|
|
# This will timeout.
|
|
__dev.ctrl_transfer(0x41, __USBDBG_SYS_RESET, 0, __INTERFACE, None, __TIMEOUT)
|
|
except USBError:
|
|
pass
|
|
|
|
|
|
if __name__ == '__main__':
|
|
if len(sys.argv) != 2:
|
|
print ('usage: openmv.py <script>')
|
|
sys.exit(1)
|
|
with open(sys.argv[1], 'r') as fin:
|
|
init()
|
|
exec_script(fin.read())
|
|
|
|
|
|
def __write_img(buff, path):
|
|
with open(path, "wb") as f:
|
|
f.write(buff)
|
|
f.close()
|