def _entry_generator(self, data): idx = 0 while True: name = extract_string(data, idx + 10) if not name: raise StopIteration() entry = FSEntry(name, attributes=data[idx:idx + 1], size=le32toi(data[idx + 2:idx + 6]), timestamp=le32toi(data[idx + 6:idx + 10])) idx += entry.entry_size yield entry
def from_out_packet(data): if not isinstance(data, array): data = array('B', data) assert len(data) >= 0x40 request_size = data[0:4] cmd1 = data[0x44] cmd2 = data[0x47] cmd3 = le32toi(data, 4) serial = data[0x4c:0x50] return CanonUSBCommand(cmd1, cmd2, cmd3, serial, data[0x50:])
def response_length(self): """Extract resplen from the response header For cmd3=0x201 (fixed response length) commands word at 0x00 is response length excluding the first 0x40, as well as the word at 0x48, the header of the next layer? """ if not self.response_header: raise CanonError("_send() this command first.") return le32toi(self.response_header, 0)
def _parse_response(self, data): struct_size = le16toi(data, 0x14) model_id = le32toi(data[0x16:0x1a]) camera_name = extract_string(data, 0x1a) num_entries = le32toi(data, 0x3a) _log.info("abilities of {} (0x{:x}): 0x{:x} long, n={}".format( camera_name, model_id, struct_size, num_entries)) offset = 0x3e abilities = [] for i in xrange(num_entries): name = extract_string(data, offset) height = le32toi(data, offset + 20) width = le32toi(data, offset + 24) idx = le32toi(data, offset + 28) _log.info(" {:-3} - 0x{:04x} {:20} {}x{}".format( i, idx, name, width, height)) offset += 32 abilities.append((idx, name, height, width)) return abilities
def from_command_packet(data): """Return a command instance from a command packet. This is used for parsing sniffed USB traffic. """ if not isinstance(data, array): data = array('B', data) assert len(data) >= 0x40 request_size = data[0:4] cmd1 = data[0x44] cmd2 = data[0x47] cmd3 = le32toi(data, 4) serial = data[0x4c:0x50]
def _reader(self, usb, first_chunk): remaining = self._correct_resplen(len(first_chunk)) if len(first_chunk) < 0x0c: # need another chunk to get to the response length chunk_len = self.next_chunk_size(remaining) first_chunk.extend(usb.bulk_read(chunk_len)) remaining -= chunk_len assert len(first_chunk) >= 0x0c # word at 0x50 is status byte self.status = le32toi(first_chunk, 0x10) _log.info("<-- {0.name:s} #{1:0} status: 0x{2:x} ".format( self, self.serial & 0x0000ffff, self.status)) yield first_chunk for chunk_size in self.chunk_sizes(remaining): yield usb.bulk_read(chunk_size)
def response_length(self): """Return the response length, excluding the first 0x40 bytes. """ if not self.response_header: raise CanonError("_send() this command first.") return le32toi(self.response_header, 6)
def _parse_response(self, data): return le32toi(data, 0x14)