mirror of
https://github.com/openmv/openmv.git
synced 2025-11-04 14:49:50 +08:00
Use built-in Python DFU-util
This commit is contained in:
parent
0573d0726d
commit
4bb1d3fc3f
@ -55,6 +55,7 @@
|
||||
<property name="can_focus">False</property>
|
||||
<property name="border_width">5</property>
|
||||
<property name="title" translatable="yes">Update Firmware</property>
|
||||
<property name="modal">True</property>
|
||||
<property name="window_position">center-on-parent</property>
|
||||
<property name="destroy_with_parent">True</property>
|
||||
<property name="type_hint">dialog</property>
|
||||
@ -107,12 +108,15 @@
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkSpinner" id="fw_spinner">
|
||||
<object class="GtkProgressBar" id="fw_progressbar">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="show_text">True</property>
|
||||
<property name="text" translatable="yes"> </property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="fill">False</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
|
||||
@ -1,28 +1,30 @@
|
||||
#!/usr/bin/env python
|
||||
import pydfu
|
||||
import openmv
|
||||
import sys, os, os.path
|
||||
import gtk
|
||||
import gtksourceview2 as gtksourceview
|
||||
from time import sleep
|
||||
import gtk, gtksourceview2 as gtksourceview
|
||||
import gio
|
||||
import pango
|
||||
import gobject
|
||||
import vte
|
||||
import serial
|
||||
from time import sleep
|
||||
import usb.core
|
||||
import usb.util
|
||||
import numpy as np
|
||||
import openmv
|
||||
from os.path import expanduser
|
||||
import subprocess
|
||||
|
||||
|
||||
UI_PATH =os.path.dirname(os.path.realpath(__file__))+"/openmv-ide.glade"
|
||||
CONFIG_PATH = expanduser("~")+"/.openmvide.config"
|
||||
EXAMPLE_PATH = os.path.dirname(os.path.realpath(__file__))+"/examples"
|
||||
SCRIPTS_PATH = os.path.dirname(os.path.realpath(__file__))+"/scripts"
|
||||
FWBIN_PATH = ""
|
||||
FWBIN_PATH = "/home/mux/src/c/stm32f4/openmv/src/build/openmv.bin"
|
||||
DFU_CMD = "dfu-util -d 0483:df11 -c 1 -i 0 -a 0 -s 0x08000000 -D %s"
|
||||
|
||||
SCALE =1
|
||||
flash_offsets= [0x08000000, 0x08004000, 0x08008000, 0x0800C000,
|
||||
0x08010000, 0x08020000, 0x08040000, 0x08060000,
|
||||
0x08080000, 0x080A0000, 0x080C0000, 0x080E0000]
|
||||
|
||||
class OMVGtk:
|
||||
def __init__(self):
|
||||
@ -146,6 +148,11 @@ class OMVGtk:
|
||||
message.run()
|
||||
message.destroy()
|
||||
|
||||
def refresh_gui(self, delay=0.0001, wait=0.0001):
|
||||
sleep(delay)
|
||||
gtk.main_iteration_do(block=False)
|
||||
sleep(wait)
|
||||
|
||||
def connect(self):
|
||||
self.terminal = self.builder.get_object('terminal')
|
||||
try:
|
||||
@ -218,16 +225,54 @@ class OMVGtk:
|
||||
|
||||
dialog.destroy()
|
||||
|
||||
# Fake multitasking :P
|
||||
def fwupdate_task(self, state):
|
||||
if (state["init"]):
|
||||
pydfu.init()
|
||||
state["init"]=False
|
||||
state["erase"]=True
|
||||
state["bar"].set_text("Erasing...")
|
||||
return True
|
||||
elif (state["erase"]):
|
||||
page = state["page"]
|
||||
total = len(flash_offsets)
|
||||
pydfu.page_erase(flash_offsets[page])
|
||||
page +=1
|
||||
state["bar"].set_fraction(page/float(total))
|
||||
if (page == total):
|
||||
state["erase"] = False
|
||||
state["write"] = True
|
||||
state["bar"].set_text("Uploading...")
|
||||
state["page"] = page
|
||||
return True
|
||||
elif (state["write"]):
|
||||
buf = state["buf"]
|
||||
xfer_bytes = state["xfer_bytes"]
|
||||
xfer_total = state["xfer_total"]
|
||||
|
||||
# Send chunk
|
||||
chunk = min (64, xfer_total-xfer_bytes)
|
||||
pydfu.write_page(buf[xfer_bytes:xfer_bytes+chunk], xfer_bytes)
|
||||
|
||||
xfer_bytes += chunk
|
||||
state["xfer_bytes"] = xfer_bytes
|
||||
state["bar"].set_fraction(xfer_bytes/float(xfer_total))
|
||||
|
||||
if (xfer_bytes == xfer_total):
|
||||
pydfu.exit_dfu()
|
||||
state["dialog"].hide()
|
||||
return False
|
||||
|
||||
return True
|
||||
|
||||
def fwupdate_clicked(self, widget):
|
||||
if (self.connected):
|
||||
dialog = self.builder.get_object("fw_dialog")
|
||||
fw_entry = self.builder.get_object("fw_entry")
|
||||
spinner = self.builder.get_object("fw_spinner")
|
||||
fw_progress = self.builder.get_object("fw_progressbar")
|
||||
ok_button = self.builder.get_object("fw_ok_button")
|
||||
cancel_button = self.builder.get_object("fw_cancel_button")
|
||||
|
||||
spinner.stop()
|
||||
spinner.set_visible(False)
|
||||
ok_button.set_sensitive(True)
|
||||
cancel_button.set_sensitive(True)
|
||||
dialog.set_transient_for(self.window);
|
||||
@ -238,24 +283,24 @@ class OMVGtk:
|
||||
if dialog.run() == gtk.RESPONSE_OK:
|
||||
ok_button.set_sensitive(False)
|
||||
cancel_button.set_sensitive(False)
|
||||
spinner.set_visible(True)
|
||||
spinner.start()
|
||||
fw_progress.set_text("")
|
||||
fw_progress.set_fraction(0.0)
|
||||
|
||||
with open(fw_entry.get_text(), 'r') as f:
|
||||
buf= f.read()
|
||||
|
||||
state={"init":True, "erase":False, "write":False,
|
||||
"page":0, "buf":buf, "bar":fw_progress, "dialog":dialog,
|
||||
"xfer_bytes":0, "xfer_total":len(buf)}
|
||||
|
||||
# call dfu-util
|
||||
openmv.enter_dfu()
|
||||
sleep(1.0)
|
||||
gobject.gobject.idle_add(self.fwupdate_task, state);
|
||||
|
||||
dfu_util = subprocess.Popen(DFU_CMD%fw_entry.get_text(), shell=True, stdout=subprocess.PIPE)
|
||||
|
||||
while dfu_util.poll() == None and gtk.events_pending():
|
||||
gtk.main_iteration()
|
||||
|
||||
if (dfu_util.returncode):
|
||||
self.show_message_dialog(gtk.MESSAGE_ERROR, "Failed to update firmware\n")
|
||||
|
||||
openmv.exit_dfu()
|
||||
|
||||
dialog.hide()
|
||||
# try:
|
||||
# except Exception as e:
|
||||
# self.show_message_dialog(gtk.MESSAGE_ERROR, "Failed to update firmware%s"%(e))
|
||||
|
||||
def reset_clicked(self, widget):
|
||||
if (self.connected):
|
||||
|
||||
@ -1,14 +1,20 @@
|
||||
#!/usr/bin/env python
|
||||
import sys
|
||||
# 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,time
|
||||
import usb.core
|
||||
import usb.util
|
||||
import struct
|
||||
import pydfu
|
||||
import numpy as np
|
||||
from PIL import Image
|
||||
import time
|
||||
import StringIO
|
||||
|
||||
__dev = None
|
||||
|
||||
# VID/PID
|
||||
__VID=0xf055
|
||||
__PID=0x9800
|
||||
@ -59,7 +65,6 @@ def init():
|
||||
__dev.set_interface_altsetting(__INTERFACE, __ALTSETTING)
|
||||
|
||||
def release():
|
||||
global __dev
|
||||
try:
|
||||
# Release device
|
||||
usb.util.dispose_resources(dev)
|
||||
@ -83,20 +88,16 @@ def fb_to_arr(buff, bpp):
|
||||
return np.column_stack((r,g,b))
|
||||
|
||||
def fb_size():
|
||||
global __dev
|
||||
# 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():
|
||||
global __dev
|
||||
buf = __dev.ctrl_transfer(0xC1, __USBDBG_FRAME_LOCK, 0, __INTERFACE, 1, __TIMEOUT)
|
||||
return struct.unpack("B", buf)[0]
|
||||
|
||||
def fb_dump():
|
||||
global __dev
|
||||
|
||||
if (fb_lock() == 0):
|
||||
return None
|
||||
|
||||
@ -161,22 +162,6 @@ def enter_dfu():
|
||||
except:
|
||||
pass
|
||||
|
||||
#See app note AN3156
|
||||
def exit_dfu():
|
||||
timeout = 1000
|
||||
dev = usb.core.find(idVendor=0x0483, idProduct=0xdf11)
|
||||
|
||||
# Claim DFU interface
|
||||
usb.util.claim_interface(dev, 0)
|
||||
|
||||
# Send DNLOAD with 0 length to exit DFU
|
||||
dev.ctrl_transfer(0x21, 0x01, 0, 0, None, timeout)
|
||||
# Execute last command
|
||||
dev.ctrl_transfer(0xA1, 0x03, 0, 0, 6, timeout)
|
||||
|
||||
# Release device
|
||||
usb.util.dispose_resources(dev)
|
||||
|
||||
def reset():
|
||||
try:
|
||||
# This will timeout.
|
||||
|
||||
Loading…
Reference in New Issue
Block a user