diff --git a/CMakeLists.txt b/CMakeLists.txt index 7f26974b..01ec5363 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -39,8 +39,11 @@ add_executable(Bloom src/SignalHandler/SignalHandler.cpp src/DebugToolDrivers/USB/Interface.cpp src/DebugToolDrivers/USB/HID/HidInterface.cpp + src/DebugToolDrivers/Microchip/AtmelICE/AtmelIce.cpp src/DebugToolDrivers/Microchip/PowerDebugger/PowerDebugger.cpp + src/DebugToolDrivers/Microchip/MplabSnap/MplabSnap.cpp + src/DebugToolDrivers/Protocols/CMSIS-DAP/Command.cpp src/DebugToolDrivers/Protocols/CMSIS-DAP/Response.cpp src/DebugToolDrivers/Protocols/CMSIS-DAP/VendorSpecific/EDBG/AVR/AvrCommand.cpp @@ -142,7 +145,8 @@ target_compile_options( PUBLIC -Wconversion PUBLIC -fno-sized-deallocation PUBLIC $<$:-g> - PUBLIC $<$:-Os> + PUBLIC $<$:-O0> +# PUBLIC $<$:-Os> PUBLIC $<$:-O2> PUBLIC $<$:-fno-inline> PUBLIC $<$:-fkeep-static-functions> diff --git a/src/DebugToolDrivers/DebugTools.hpp b/src/DebugToolDrivers/DebugTools.hpp index 9ab06998..fd0216f1 100644 --- a/src/DebugToolDrivers/DebugTools.hpp +++ b/src/DebugToolDrivers/DebugTools.hpp @@ -3,3 +3,4 @@ #include "DebugTool.hpp" #include "src/DebugToolDrivers/Microchip/AtmelICE/AtmelIce.hpp" #include "src/DebugToolDrivers/Microchip/PowerDebugger/PowerDebugger.hpp" +#include "src/DebugToolDrivers/Microchip/MplabSnap/MplabSnap.hpp" diff --git a/src/DebugToolDrivers/Protocols/CMSIS-DAP/VendorSpecific/EDBG/AVR/EdbgAvr8Interface.cpp b/src/DebugToolDrivers/Protocols/CMSIS-DAP/VendorSpecific/EDBG/AVR/EdbgAvr8Interface.cpp index ddac9179..c8047103 100644 --- a/src/DebugToolDrivers/Protocols/CMSIS-DAP/VendorSpecific/EDBG/AVR/EdbgAvr8Interface.cpp +++ b/src/DebugToolDrivers/Protocols/CMSIS-DAP/VendorSpecific/EDBG/AVR/EdbgAvr8Interface.cpp @@ -652,7 +652,11 @@ TargetState EdbgAvr8Interface::getTargetState() { } TargetMemoryBuffer EdbgAvr8Interface::readMemory(Avr8MemoryType type, std::uint32_t address, std::uint32_t bytes) { - if (type == Avr8MemoryType::FLASH_PAGE && this->targetParameters.flashPageSize.value_or(0) > 0) { + if (type == Avr8MemoryType::FLASH_PAGE) { + if (this->targetParameters.flashPageSize.value_or(0) < 1) { + throw Exception("Missing/invalid flash page size parameter"); + } + // Flash reads must be done in pages auto pageSize = this->targetParameters.flashPageSize.value(); @@ -744,40 +748,41 @@ TargetMemoryBuffer EdbgAvr8Interface::readMemory(Avr8MemoryType type, std::uint3 return memoryBuffer; } - } - /* - * EDBG AVR8 debug tools behave in a really weird way when responding with more than two packets - * for a single read memory command. The data they return in this case appears to be of little use. - * - * To address this, we make sure we only issue read memory commands that will result in no more than two - * response packets. For calls that require more than this, we simply split them into numerous calls. - */ - - /* - * The subtraction of 20 bytes here is just to account for any other bytes included in the response - * that isn't actually the memory data (like the command ID, version bytes, etc). I could have sought the - * actual value but who has the time. It won't exceed 20 bytes. Bite me. - */ - auto singlePacketSize = static_cast(this->edbgInterface.getUsbHidInputReportSize() - 20); - auto totalResponsePackets = std::ceil(static_cast(bytes) / static_cast(singlePacketSize)); - auto totalReadsRequired = std::ceil(static_cast(totalResponsePackets) / 2); - - if (totalResponsePackets > 2) { + } else { /* - * This call to readMemory() will result in more than two response packets, so split it into multiple calls - * that will result in no more than two response packets per call. + * EDBG AVR8 debug tools behave in a really weird way when responding with more than two packets + * for a single read (non-flash) memory command. The data they return in this case appears to be of little use. + * + * To address this, we make sure we only issue read memory commands that will result in no more than two + * response packets. For calls that require more than this, we simply split them into numerous calls. */ - auto output = std::vector(); - for (float i = 1; i <= totalReadsRequired; i++) { - auto bytesToRead = static_cast((bytes - output.size()) > (singlePacketSize * 2) ? - (singlePacketSize * 2) : bytes - output.size()); - auto data = this->readMemory(type, static_cast(address + output.size()), bytesToRead); - output.insert(output.end(), data.begin(), data.end()); + /* + * The subtraction of 20 bytes here is just to account for any other bytes included in the response + * that isn't actually the memory data (like the command ID, version bytes, etc). I could have sought the + * actual value but who has the time. It won't exceed 20 bytes. Bite me. + */ + auto singlePacketSize = static_cast(this->edbgInterface.getUsbHidInputReportSize() - 20); + auto totalResponsePackets = std::ceil(static_cast(bytes) / static_cast(singlePacketSize)); + auto totalReadsRequired = std::ceil(static_cast(totalResponsePackets) / 2); + + if (totalResponsePackets > 2) { + /* + * This call to readMemory() will result in more than two response packets, so split it into multiple calls + * that will result in no more than two response packets per call. + */ + auto output = std::vector(); + + for (float i = 1; i <= totalReadsRequired; i++) { + auto bytesToRead = static_cast((bytes - output.size()) > (singlePacketSize * 2) ? + (singlePacketSize * 2) : bytes - output.size()); + auto data = this->readMemory(type, static_cast(address + output.size()), bytesToRead); + output.insert(output.end(), data.begin(), data.end()); + } + + return output; } - - return output; } auto commandFrame = CommandFrames::Avr8Generic::ReadMemory(); diff --git a/src/TargetController/TargetController.hpp b/src/TargetController/TargetController.hpp index 4353b4bc..c5c57bfa 100644 --- a/src/TargetController/TargetController.hpp +++ b/src/TargetController/TargetController.hpp @@ -85,6 +85,12 @@ namespace Bloom return std::make_unique(); } }, + { + "snap", + []() -> std::unique_ptr { + return std::make_unique(); + } + }, }; }