public void ReadEEPROM(BootloaderClient endpoint, MemoryMap dest) { Console.CursorVisible = false; Console.Write(" Reading EEPROM memory ({0}kB): ", dest.Size / 1024); ConsoleProgressBar cpb = new ConsoleProgressBar(0, dest.Size); for (uint addr = 0; addr < dest.Size; addr += 128, cpb.Progress = addr) { Message msg_readpage = new Message(endpoint.BootloaderAddress, MessageType.ReadEepromPage, new byte[] { (byte)(addr & 0xFF), (byte)(addr >> 8), }); Message response = SendAndWaitForResponse(endpoint, msg_readpage, 2000); dest.Write(addr, response.Payload, 0, 128); } Console.CursorVisible = true; Console.WriteLine("Done."); }
public bool BinaryCompare(MemoryMap mmread, ref uint difference_address) { if (mmread.Size != this.Size) { difference_address = uint.MaxValue; //todo other method for extracting this information return(false); // size don't match } for (uint i = 0; i < this.Size; i++) { if (mmread.mem[i] != this.mem[i]) { difference_address = i; return(false); } } return(true); }
public void WriteFLASH(BootloaderClient endpoint, MemoryMap source) { Console.CursorVisible = false; Console.Write(" Writing FLASH memory ({0}kB): ", source.Size / 1024); ConsoleProgressBar cpb = new ConsoleProgressBar(0, source.Size); for (uint addr = 0; addr < source.Size; addr += 128, cpb.Progress = addr) { byte[] payload = new byte[2 + 128]; payload[0] = (byte)(addr & 0xFF); payload[1] = (byte)((addr >> 8) & 0xFF); source.Read(addr, payload, 2, 128); Message msg_write = new Message(endpoint.BootloaderAddress, MessageType.WriteFlashPage, payload); Message response = SendAndWaitForResponse(endpoint, msg_write, 2000); } Console.CursorVisible = true; Console.WriteLine("Done."); }
public bool VerifyEEPROM(BootloaderClient endpoint, MemoryMap expected) { Console.CursorVisible = false; Console.Write(" Verifying EEPROM memory ({0}kB): ", expected.Size / 1024); ConsoleProgressBar cpb = new ConsoleProgressBar(0, expected.Size); MemoryMap mmread = new MemoryMap(expected.Size); for (uint addr = 0; addr < expected.Size; addr += 128, cpb.Progress = addr) { Message msg_readpage = new Message(endpoint.BootloaderAddress, MessageType.ReadEepromPage, new byte[] { (byte)(addr & 0xFF), (byte)(addr >> 8), }); Message response = SendAndWaitForResponse(endpoint, msg_readpage, 2000); mmread.Write(addr, response.Payload, 0, 128); } UInt32 difference_address = 0; bool result = expected.BinaryCompare(mmread, ref difference_address); Console.CursorVisible = true; if (result) { Console.WriteLine("Correct."); } else { Console.ForegroundColor = ConsoleColor.Red; Console.WriteLine("Failed."); Console.ForegroundColor = ConsoleColor.Gray; byte expected_byte = expected.ReadByte(difference_address); byte existing_byte = mmread.ReadByte(difference_address); throw new MemoryVerificationException("FLASH", difference_address, expected_byte, existing_byte); } return(result); }
static void Main(string[] args) { ShowIntro(); random = new Random(); BootloaderJobsLoader btp = new BootloaderJobsLoader(); Console.WriteLine($"Reading task file..."); try { btp.LoadTasks("bootloader_tasks_real.json"); } catch (Exception ex) { ColorConsole.WriteLine(ConsoleColor.Red, "Error druing reading: " + ex.Message); } // Find highest bootloader id byte[] addresses_to_check = btp.Jobs.Where(x => x.BootloaderID.HasValue).Select(x => x.BootloaderID.Value).Distinct().ToArray(); // Show some summary Console.WriteLine($"Task summary:"); Console.WriteLine($" Found {btp.Count} task(s)."); Console.WriteLine($" Highest bootloader ID: 0x{addresses_to_check.Max():X2}"); Console.WriteLine($" Unique bootloaders (by ID): {btp.Jobs.Select(x => x.BootloaderID).Where(x => x.HasValue).Distinct().Count()}"); Console.WriteLine($" Unique bootloaders: {string.Join(",", addresses_to_check.Select(x => "0x" + x.ToString("X2")).Distinct())}"); // // Wait for all serial ports to be connected and identified AVRBootloaderCnC cnc = new AVRBootloaderCnC(); cnc.SendAdvertisementToEveryDetectedPort(); // Scan all available serial ports for bootloaders cnc.AcquireBootloaderDevicesInParallel(addresses_to_check); // show found devices cnc.ShowDevices(); for (int job_index = 0; job_index < btp.Count; job_index++) { JobEntry job_entry = btp.Jobs[job_index]; JobTypeDescriptor job_type_descriptor = JobTypeDescriptorCollection.GetDescriptor(job_entry.JobType); ColorConsole.WriteLine(ConsoleColor.Cyan, $"Running task {job_index}: {job_entry.JobType} for device {job_entry.CPU} ID={job_entry.BootloaderID:X2}..."); // Get the device BootloaderClient device = cnc.Devices.Where(x => x.BootloaderAddress == job_entry.BootloaderID).FirstOrDefault(); if (device == null && job_type_descriptor.IsPhysicalDeviceNeeded) { ColorConsole.WriteLine(ConsoleColor.Yellow, " No proper device found."); continue; } if (job_entry.JobType == JobType.ReadEepromMemory) { MemoryMap mm = new MemoryMap(job_entry.ProgrammableMemorySize); cnc.ReadEEPROM(device, mm); IntelHEX16Storage storage = new IntelHEX16Storage(mm); storage.Save(job_entry.FileName); } if (job_entry.JobType == JobType.ReadFlashMemory) { MemoryMap mm = new MemoryMap(job_entry.ProgrammableMemorySize); cnc.ReadFLASH(device, mm); IntelHEX16Storage storage = new IntelHEX16Storage(mm); storage.Save(job_entry.FileName); } if (job_entry.JobType == JobType.WriteEepromMemory) { FileInfo fi = new FileInfo(job_entry.FileName); MemoryMap mm = new MemoryMap(job_entry.ProgrammableMemorySize); IntelHEX16Storage storage = new IntelHEX16Storage(mm); storage.Load(fi.FullName); Console.WriteLine($" File name: {fi.FullName}"); Console.WriteLine($" Modified.: {fi.LastWriteTime}"); cnc.WriteEEPROM(device, mm); } if (job_entry.JobType == JobType.WriteFlashMemory) { FileInfo fi = new FileInfo(job_entry.FileName); MemoryMap mm = new MemoryMap(job_entry.ProgrammableMemorySize); IntelHEX16Storage storage = new IntelHEX16Storage(mm); storage.Load(fi.FullName); Console.WriteLine($" File name: {fi.FullName}"); Console.WriteLine($" Modified.: {fi.LastWriteTime}"); cnc.WriteFLASH(device, mm); } if (job_entry.JobType == JobType.Reboot) { cnc.Reboot(device); } if (job_entry.JobType == JobType.WaitForKey) { if (!string.IsNullOrEmpty(job_entry.WaitForKeyMessage)) { ColorConsole.PressAnyKey(job_entry.WaitForKeyMessage); } else { ColorConsole.PressAnyKey(); } } if (job_entry.JobType == JobType.ReadBootloaderVersion) { string ver = ""; cnc.ReadBootloaderVersion(device, ref ver); } } ColorConsole.PressAnyKey(); }
static void ___________Main(string[] args) { Console.WriteLine("SmartTable bootloader C&C software by Tomasz Jaworski"); random = new Random(); //MemoryMap mm = new MemoryMap(0x10000); // IntelHEX16Storage st = new IntelHEX16Storage(mm); // st.Load(@"d:\praca\projekty\SmartTable\atmega328p-rs485-bootloader\Debug\atmega328p_bootloader.hex"); // mm.Dump("test.txt"); //if (SerialPort.GetPortNames().Length == 0) { // Console.WriteLine("No serial ports available, quitting..."); // return; //} AVRBootloaderCnC cnc = new AVRBootloaderCnC(); cnc.SendAdvertisementToEveryDetectedPort(); cnc.AcquireBootloaderDevices(0x20); // show found devices cnc.ShowDevices(); Console.WriteLine("Reading bootloader version and signature"); foreach (Device dev in cnc.Devices) { Console.WriteLine("Reading device {0:X2}... ", dev.address); // read bootloader version and timestamp string ver = ""; cnc.ReadVersion(dev, ref ver); // read CPU signature byte[] bsig = null; cnc.ReadSignature(dev, out bsig); } #region DEMO 1 - Download EEPROM from all found devices Console.WriteLine("Reading EEPROM and Flash memories..."); foreach (Device dev in cnc.Devices) { Console.WriteLine("Reading device {0:X2}... ", dev.address); // read eeprom MemoryMap mm = new MemoryMap(1024); cnc.ReadEEPROM(dev, mm); string fname = string.Format("eeprom_{0:X2}", dev.address); mm.Dump(fname + ".txt", DumpMode.Text); mm.Dump(fname + ".bin", DumpMode.Binary); // read flash mm = new MemoryMap(32 * 1024); cnc.ReadFLASH(dev, mm); fname = string.Format("flash_{0:X2}", dev.address); mm.Dump(fname + ".txt", DumpMode.Text); mm.Dump(fname + ".bin", DumpMode.Binary); } #endregion #region DEMO 2 - Increment a counter in eeprom (@ 0x0A) and in flash (@ 0x0100) /* * Console.WriteLine("Reading EEPROM and Flash memories..."); * * foreach (Device dev in cnc.Devices) { * Console.WriteLine("Reading device {0:X2}... ", dev.address); * * // read eeprom * MemoryMap mm = new MemoryMap(1024); * cnc.ReadEEPROM(dev, mm); * * UInt16 a = mm.ReadUInt16(10); * if (a == 0xffff) * a = 0; * else * a++; * mm.Write(10, a); * cnc.WriteEEPROM(dev, mm); * Console.WriteLine("A=" + a.ToString()); * } * * * foreach (Device dev in cnc.Devices) { * Console.WriteLine("Reading device {0:X2}... ", dev.address); * * // read eeprom * MemoryMap mm = new MemoryMap(32*1024); * cnc.ReadFLASH(dev, mm); * * UInt16 a = mm.ReadUInt16(0x100); * if (a == 0xffff) * a = 0; * else * a++; * mm.Write(0x100, a); * cnc.WriteFLASH(dev, mm); * Console.WriteLine("A=" + a.ToString()); * } */ #endregion #region DEMO 3 - fill eeprom and flash with random data /* * foreach (Device dev in cnc.Devices) { * // read eeprom * MemoryMap mm = new MemoryMap(1024); * for (uint i = 0; i < 1024; i++) * mm.Write(i, (byte)random.Next()); * * cnc.WriteEEPROM(dev, mm); * string fname = string.Format("eeprom_random_written_{0:X2}", dev.address); * mm.Dump(fname + ".txt", DumpMode.Text); * mm.Dump(fname + ".bin", DumpMode.Binary); * * mm.Zero(); * * cnc.ReadEEPROM(dev, mm); * fname = string.Format("eeprom_random_read_{0:X2}", dev.address); * mm.Dump(fname + ".txt", DumpMode.Text); * mm.Dump(fname + ".bin", DumpMode.Binary); * } * * foreach (Device dev in cnc.Devices) { * // read eeprom * MemoryMap mm = new MemoryMap(32*1024); * for (uint i = 0; i < mm.Size; i++) * mm.Write(i, (byte)random.Next()); * * cnc.WriteFLASH(dev, mm); * string fname = string.Format("flash_random_written_{0:X2}", dev.address); * mm.Dump(fname + ".txt", DumpMode.Text); * mm.Dump(fname + ".bin", DumpMode.Binary); * * mm.Zero(); * * cnc.ReadFLASH(dev, mm); * fname = string.Format("flash_random_read_{0:X2}", dev.address); * mm.Dump(fname + ".txt", DumpMode.Text); * mm.Dump(fname + ".bin", DumpMode.Binary); * } */ #endregion /* * List<SerialPort> ports = ListAndOpenSerialPorts(); * * // send advertisement to all devices, co they can stay in bootloader mode * SendAdvertisement(ports); * * // purge buffers * PurgeSerialPorts(ports); * * List<Device> endpoints = new List<Device>(); */ /* * // get list of devices for each serial port * foreach (SerialPort sp in ports) * AcquireDevicesOnSerialPort(endpoints, sp); * * // show discovered devices * ShowDevices(endpoints.ToArray()); */ //endpoints.Add(new Device(ports[0], 0x51)); /* MemoryMap eeprom = new MemoryMap(1024); * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom1a.txt"); * eeprom.Write(123, eeprom.ReadInt16(123) + 123); * WriteEEPROM(endpoints[0], eeprom); * VerifyEEPROM(endpoints[0], eeprom); * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom2a.txt"); * * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom1b.txt"); * eeprom.Write(123, eeprom.ReadInt16(123) + 123); * WriteEEPROM(endpoints[0], eeprom); * VerifyEEPROM(endpoints[0], eeprom); * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom2b.txt"); * * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom1c.txt"); * eeprom.Write(123, eeprom.ReadInt16(123) + 123); * WriteEEPROM(endpoints[0], eeprom); * eeprom.Write(400, 99); * VerifyEEPROM(endpoints[0], eeprom); * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom2c.txt"); * * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom1d.txt"); * eeprom.Write(123, eeprom.ReadInt16(123) + 123); * WriteEEPROM(endpoints[0], eeprom); * VerifyEEPROM(endpoints[0], eeprom); * ReadEEPROM(endpoints[0], eeprom); * eeprom.Dump("eeprom2d.txt"); */ //byte[] sig; //ReadSignature(endpoints[0], out sig); }
public void LoadTasks(string taskDescriptionFile) { // Read tasks Jobs.JobEntryCollection collection = null; try { string content = File.ReadAllText(taskDescriptionFile); collection = JsonConvert.DeserializeObject <Jobs.JobEntryCollection>(content); } catch (IOException ioex) { throw new BootloaderException($"Job list load error: {ioex.Message}", ioex); } catch (JsonException jex) { throw new BootloaderException($"Job list parsing error: {jex.Message}", jex); } // Verify jobs for (int i = 0; i < collection.Jobs.Length; i++) { JobEntry task = collection.Jobs[i]; try { //todo: refactorize if (task.JobType == JobType.WriteEepromMemory) { //TODO: replace fake load into fake memory with a clear verification procedure MemoryMap mm = new MemoryMap(task.ProgrammableMemorySize); IntelHEX16Storage s = new IntelHEX16Storage(mm); s.Load(task.FileName); } if (task.JobType == JobType.WriteFlashMemory) { //TODO: replace fake load into fake memory with a clear verification procedure MemoryMap mm = new MemoryMap(task.ProgrammableMemorySize); IntelHEX16Storage s = new IntelHEX16Storage(mm); s.Load(task.FileName); } if (task.JobType == JobType.ReadFlashMemory || task.JobType == JobType.ReadEepromMemory) { //TODO: replace fake load into fake memory with a clear verification procedure // MemoryMap mm = new MemoryMap(task.ProgrammableMemorySize); // IntelHEX16Storage s = new IntelHEX16Storage(mm); //s.Load(task.FileName); } if (task.JobType == JobType.Reboot) { //? } } catch (Exception ex) { throw new BootloaderException($"Job verification failed ({task.JobType}, task #{i}): {ex.Message}", ex); } } // Seems ok this.jobs = collection.Jobs; }