def _GetFlashId(self, dctl): if self.chipgen == 0: info = [] for ch in [0, 1, 3, 7]: # TODO: send nand reset command first? # 4-byte fid, 2 per channel cdb = [0] * 16 cdb[0] = 0xD0 cdb[1] = ch cdb[2] = 0xF0 cdb[3] = 0x90 cdb[4] = 0xF1 cdb[5] = 1 cdb[6] = 0 cdb[7] = 0xF2 cdb[8] = 4 data = [0] * 512 data = scsi.ScsiRequest(dctl, cdb, data) if _verbose: open("_alc_D0%02X.bin" % ch, "wb+").write(bytearray(data)) info += data[0:16] info += data[0x80:0x80 + 16] return info else: cdb = [0] * 16 cdb[0] = 0xFA cdb[1] = 0 data = [0] * 512 info = scsi.ScsiRequest(dctl, cdb, data) if _verbose: open("_alc_FA00.bin", "wb+").write(bytearray(info)) return info
def _GetFirmwareVersion(self, dctl): version = -1 cdb = scsi.CDB(cdb=[0xFA, 0x0E]) data = [0] * 512 data = scsi.ScsiRequest(dctl, cdb.data, data) if data[6] >= 0xF0: version = (data[6] << 24) | (data[4] << 16) | ( data[5] << 8) | data[7] elif data[6] == 0x36: version = (data[6] << 24) | (data[7] << 16) | ( data[4] << 8) | data[5] else: version = (data[6] << 8) | data[7] data = [0] * 512 * 18 cdb = scsi.CDB(cdb=[0xFA, 0x10]) cdb.PB(2, len(data) / 512).PB(4, 0xC0) data = scsi.ScsiRequest(dctl, cdb.data, data, mayFail=True) if data != None: if _verbose: open("_alc_FA10.bin", "wb+").write(bytearray(data)) if data[0xFFB] == 0x51: version |= data[0xFFA] << 32 else: if _verbose: print("%s: Command 0x%02X%02X failed (norm for old chips)" % (Name(), cdb.data[0], cdb.data[1])) return version
def Detect(self, dctl, force=False): cdb = [0] * 16 cdb[0] = 0x9A data = [0] * 512 info = scsi.ScsiRequest(dctl, cdb, data) if info == None: if _verbose: print("%s: Command 0x%02X failed" % (Name(), cdb[0])) return False if _verbose: open("_alc_9A.bin", "wb+").write(bytearray(info)) self.chipver = info[4] * 256 + info[5] for chip in knownControllers: if chip.Chip == self.chipver: self.chips.append(chip) self.chipgen = chip.Gen if info[0x2B] == 0xAA: self.fwloaded = info[0x2C] != 0 self.fwversionold = info[0x2D] * 256 + info[0x2E] # 0x2E is always zero? if self.chipver in [0x0C0E, 0xAA06]: self.badblocks = info[0x25] elif self.fwloaded: self.badblocks = info[0x25] * 4 return True
def _GetFlashId(self, dctl): cdb = [0] * 12 cdb[0] = 6 cdb[1] = 0x56 # also 4, but unavailable on newer firmwares data = [0] * 512 info = scsi.ScsiRequest(dctl, cdb, data) return info
def _GetFlashId(self, dctl): cdb = [0] * 16 cdb[0] = 0xF0 cdb[1] = 0x06 cdb[11] = 1 # sectors data = [0] * 512 info = scsi.ScsiRequest(dctl, cdb, data) return info
def ProcessDevice(self, dctl, report): cdb = [0] * 16 cdb[0] = 0xFA cdb[1] = 0x0E data = [0] * 512 info = scsi.ScsiRequest(dctl, cdb, data) if info == None: if _verbose: print("%s: Command 0x%02X%02X failed" % (Name(), cdb[0], cdb[1])) else: if _verbose: open("_alc_FA0E.bin", "wb+").write(bytearray(info)) self.chiprev = info[0xB] report.append(("Controller", self.ControllerName())) if self.fwloaded: if self.chipgen == 0: self.fwversion = self.fwversionold self.fwversionstr = "%02d%02d" % (self.fwversionold >> 8, self.fwversionold & 255) else: self.fwversion = self._GetFirmwareVersion(dctl) if self.fwversion <= 0xFFFF: self.fwversionstr = "%04X" % self.fwversion else: self.fwversionstr = "%08X" % (self.fwversion & 0xFFFFFFFF) if (self.fwversion & 0xFF000000) == 0xF0000000: self.fwversionstr += "_%02X" (self.fwversion >> 32) else: self.fwversionstr = "Not loaded" report.append(("Firmware", self.fwversionstr)) flashinfo = self._GetFlashId(dctl) if flashinfo != None: #TODO: 8-byte entries on old versions? flashids = [flashinfo[i * 16:i * 16 + 6] for i in range(8)] # pick a non-zero entry for flash in flashids: if flash[:6] != [0, 0, 0, 0, 0, 0]: break else: flash = flashids[0] report.append(("Flash ID", flash, "fid")) else: report.append(("Flash ID", "Unavailable")) return report
def _GetInfoPage(self, dctl, kind="", size=512 + 16): cdb = [0] * 12 cdb[0] = 6 cdb[1] = 5 if kind != "": for i in range(min(len(kind), 10)): cdb[2 + i] = ord(kind[i]) data = [0] * (size) info = scsi.ScsiRequest(dctl, cdb, data) if info != None: #open("_ph_0605%s.bin"%kind, "wb+").write(bytearray(info)) if _verbose == True: if len(info) == 512 + 16: if info[512] != ord('I') or info[513] != ord('F'): print("* Warning: Strange info page mark") return info
def Detect(self, dctl, force=False): cdb = [0] * 16 cdb[0] = 0xF0 cdb[1] = 0x2A cdb[11] = 1 # sectors data = [0] * 512 info = scsi.ScsiRequest(dctl, cdb, data) if info == None: return False #open("_smi_F02A.bin", "wb+").write(bytearray(info)) if info[0x1AE] == ord('S') and info[0x1AF] == ord('M'): self.model = "".join([chr(x) for x in info[0x1AE:0x1AE + 8] ]).split('\0')[0] self.version = "".join([chr(x) for x in info[0x190:0x1AE]]).split('\0')[0] else: return False return True