| Index: embios/trunk/tools/embios.py |
| — | — | @@ -25,7 +25,10 @@ |
| 26 | 26 | import os
|
| 27 | 27 | import inspect
|
| 28 | 28 | import re
|
| | 29 | +import time
|
| 29 | 30 |
|
| | 31 | +from functools import wraps
|
| | 32 | +
|
| 30 | 33 | import libembios
|
| 31 | 34 | from libembios import Error
|
| 32 | 35 | import libembiosdata
|
| — | — | @@ -144,6 +147,7 @@ |
| 145 | 148 | Decorator for all commands.
|
| 146 | 149 | The decorated function is called with (self, all, other, arguments, ...)
|
| 147 | 150 | """
|
| | 151 | + @wraps(func)
|
| 148 | 152 | def decorator(*args):
|
| 149 | 153 | return func(args[0], *args[1:])
|
| 150 | 154 | func._command = True
|
| — | — | @@ -179,12 +183,8 @@ |
| 180 | 184 | self.embios = libembios.Embios()
|
| 181 | 185 | except libembios.DeviceNotFoundError:
|
| 182 | 186 | self.logger.error("No emBIOS device found!")
|
| 183 | | - end(1)
|
| 184 | | - try:
|
| 185 | | - self.getinfo("version")
|
| 186 | | - except libembios.DeviceNotFoundError:
|
| 187 | | - self.logger.error("Device not found!")
|
| 188 | | - exit(2)
|
| | 187 | + exit(1)
|
| | 188 | + self.getinfo("version")
|
| 189 | 189 |
|
| 190 | 190 | def _parsecommand(self, func, args):
|
| 191 | 191 | # adds self to the commandline args.
|
| — | — | @@ -194,20 +194,24 @@ |
| 195 | 195 | try:
|
| 196 | 196 | self.cmddict[func](*args)
|
| 197 | 197 | except ArgumentError, e:
|
| 198 | | - usage(e)
|
| | 198 | + usage(e, specific=func)
|
| 199 | 199 | except ArgumentError:
|
| 200 | | - usage("Syntax Error in function '" + func + "'")
|
| | 200 | + usage("Syntax Error in function '" + func + "'", specific=func)
|
| 201 | 201 | except ArgumentTypeError, e:
|
| 202 | | - usage(e)
|
| | 202 | + usage(e, specific=func)
|
| 203 | 203 | except NotImplementedError:
|
| 204 | 204 | self.logger.error("This function is not implemented yet!")
|
| 205 | 205 | except libembios.DeviceError, e:
|
| 206 | 206 | self.logger.error(str(e))
|
| | 207 | + except ValueError:
|
| | 208 | + usage(specific=func)
|
| 207 | 209 | except TypeError, e:
|
| 208 | 210 | if str(e).split(" ", 1)[0] == func + "()":
|
| 209 | 211 | self.logger.error(usage("Argument Error in '" + func + "': Wrong argument count", specific=func))
|
| 210 | 212 | else:
|
| 211 | 213 | raise
|
| | 214 | + except libembios.usb.core.USBError:
|
| | 215 | + self.logger.error("Problem with USB connection.")
|
| 212 | 216 | else:
|
| 213 | 217 | usage("No such command")
|
| 214 | 218 |
|
| — | — | @@ -322,9 +326,7 @@ |
| 323 | 327 | with f:
|
| 324 | 328 | self.embios.write(addr, f.read())
|
| 325 | 329 | self.logger.info("done\n")
|
| 326 | | -
|
| 327 | | -
|
| 328 | | -
|
| | 330 | +
|
| 329 | 331 | @command
|
| 330 | 332 | def downloadfile(self, addr, size, filename):
|
| 331 | 333 | """
|
| — | — | @@ -371,7 +373,7 @@ |
| 372 | 374 | self.logger.info("Integer '"+self._hex(integer)+"' read from address "+self._hex(addr))
|
| 373 | 375 |
|
| 374 | 376 | @command
|
| 375 | | - def i2crecv(self, bus, slave, addr, size):
|
| | 377 | + def i2cread(self, bus, slave, addr, size):
|
| 376 | 378 | """
|
| 377 | 379 | Reads data from an I2C device
|
| 378 | 380 | <bus> the bus index
|
| — | — | @@ -383,103 +385,75 @@ |
| 384 | 386 | slave = self._hexint(slave)
|
| 385 | 387 | addr = self._hexint(addr)
|
| 386 | 388 | size = self._hexint(size)
|
| 387 | | - raise NotImplementedError
|
| | 389 | + self.embios.i2cread(bus, slave, addr, size)
|
| 388 | 390 |
|
| 389 | 391 | @command
|
| 390 | | - def i2csend(self, bus, slave, addr, *args):
|
| | 392 | + def i2cwrite(self, bus, slave, addr, *args):
|
| 391 | 393 | """
|
| 392 | 394 | Writes data to an I2C device
|
| 393 | 395 | <bus> the bus index
|
| 394 | 396 | <slave> the slave address
|
| 395 | 397 | <addr> the start address on the I2C device
|
| 396 | | - <db1> ... <dbN> the data in single bytes, seperated by whitespaces,
|
| 397 | | - eg. 0x37 0x56 0x45 0x12
|
| | 398 | + <db1> ... <dbN> the data in single bytes, encoded in hex,
|
| | 399 | + seperated by whitespaces, eg. 37 56 45 12
|
| 398 | 400 | """
|
| 399 | 401 | bus = self._hexint(bus)
|
| 400 | 402 | slave = self._hexint(slave)
|
| 401 | 403 | addr = self._hexint(addr)
|
| 402 | | - data = []
|
| | 404 | + data = ""
|
| 403 | 405 | for arg in args:
|
| 404 | | - data.append(self._hexint(arg))
|
| 405 | | - raise NotImplementedError
|
| | 406 | + data += chr(self._hexint(arg))
|
| | 407 | + self.embios.i2cwrite(bus, slave, addr, data)
|
| 406 | 408 |
|
| 407 | 409 | @command
|
| 408 | | - def readusbconsole(self, size, outtype):
|
| | 410 | + def console(self):
|
| 409 | 411 | """
|
| 410 | | - Reads data from the USB console.
|
| 411 | | - <size>: the number of bytes to read
|
| 412 | | - <outtype>: defines how to output the result:
|
| 413 | | - 'file': writes the result to file <file>
|
| 414 | | - 'printstring': writes the result as string to the console window
|
| 415 | | - 'printhex': writes the result in hexedit notation to the console window
|
| 416 | | - <file>: the file to write the result to, can be omitted
|
| 417 | | - if <outtype> is not 'file'
|
| | 412 | + Reads data from the USB console continuously
|
| 418 | 413 | """
|
| 419 | | - size = self._hexint(size)
|
| 420 | | - raise NotImplementedError
|
| 421 | | -
|
| | 414 | + while True:
|
| | 415 | + resp = self.embios.usbcread()
|
| | 416 | + self.logger.log(resp.data)
|
| | 417 | + time.sleep(0.1 / resp.maxsize * (resp.maxsize - len(resp.data)))
|
| 422 | 418 |
|
| 423 | 419 | @command
|
| 424 | | - def writeusbconsole_file(self, file, offset=0, length=None):
|
| | 420 | + def writeusbconsole(self, *args):
|
| 425 | 421 | """
|
| 426 | | - Writes the file <file> to the USB console.
|
| 427 | | - Optional params <offset> <length>: specify the range in <file> to write
|
| | 422 | + Writes the string <db1> ... <dbN> to the USB console.
|
| 428 | 423 | """
|
| 429 | | -
|
| 430 | | - offset = self._hexint(offset)
|
| 431 | | - length = self._hexint(length)
|
| 432 | | - raise NotImplementedError
|
| | 424 | + text = ""
|
| | 425 | + for word in args:
|
| | 426 | + text += word + " "
|
| | 427 | + text = text[:-1]
|
| | 428 | + self.logger.info("Writing '"+text+"' to the usb console\n")
|
| | 429 | + self.embios.usbcwrite(text)
|
| 433 | 430 |
|
| 434 | 431 | @command
|
| 435 | | - def writeusbconsole_direct(self, *args):
|
| | 432 | + def readdevconsole(self, bitmask):
|
| 436 | 433 | """
|
| 437 | | - Writes the strings <db1> ... <dbN> to the USB console."
|
| | 434 | + Reads data continuously from one or more of the device's consoles.
|
| | 435 | + <bitmask>: the bitmask of the consoles to read from.
|
| 438 | 436 | """
|
| 439 | | - raise NotImplementedError
|
| 440 | | -
|
| 441 | | - @command
|
| 442 | | - def readdevconsole(self, bitmask, size, outtype, file=None):
|
| 443 | | - """
|
| 444 | | - Reads data from one or more of the device's consoles.
|
| 445 | | - <bitmask>: the bitmask of the consoles to read from
|
| 446 | | - <size>: the number of bytes to read
|
| 447 | | - <outtype>: defines how to output the result:
|
| 448 | | - 'file': writes the result to file <file>
|
| 449 | | - 'printstring': writes the result as string to the console window
|
| 450 | | - 'printhex': writes the result in hexedit notation to the console window
|
| 451 | | - <file>: the file to write the result to, can be omitted
|
| 452 | | - if <outtype> is not 'file'
|
| 453 | | - """
|
| 454 | 437 | bitmask = self._hexint(bitmask)
|
| 455 | | - size = self._hexint(size)
|
| 456 | | - outtype = self._strcheck(['file', 'printstring', 'printhex'])
|
| 457 | | - raise NotImplementedError
|
| 458 | | -
|
| | 438 | + while True:
|
| | 439 | + resp = self.embios.cread()
|
| | 440 | + self.logger.log(resp.data)
|
| | 441 | + time.sleep(0.1 / resp.maxsize * (resp.maxsize - len(resp.data)))
|
| | 442 | +
|
| 459 | 443 | @command
|
| 460 | | - def writedevconsole_file(self, bitmask, file, offset=0, length=None):
|
| | 444 | + def writedevconsole(self, bitmask, *args):
|
| 461 | 445 | """
|
| 462 | | - Writes the file <file> to the device consoles specified by <bitmask>
|
| 463 | | - Optional params <offset> <length>: specify the range in <file> to write
|
| | 446 | + Writes the string <db1> ... <dbN> to one or more of the device's consoles.
|
| | 447 | + <bitmask>: the bitmask of the consoles to write to
|
| 464 | 448 | """
|
| 465 | 449 | bitmask = self._hexint(bitmask)
|
| 466 | | -
|
| 467 | | - offset = self._hexint(offset)
|
| 468 | | - length = self._hexint(length)
|
| 469 | | - raise NotImplementedError
|
| | 450 | + text = ""
|
| | 451 | + for word in args:
|
| | 452 | + text += word + " "
|
| | 453 | + text = text[:-1]
|
| | 454 | + self.logger.info("Writing '"+text+"' to the device consoles identified with "+self._hex(bitmask)+"\n")
|
| | 455 | + self.embios.cwrite(text, bitmask)
|
| 470 | 456 |
|
| 471 | 457 | @command
|
| 472 | | - def writedevconsole_direct(self, bitmask, *args):
|
| 473 | | - """
|
| 474 | | - Writes the integers <db1> ... <dbN> to the device consoles specified
|
| 475 | | - by <bitmask>
|
| 476 | | - """
|
| 477 | | - bitmask = self._hexint(bitmask)
|
| 478 | | - data = []
|
| 479 | | - for arg in args:
|
| 480 | | - data.append(self._hexint(arg))
|
| 481 | | - raise NotImplementedError
|
| 482 | | -
|
| 483 | | - @command
|
| 484 | 458 | def flushconsolebuffers(self, bitmask):
|
| 485 | 459 | """
|
| 486 | 460 | flushes one or more of the device consoles' buffers.
|
| — | — | @@ -515,6 +489,7 @@ |
| 516 | 490 | """
|
| 517 | 491 | Locks (freezes) the scheduler
|
| 518 | 492 | """
|
| | 493 | + self.logger.info("Will now lock scheduler\n")
|
| 519 | 494 | self.embios.lockscheduler()
|
| 520 | 495 |
|
| 521 | 496 | @command
|
| — | — | @@ -522,6 +497,7 @@ |
| 523 | 498 | """
|
| 524 | 499 | Unlocks (unfreezes) the scheduler
|
| 525 | 500 | """
|
| | 501 | + self.logger.info("Will now unlock scheduler\n")
|
| 526 | 502 | self.embios.unlockscheduler()
|
| 527 | 503 |
|
| 528 | 504 | @command
|
| — | — | @@ -573,19 +549,8 @@ |
| 574 | 550 | Uploads the emBIOS application <filename> to
|
| 575 | 551 | the beginning of the user memory and executes it
|
| 576 | 552 | """
|
| 577 | | - try:
|
| 578 | | - f = open(filename, "rb")
|
| 579 | | - except IOError:
|
| 580 | | - raise ArgumentError("File not readable. Does it exist?")
|
| 581 | | - data = self.embios.getusermemrange()
|
| 582 | | - addr = data.lower
|
| 583 | | - maxsize = data.upper - data.lower
|
| 584 | | - filesize = os.path.getsize(filename)
|
| 585 | | - if filesize > maxsize:
|
| 586 | | - raise ArgumentError("The file is too big, it doesn't fit into the user memory.")
|
| 587 | | - self.logger.info("Uploading application to "+self._hex(addr)+" - "+self._hex(addr+filesize)+"\n")
|
| 588 | | - self.embios.write(addr, f.read())
|
| 589 | | - self.execimage(addr)
|
| | 553 | + #self.execimage(addr)
|
| | 554 | + raise NotImplementedError
|
| 590 | 555 |
|
| 591 | 556 | @command
|
| 592 | 557 | def execimage(self, addr):
|
| — | — | @@ -595,10 +560,19 @@ |
| 596 | 561 | addr = self._hexint(addr)
|
| 597 | 562 | self.logger.info("Starting emBIOS app at "+self._hex(addr)+"\n")
|
| 598 | 563 | self.embios.execimage(addr)
|
| 599 | | -
|
| | 564 | +
|
| 600 | 565 | @command
|
| 601 | | - def readrawbootflash(self, addr_flash, addr_mem, size):
|
| | 566 | + def flushcaches(self):
|
| 602 | 567 | """
|
| | 568 | + Flushes the CPUs data and instruction caches.
|
| | 569 | + """
|
| | 570 | + self.logger.info("Flushing CPU data and instruction caches...")
|
| | 571 | + self.embios.flushcaches()
|
| | 572 | + self.logger.info("done\n")
|
| | 573 | +
|
| | 574 | + @command
|
| | 575 | + def readbootflash(self, addr_flash, addr_mem, size):
|
| | 576 | + """
|
| 603 | 577 | Reads <size> bytes from bootflash to memory.
|
| 604 | 578 | <addr_bootflsh>: the address in bootflash to read from
|
| 605 | 579 | <addr_mem>: the address in memory to copy the data to
|
| — | — | @@ -609,9 +583,9 @@ |
| 610 | 584 | self.logger.info("Dumping boot flash addresses "+self._hex(addr_flash)+" - "+
|
| 611 | 585 | hex(addr_flash+size)+" to "+self._hex(addr_mem)+" - "+self._hex(addr_mem+size)+"\n")
|
| 612 | 586 | self.embios.bootflashread(addr_flash, addr_mem, size)
|
| 613 | | -
|
| | 587 | +
|
| 614 | 588 | @command
|
| 615 | | - def writerawbootflash(self, addr_flash, addr_mem, size, force=False):
|
| | 589 | + def writebootflash(self, addr_flash, addr_mem, size, force=False):
|
| 616 | 590 | """
|
| 617 | 591 | Writes <size> bytes from memory to bootflash.
|
| 618 | 592 | ATTENTION: Don't call this unless you really know what you're doing!
|
| — | — | @@ -628,23 +602,32 @@ |
| 629 | 603 | hex(addr_mem+size)+" to "+self._hex(addr_flash)+" - "+self._hex(addr_flash+size)+"\n")
|
| 630 | 604 | if force == False:
|
| 631 | 605 | self.logger.info("If this was not what you intended press Ctrl-C NOW")
|
| 632 | | - import time
|
| 633 | | - for i in range(5):
|
| | 606 | + for i in range(10):
|
| 634 | 607 | self.logger.info(".")
|
| 635 | 608 | time.sleep(1)
|
| 636 | 609 | self.logger.info("\n")
|
| 637 | 610 | self.embios.bootflashwrite(addr_flash, addr_mem, size)
|
| 638 | | -
|
| | 611 | +
|
| 639 | 612 | @command
|
| 640 | | - def flushcaches(self):
|
| | 613 | + def runfirmware(self, addr, filename):
|
| 641 | 614 | """
|
| 642 | | - Flushes the CPUs data and instruction caches.
|
| | 615 | + Uploads the firmware in 'filename' to the beginning of the
|
| | 616 | + user memory and executes it
|
| 643 | 617 | """
|
| 644 | | - self.logger.info("Flushing CPU data and instruction caches...")
|
| 645 | | - self.embios.flushcaches()
|
| 646 | | - self.logger.info("done\n")
|
| | 618 | + addr = self._hexint(addr)
|
| | 619 | + self.uploadfile(addr, filename)
|
| | 620 | + self.execfirmware(addr)
|
| 647 | 621 |
|
| 648 | 622 | @command
|
| | 623 | + def execfirmware(self, addr):
|
| | 624 | + """
|
| | 625 | + Executes the firmware at addr
|
| | 626 | + """
|
| | 627 | + addr = self._hexint(addr)
|
| | 628 | + self.logger.info("Running firmware at "+self._hex(addr)+". Bye.")
|
| | 629 | + self.embios.execfirmware(addr)
|
| | 630 | +
|
| | 631 | + @command
|
| 649 | 632 | def aesencrypt(self, addr, size, keyindex):
|
| 650 | 633 | """
|
| 651 | 634 | Encrypts a buffer using a hardware key
|
| Index: embios/trunk/tools/libembiosdata.py |
| — | — | @@ -1,3 +1,26 @@ |
| | 2 | +#!/usr/bin/env python
|
| | 3 | +#
|
| | 4 | +#
|
| | 5 | +# Copyright 2010 TheSeven, benedikt93, Farthen
|
| | 6 | +#
|
| | 7 | +#
|
| | 8 | +# This file is part of emBIOS.
|
| | 9 | +#
|
| | 10 | +# emBIOS is free software: you can redistribute it and/or
|
| | 11 | +# modify it under the terms of the GNU General Public License as
|
| | 12 | +# published by the Free Software Foundation, either version 2 of the
|
| | 13 | +# License, or (at your option) any later version.
|
| | 14 | +#
|
| | 15 | +# emBIOS is distributed in the hope that it will be useful,
|
| | 16 | +# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
| | 17 | +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
| | 18 | +# See the GNU General Public License for more details.
|
| | 19 | +#
|
| | 20 | +# You should have received a copy of the GNU General Public License
|
| | 21 | +# along with emBIOS. If not, see <http://www.gnu.org/licenses/>.
|
| | 22 | +#
|
| | 23 | +#
|
| | 24 | +
|
| 2 | 25 | thread_state = (
|
| 3 | 26 | "THREAD_FREE",
|
| 4 | 27 | "THREAD_SUSPENDED",
|
| — | — | @@ -20,7 +43,7 @@ |
| 21 | 44 | thread_type = (
|
| 22 | 45 | "USER_THREAD",
|
| 23 | 46 | "OS_THREAD",
|
| 24 | | - "ORE_THREAD"
|
| | 47 | + "CORE_THREAD"
|
| 25 | 48 | )
|
| 26 | 49 |
|
| 27 | 50 | hwtypes = {
|
| Index: embios/trunk/tools/libembios.py |
| — | — | @@ -67,8 +67,12 @@ |
| 68 | 68 |
|
| 69 | 69 |
|
| 70 | 70 | class Embios(object):
|
| | 71 | + """
|
| | 72 | + Class for all embios functions.
|
| | 73 | + """
|
| 71 | 74 | def __init__(self):
|
| 72 | | - self.lib = Lib(self)
|
| | 75 | + self.lib = Lib()
|
| | 76 | + self.getpacketsizeinfo()
|
| 73 | 77 |
|
| 74 | 78 | @staticmethod
|
| 75 | 79 | def _alignsplit(addr, size, blksize, align):
|
| — | — | @@ -121,9 +125,7 @@ |
| 122 | 126 | from the device. This cares about too long packages
|
| 123 | 127 | and decides whether to use DMA or not.
|
| 124 | 128 | """
|
| 125 | | - if not self.lib.connected:
|
| 126 | | - self.lib.connect()
|
| 127 | | - cin_maxsize = self.lib.dev.packetsizelimit["cin"] - 0x10
|
| | 129 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| 128 | 130 | din_maxsize = self.lib.dev.packetsizelimit["din"]
|
| 129 | 131 | data = ""
|
| 130 | 132 | (headsize, bodysize, tailsize) = self._alignsplit(addr, size, cin_maxsize, 16)
|
| — | — | @@ -148,9 +150,7 @@ |
| 149 | 151 | in the memory of the device. This cares about too long packages
|
| 150 | 152 | and decides whether to use DMA or not.
|
| 151 | 153 | """
|
| 152 | | - if not self.lib.connected:
|
| 153 | | - self.lib.connect()
|
| 154 | | - cout_maxsize = self.lib.dev.packetsizelimit["cout"] - 0x10
|
| | 154 | + cout_maxsize = self.lib.dev.packetsizelimit["cout"] - self.lib.headersize
|
| 155 | 155 | dout_maxsize = self.lib.dev.packetsizelimit["dout"]
|
| 156 | 156 | (headsize, bodysize, tailsize) = self._alignsplit(addr, len(data), cout_maxsize, 16)
|
| 157 | 157 | offset = 0
|
| — | — | @@ -203,7 +203,7 @@ |
| 204 | 204 | """ Reads a zero terminated string from memory
|
| 205 | 205 | Reads only a maximum of 'maxlength' chars.
|
| 206 | 206 | """
|
| 207 | | - cin_maxsize = self.lib.dev.packetsizelimit["cin"] - 0x10
|
| | 207 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| 208 | 208 | string = ""
|
| 209 | 209 | while (len(string) < maxlength or maxlength < 0):
|
| 210 | 210 | data = self.readmem(addr, min(maxlength - len(string), cin_maxsize))
|
| — | — | @@ -218,25 +218,61 @@ |
| 219 | 219 |
|
| 220 | 220 | def i2cread(self, index, slaveaddr, startaddr, size):
|
| 221 | 221 | """ Reads data from an i2c slave """
|
| | 222 | + if size > 256 or size < 1:
|
| | 223 | + raise ValueError("Size must be a number between 1 and 256")
|
| | 224 | + if size == 256:
|
| | 225 | + size = 0
|
| | 226 | + resp = self.lib.monitorcommand(struct.pack("IBBBBII", 8, index, slaveaddr, startaddr, size, 0, 0), "III%ds" % size, (None, None, None, "data"))
|
| | 227 | + return resp.data
|
| 222 | 228 |
|
| 223 | 229 | def i2cwrite(self, index, slaveaddr, startaddr, data):
|
| 224 | 230 | """ Writes data to an i2c slave """
|
| | 231 | + size = len(data)
|
| | 232 | + if size > 256 or size < 1:
|
| | 233 | + raise ValueError("Size must be a number between 1 and 256")
|
| | 234 | + if size == 256:
|
| | 235 | + size = 0
|
| | 236 | + return self.lib.monitorcommand(struct.pack("IBBBBII%ds" % size, 9, index, slaveaddr, startaddr, size, 0, 0, data), "III" % size, (None, None, None))
|
| 225 | 237 |
|
| 226 | | - def usbcread(self, size):
|
| 227 | | - """ Reads data with size 'size' from the USB console """
|
| | 238 | + def usbcread(self):
|
| | 239 | + """ Reads one packet with the maximal cin size """
|
| | 240 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| | 241 | + resp = self.lib.monitorcommand(struct.pack("IIII", 10, cin_maxsize, 0, 0), "III%ds" % cin_maxsize, ("validsize", "buffersize", "queuesize", "data"))
|
| | 242 | + resp.data = resp.data[:resp.validsize]
|
| | 243 | + resp.maxsize = cin_maxsize
|
| | 244 | + return resp
|
| 228 | 245 |
|
| 229 | 246 | def usbcwrite(self, data):
|
| 230 | 247 | """ Writes data to the USB console """
|
| | 248 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| | 249 | + size = len(data)
|
| | 250 | + while len(data) > 0:
|
| | 251 | + writesize = min(cin_maxsize, len(data))
|
| | 252 | + resp = self.lib.monitorcommand(struct.pack("IIII%ds" % writesize, 11, writesize, 0, 0, data[:writesize]), "III", ("validsize", "buffersize", "freesize"))
|
| | 253 | + data = data[resp.validsize:]
|
| | 254 | + return size
|
| 231 | 255 |
|
| 232 | | - def cread(self, size, bitmask):
|
| 233 | | - """ Reads data with the specified size from the device consoles
|
| | 256 | + def cread(self, bitmask=0x1):
|
| | 257 | + """ Reads one packet with the maximal cin size from the device consoles
|
| 234 | 258 | identified with the specified bitmask
|
| 235 | 259 | """
|
| | 260 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| | 261 | + resp = self.lib.monitorcommand(struct.pack("IIII", 14, cin_maxsize, 0, 0), "III%ds" % cin_maxsize, ("size", None, None))
|
| | 262 | + resp.data = resp.data[size:]
|
| | 263 | + resp.maxsize = cin_maxsize
|
| | 264 | + return resp
|
| 236 | 265 |
|
| 237 | | - def cwrite(self, data):
|
| | 266 | + def cwrite(self, data, bitmask=0x1):
|
| 238 | 267 | """ Writes data to the device consoles
|
| 239 | 268 | identified with the specified bitmask.
|
| 240 | 269 | """
|
| | 270 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| | 271 | + size = len(data)
|
| | 272 | + while len(data) > 0:
|
| | 273 | + writesize = min(cin_maxsize, len(data))
|
| | 274 | + resp = self.lib.monitorcommand(struct.pack("IIII%ds" % writesize, 13, writesize, 0, 0, data[:writesize]), "III", (None, None, None))
|
| | 275 | + data = data[writesize:]
|
| | 276 | + return size
|
| 241 | 277 |
|
| 242 | 278 | def cflush(self, bitmask):
|
| 243 | 279 | """ Flushes the consoles specified with 'bitmask' """
|
| — | — | @@ -244,7 +280,7 @@ |
| 245 | 281 |
|
| 246 | 282 | def getprocinfo(self):
|
| 247 | 283 | """ Gets current state of the scheduler """
|
| 248 | | - cin_maxsize = self.lib.dev.packetsizelimit["cin"] - 0x10
|
| | 284 | + cin_maxsize = self.lib.dev.packetsizelimit["cin"] - self.lib.headersize
|
| 249 | 285 | # Get the size
|
| 250 | 286 | schedulerstate = self.lockscheduler()
|
| 251 | 287 | resp = self.lib.monitorcommand(struct.pack("IIII", 15, 0, 0, 0), "III", ("structver", "tablesize", None))
|
| — | — | @@ -338,15 +374,15 @@ |
| 339 | 375 | elif threadtype == "system":
|
| 340 | 376 | threadtype = 1
|
| 341 | 377 | else:
|
| 342 | | - raise SyntaxError("Threadtype must be either 'system' or 'user'")
|
| | 378 | + raise ValueError("Threadtype must be either 'system' or 'user'")
|
| 343 | 379 | if priority > 256 or priority < 0:
|
| 344 | | - raise SyntaxError("Priority must be a number between 0 and 256")
|
| | 380 | + raise ValueError("Priority must be a number between 0 and 256")
|
| 345 | 381 | if state == "ready":
|
| 346 | 382 | state = 0
|
| 347 | 383 | elif state == "suspended":
|
| 348 | 384 | state = 1
|
| 349 | 385 | else:
|
| 350 | | - raise SyntaxError("State must be either 'ready' or 'suspended'")
|
| | 386 | + raise ValueError("State must be either 'ready' or 'suspended'")
|
| 351 | 387 | resp = self.lib.monitorcommand(struct.pack("IIIIIIII", 19, nameptr, entrypoint, stackptr, stacksize, threadtype, priority, state), "III", (id, None, None))
|
| 352 | 388 | if resp.id < 0:
|
| 353 | 389 | raise DeviceError("The device returned the error code "+str(resp.id))
|
| — | — | @@ -394,21 +430,19 @@ |
| 395 | 431 |
|
| 396 | 432 |
|
| 397 | 433 | class Lib(object):
|
| 398 | | - def __init__(self, embios):
|
| | 434 | + def __init__(self):
|
| 399 | 435 | self.idVendor = 0xFFFF
|
| 400 | 436 | self.idProduct = 0xE000
|
| 401 | | -
|
| 402 | | - self.embios = embios
|
| 403 | | - self.connected = False
|
| | 437 | +
|
| | 438 | + self.headersize = 0x10
|
| | 439 | +
|
| | 440 | + self.connect()
|
| 404 | 441 |
|
| 405 | 442 | def connect(self):
|
| 406 | 443 | self.dev = Dev(self.idVendor, self.idProduct)
|
| 407 | 444 | self.connected = True
|
| 408 | | - self.embios.getpacketsizeinfo()
|
| 409 | 445 |
|
| 410 | 446 | def monitorcommand(self, cmd, rcvdatatypes=None, rcvstruct=None):
|
| 411 | | - if not self.connected:
|
| 412 | | - self.connect()
|
| 413 | 447 | self.dev.cout(cmd)
|
| 414 | 448 | if rcvdatatypes:
|
| 415 | 449 | rcvdatatypes = "I" + rcvdatatypes # add the response
|
| — | — | @@ -441,7 +475,7 @@ |
| 442 | 476 |
|
| 443 | 477 | self.interface = 0
|
| 444 | 478 | self.timeout = 100
|
| 445 | | -
|
| | 479 | +
|
| 446 | 480 | self.connect()
|
| 447 | 481 | self.findEndpoints()
|
| 448 | 482 |
|
| — | — | @@ -484,13 +518,13 @@ |
| 485 | 519 | def send(self, endpoint, data):
|
| 486 | 520 | size = self.dev.write(endpoint, data, self.interface, self.timeout)
|
| 487 | 521 | if size != len(data):
|
| 488 | | - raise SendError
|
| | 522 | + raise SendError("Not all data was written!")
|
| 489 | 523 | return len
|
| 490 | 524 |
|
| 491 | 525 | def receive(self, endpoint, size):
|
| 492 | 526 | read = self.dev.read(endpoint, size, self.interface, self.timeout)
|
| 493 | 527 | if len(read) != size:
|
| 494 | | - raise ReceiveError
|
| | 528 | + raise ReceiveError("Requested size and read size don't match!")
|
| 495 | 529 | return read
|
| 496 | 530 |
|
| 497 | 531 | def cout(self, data):
|