From 0e10e4b691e4ec897e277c30fe5e49b3999d5527 Mon Sep 17 00:00:00 2001 From: Per Kristian Schanke Date: Wed, 15 Nov 2017 11:02:27 +0100 Subject: [PATCH] Update in accordance to review. --- nrfjprog/include/nrfjprog.h | 72 ++++---- src/highlevel.cpp | 157 ++++++++--------- src/highlevel.h | 1 + src/nrfjprogwrapper.cpp | 333 ++++++++---------------------------- src/rtt.cpp | 252 +++++++++++++++------------ src/rtt.h | 11 +- src/rtt_batons.h | 36 ++-- src/utility/conversion.cpp | 57 +----- src/utility/conversion.h | 6 +- 9 files changed, 351 insertions(+), 574 deletions(-) diff --git a/nrfjprog/include/nrfjprog.h b/nrfjprog/include/nrfjprog.h index c593588d..86b12def 100644 --- a/nrfjprog/include/nrfjprog.h +++ b/nrfjprog/include/nrfjprog.h @@ -42,34 +42,34 @@ #define micro_version (1) - enum NrfjprogErrorCodesType { +enum NrfjprogErrorCodesType { - Success = 0, // Requested operation (operations) were successfully completed. + Success = 0, // Requested operation (operations) were successfully completed. - /* nrfjprog.exe or PC errors */ - NrfjprogError = 1, // An error condition that should not occur has happened. + /* nrfjprog.exe or PC errors */ + NrfjprogError = 1, // An error condition that should not occur has happened. // It is most probably a bug in nrfjprog.exe or nrfjprog.dll. - NrfjprogOutdatedError = 2, // Nrfjprog version is too old for the device - MemoryAllocationError = 3, // Memory allocation for nrfjprog failed failed. + NrfjprogOutdatedError = 2, // Nrfjprog version is too old for the device + MemoryAllocationError = 3, // Memory allocation for nrfjprog failed failed. - /* Command line input errors */ + /* Command line input errors */ InvalidArgumentError = 11, // Invalid arguments passed to the application. InsufficientArgumentsError = 12, // Needed arguments not passed to the application. IncompatibleArgumentsError = 13, // Incompatible arguments passed to the application. DuplicatedArgumentsError = 14, // The same argument has been provided twice. - NoOperationError = 15, // The arguments passed do not perform a valid operation. - UnavailableOperationBecauseProtectionError = 16, // The operation attempted can not be performed because either the main-ap or the ctrl-ap is not available. - UnavailableOperationInFamilyError = 17, // The operation attempted can not be performed in the device because the feature is lacking in your device. - WrongFamilyForDeviceError = 18, // The --family option given with the command (or the default from nrfjprog.ini) does not match the device connected. + NoOperationError = 15, // The arguments passed do not perform a valid operation. + UnavailableOperationBecauseProtectionError = 16, // The operation attempted can not be performed because either the main-ap or the ctrl-ap is not available. + UnavailableOperationInFamilyError = 17, // The operation attempted can not be performed in the device because the feature is lacking in your device. + WrongFamilyForDeviceError = 18, // The --family option given with the command (or the default from nrfjprog.ini) does not match the device connected. UnavailableOperationBecauseMpuConfiguration = 19, // For nRF51, --eraseuicr is unavailable unless the device came with an ANT softdevice programmed at Nordic factory. - /* nrfjprog.dll errors */ + /* nrfjprog.dll errors */ NrfjprogDllNotFoundError = 20, // Unable to find nrfjprog.dll in the installation folder. Reinstall nrfjprog. NrfjprogDllLoadFailedError = 21, // Failed to Load nrfjprog.dll NrfjprogDllFunctionLoadFailedError = 22, // Failed to Load the functions from nrfjprog.dll - NrfjprogDllNotImplementedError = 23, // Dll still does not implement this function for your device. + NrfjprogDllNotImplementedError = 23, // Dll still does not implement this function for your device. /* nrfjprog.ini errors */ NrfjprogIniSyntaxError = 24, // Syntax error in nrfjprog.ini file @@ -78,30 +78,30 @@ NrfjprogIniFamilyMissingError = 27, // Family parameter cannot be parsed from ini file. Line might be deleted or invalid format. NrfjprogIniClockspeedMissingError = 28, // Clockspeed parameter cannot be parsed from ini file. Line might be deleted or invalid format. - /* JLinkARM.dll errors */ + /* JLinkARM.dll errors */ JLinkARMDllNotFoundError = 30, // Unable to find install path for JLink software - JLinkARMDllInvalidError = 31, // Dll found does not seem a valid dll. - JLinkARMDllFailedToOpenError = 32, // Dll could not be opened. - JLinkARMDllError = 33, // Dll reported error. - JLinkARMDllTooOldError = 34, // Dll is too old for functionality. Install a newer version of JLinkARM.dll + JLinkARMDllInvalidError = 31, // Dll found does not seem a valid dll. + JLinkARMDllFailedToOpenError = 32, // Dll could not be opened. + JLinkARMDllError = 33, // Dll reported error. + JLinkARMDllTooOldError = 34, // Dll is too old for functionality. Install a newer version of JLinkARM.dll - /* Emulator errors */ + /* Emulator errors */ InvalidSerialNumberError = 40, // Serial number provided is not among those connected. NoDebuggersError = 41, // There are no debuggers connected to the PC. - NotPossibleToConnectError = 42, // Not possible to connect to the NRF device. - LowVoltageError = 43, // Low voltage detected at target device. + NotPossibleToConnectError = 42, // Not possible to connect to the NRF device. + LowVoltageError = 43, // Low voltage detected at target device. - /* General errors */ + /* General errors */ FileNotFoundError = 51, // Unable to find the given file. - InvalidHexFileError = 52, // File specified does not seem a valid hex file. - FicrReadError = 53, // FICR read failed. - WrongArgumentError = 54, // One of the arguments is wrong. Path does not exist, memory access is not aligned... - VerifyError = 55, // The write verify operation failed. - NoWritePermissionError = 56, // Unable to create file in the current working directory. - NVMCOperationError = 57, // The flash operation in the device failed. - FlashNotErasedError = 58, // A program operation failed because the area to write was not erased. - RamIsOffError = 59, // The RAM area to read or write is unpowered. - NoReadPermissionError = 60, // Unable to open file for read. + InvalidHexFileError = 52, // File specified does not seem a valid hex file. + FicrReadError = 53, // FICR read failed. + WrongArgumentError = 54, // One of the arguments is wrong. Path does not exist, memory access is not aligned... + VerifyError = 55, // The write verify operation failed. + NoWritePermissionError = 56, // Unable to create file in the current working directory. + NVMCOperationError = 57, // The flash operation in the device failed. + FlashNotErasedError = 58, // A program operation failed because the area to write was not erased. + RamIsOffError = 59, // The RAM area to read or write is unpowered. + NoReadPermissionError = 60, // Unable to open file for read. NoExternalMemoryConfiguredError = 61, // A QSPI operation is attempted without an external memory configured. RecoverFailed = 62, // Recovery failed. @@ -112,11 +112,11 @@ NrfjprogQspiIniParsingError = 73, // QSPI ini file parsed has one or more missing keys. NrfjprogQspiIniCustomMissingError = 74, // QSPI ini file parsed has no custom instructions specified, but option --qspicustominit option was given. - /* Warning. Will not be returned by nrfjprog but used to generate warnings. */ - FicrOperationWarning = 100, // FICR operation. It is important to be certain of what you do. - UnalignedPageEraseWarning = 101, // Address provided with page erase is not aligned to first address of page. - NoLogWarning = 102, // No log is possible because the program has no write permission in the current directory. - UicrWriteOperationWithoutEraseWarning = 103, // A UICR write operation is requested but there has not been a UICR erase. + /* Warning. Will not be returned by nrfjprog but used to generate warnings. */ + FicrOperationWarning = 100, // FICR operation. It is important to be certain of what you do. + UnalignedPageEraseWarning = 101, // Address provided with page erase is not aligned to first address of page. + NoLogWarning = 102, // No log is possible because the program has no write permission in the current directory. + UicrWriteOperationWithoutEraseWarning = 103, // A UICR write operation is requested but there has not been a UICR erase. VeryLongOperationWarning = 104 // An operation that might take up to several minutes is been execued. Please wait. }; diff --git a/src/highlevel.cpp b/src/highlevel.cpp index 8e0264e5..78883c00 100644 --- a/src/highlevel.cpp +++ b/src/highlevel.cpp @@ -417,6 +417,78 @@ void HighLevel::init(v8::Local tpl) Nan::SetPrototypeMethod(tpl, "close", CloseDevice); } +void HighLevel::initConsts(Nan::ADDON_REGISTER_FUNCTION_ARGS_TYPE target) +{ + NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAA_REV1); + NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAA_REV2); + NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAA_REV3); + NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAB_REV3); + NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAC_REV3); + NODE_DEFINE_CONSTANT(target, NRF51802_xxAA_REV3); + NODE_DEFINE_CONSTANT(target, NRF51801_xxAB_REV3); + NODE_DEFINE_CONSTANT(target, NRF51_XLR1); + NODE_DEFINE_CONSTANT(target, NRF51_XLR2); + NODE_DEFINE_CONSTANT(target, NRF51_XLR3); + NODE_DEFINE_CONSTANT(target, NRF51_L3); + NODE_DEFINE_CONSTANT(target, NRF51_XLR3P); + NODE_DEFINE_CONSTANT(target, NRF51_XLR3LC); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_ENGA); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_ENGB); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_REV1); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_REV2); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_FUTURE); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAB_REV1); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAB_REV2); + NODE_DEFINE_CONSTANT(target, NRF52832_xxAB_FUTURE); + NODE_DEFINE_CONSTANT(target, NRF52840_xxAA_ENGA); + NODE_DEFINE_CONSTANT(target, NRF52840_xxAA_FUTURE); + NODE_DEFINE_CONSTANT(target, NRF52810_xxAA_REV1); + NODE_DEFINE_CONSTANT(target, NRF52810_xxAA_FUTURE); + NODE_DEFINE_CONSTANT(target, NRF52_FP1_ENGA); + NODE_DEFINE_CONSTANT(target, NRF52_FP1_ENGB); + NODE_DEFINE_CONSTANT(target, NRF52_FP1); + NODE_DEFINE_CONSTANT(target, NRF52_FP1_FUTURE); + NODE_DEFINE_CONSTANT(target, NRF52_FP2_ENGA); + + NODE_DEFINE_CONSTANT(target, NRF51_FAMILY); + NODE_DEFINE_CONSTANT(target, NRF52_FAMILY); + NODE_DEFINE_CONSTANT(target, UNKNOWN_FAMILY); + + NODE_DEFINE_CONSTANT(target, ERASE_NONE); + NODE_DEFINE_CONSTANT(target, ERASE_ALL); + NODE_DEFINE_CONSTANT(target, ERASE_PAGES); + NODE_DEFINE_CONSTANT(target, ERASE_PAGES_INCLUDING_UICR); + + NODE_DEFINE_CONSTANT(target, JsSuccess); + NODE_DEFINE_CONSTANT(target, CouldNotFindJlinkDLL); + NODE_DEFINE_CONSTANT(target, CouldNotFindJprogDLL); + NODE_DEFINE_CONSTANT(target, CouldNotLoadDLL); + NODE_DEFINE_CONSTANT(target, CouldNotOpenDevice); + NODE_DEFINE_CONSTANT(target, CouldNotOpenDLL); + NODE_DEFINE_CONSTANT(target, CouldNotConnectToDevice); + NODE_DEFINE_CONSTANT(target, CouldNotCallFunction); + NODE_DEFINE_CONSTANT(target, CouldNotErase); + NODE_DEFINE_CONSTANT(target, CouldNotProgram); + NODE_DEFINE_CONSTANT(target, CouldNotRead); + NODE_DEFINE_CONSTANT(target, CouldNotOpenHexFile); + + NODE_DEFINE_CONSTANT(target, RESET_NONE); + NODE_DEFINE_CONSTANT(target, RESET_SYSTEM); + NODE_DEFINE_CONSTANT(target, RESET_DEBUG); + NODE_DEFINE_CONSTANT(target, RESET_PIN); + + NODE_DEFINE_CONSTANT(target, ERASE_NONE); + NODE_DEFINE_CONSTANT(target, ERASE_ALL); + NODE_DEFINE_CONSTANT(target, ERASE_PAGES); + NODE_DEFINE_CONSTANT(target, ERASE_PAGES_INCLUDING_UICR); + + NODE_DEFINE_CONSTANT(target, VERIFY_NONE); + NODE_DEFINE_CONSTANT(target, VERIFY_READ); + + NODE_DEFINE_CONSTANT(target, INPUT_FORMAT_HEX_FILE); + NODE_DEFINE_CONSTANT(target, INPUT_FORMAT_HEX_STRING); +} + NAN_METHOD(HighLevel::GetDllVersion) { parse_parameters_function_t p = [&] (Nan::NAN_METHOD_ARGS_TYPE parameters, int &argumentCount) -> Baton* { @@ -850,88 +922,3 @@ NAN_METHOD(HighLevel::CloseDevice) CallFunction(info, p, e, nullptr, true); } - -#include "rtt.h" - -extern "C" { - void initConsts(Nan::ADDON_REGISTER_FUNCTION_ARGS_TYPE target) - { - NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAA_REV1); - NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAA_REV2); - NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAA_REV3); - NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAB_REV3); - NODE_DEFINE_CONSTANT(target, NRF51xxx_xxAC_REV3); - NODE_DEFINE_CONSTANT(target, NRF51802_xxAA_REV3); - NODE_DEFINE_CONSTANT(target, NRF51801_xxAB_REV3); - NODE_DEFINE_CONSTANT(target, NRF51_XLR1); - NODE_DEFINE_CONSTANT(target, NRF51_XLR2); - NODE_DEFINE_CONSTANT(target, NRF51_XLR3); - NODE_DEFINE_CONSTANT(target, NRF51_L3); - NODE_DEFINE_CONSTANT(target, NRF51_XLR3P); - NODE_DEFINE_CONSTANT(target, NRF51_XLR3LC); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_ENGA); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_ENGB); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_REV1); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_REV2); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAA_FUTURE); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAB_REV1); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAB_REV2); - NODE_DEFINE_CONSTANT(target, NRF52832_xxAB_FUTURE); - NODE_DEFINE_CONSTANT(target, NRF52840_xxAA_ENGA); - NODE_DEFINE_CONSTANT(target, NRF52840_xxAA_FUTURE); - NODE_DEFINE_CONSTANT(target, NRF52810_xxAA_REV1); - NODE_DEFINE_CONSTANT(target, NRF52810_xxAA_FUTURE); - NODE_DEFINE_CONSTANT(target, NRF52_FP1_ENGA); - NODE_DEFINE_CONSTANT(target, NRF52_FP1_ENGB); - NODE_DEFINE_CONSTANT(target, NRF52_FP1); - NODE_DEFINE_CONSTANT(target, NRF52_FP1_FUTURE); - NODE_DEFINE_CONSTANT(target, NRF52_FP2_ENGA); - - NODE_DEFINE_CONSTANT(target, NRF51_FAMILY); - NODE_DEFINE_CONSTANT(target, NRF52_FAMILY); - NODE_DEFINE_CONSTANT(target, UNKNOWN_FAMILY); - - NODE_DEFINE_CONSTANT(target, ERASE_NONE); - NODE_DEFINE_CONSTANT(target, ERASE_ALL); - NODE_DEFINE_CONSTANT(target, ERASE_PAGES); - NODE_DEFINE_CONSTANT(target, ERASE_PAGES_INCLUDING_UICR); - - NODE_DEFINE_CONSTANT(target, JsSuccess); - NODE_DEFINE_CONSTANT(target, CouldNotFindJlinkDLL); - NODE_DEFINE_CONSTANT(target, CouldNotFindJprogDLL); - NODE_DEFINE_CONSTANT(target, CouldNotLoadDLL); - NODE_DEFINE_CONSTANT(target, CouldNotOpenDevice); - NODE_DEFINE_CONSTANT(target, CouldNotOpenDLL); - NODE_DEFINE_CONSTANT(target, CouldNotConnectToDevice); - NODE_DEFINE_CONSTANT(target, CouldNotCallFunction); - NODE_DEFINE_CONSTANT(target, CouldNotErase); - NODE_DEFINE_CONSTANT(target, CouldNotProgram); - NODE_DEFINE_CONSTANT(target, CouldNotRead); - NODE_DEFINE_CONSTANT(target, CouldNotOpenHexFile); - - NODE_DEFINE_CONSTANT(target, RESET_NONE); - NODE_DEFINE_CONSTANT(target, RESET_SYSTEM); - NODE_DEFINE_CONSTANT(target, RESET_DEBUG); - NODE_DEFINE_CONSTANT(target, RESET_PIN); - - NODE_DEFINE_CONSTANT(target, ERASE_NONE); - NODE_DEFINE_CONSTANT(target, ERASE_ALL); - NODE_DEFINE_CONSTANT(target, ERASE_PAGES); - NODE_DEFINE_CONSTANT(target, ERASE_PAGES_INCLUDING_UICR); - - NODE_DEFINE_CONSTANT(target, VERIFY_NONE); - NODE_DEFINE_CONSTANT(target, VERIFY_READ); - - NODE_DEFINE_CONSTANT(target, INPUT_FORMAT_HEX_FILE); - NODE_DEFINE_CONSTANT(target, INPUT_FORMAT_HEX_STRING); - } - - NAN_MODULE_INIT(init) - { - initConsts(target); - HighLevel::Init(target); - RTT::Init(target); - } -} - -NODE_MODULE(pc_nrfjprog, init); diff --git a/src/highlevel.h b/src/highlevel.h index 45e7b33e..7d193bf2 100644 --- a/src/highlevel.h +++ b/src/highlevel.h @@ -56,6 +56,7 @@ class HighLevel : public Nan::ObjectWrap { public: static NAN_MODULE_INIT(Init); + static void initConsts(Nan::ADDON_REGISTER_FUNCTION_ARGS_TYPE tpl); private: explicit HighLevel(); diff --git a/src/nrfjprogwrapper.cpp b/src/nrfjprogwrapper.cpp index 0c727f6b..6b94a6c9 100644 --- a/src/nrfjprogwrapper.cpp +++ b/src/nrfjprogwrapper.cpp @@ -41,6 +41,12 @@ LibraryHandleType nrfJproglibraryHandle; std::string nrfjprogPath; +#define LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(target, name, handle) do { \ + if (!load_func_ptr((target), (name), (handle))) { \ + return errorcode_t::CouldNotLoadDLL; \ + } \ +} while (0); + errorcode_t loadnRFjprogFunctions(nRFjprogDllFunctionPointersType * dll_function) { if (nrfjprogPath.empty()) { @@ -54,265 +60,74 @@ errorcode_t loadnRFjprogFunctions(nRFjprogDllFunctionPointersType * dll_function nrfJproglibraryHandle = LibraryLoad(nrfjprogPath); - if (!nrfJproglibraryHandle){ - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->dll_version, "NRFJPROG_dll_version", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_dll_open, "NRFJPROG_is_dll_open", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->open_dll, "NRFJPROG_open_dll", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->close_dll, "NRFJPROG_close_dll", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->enum_emu_snr, "NRFJPROG_enum_emu_snr", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_connected_to_emu, "NRFJPROG_is_connected_to_emu", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->connect_to_emu_with_snr, "NRFJPROG_connect_to_emu_with_snr", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->connect_to_emu_without_snr, "NRFJPROG_connect_to_emu_without_snr", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_connected_emu_snr, "NRFJPROG_read_connected_emu_snr", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_connected_emu_fwstr, "NRFJPROG_read_connected_emu_fwstr", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->disconnect_from_emu, "NRFJPROG_disconnect_from_emu", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->recover, "NRFJPROG_recover", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_connected_to_device, "NRFJPROG_is_connected_to_device", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->connect_to_device, "NRFJPROG_connect_to_device", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->disconnect_from_device, "NRFJPROG_disconnect_from_device", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->readback_protect, "NRFJPROG_readback_protect", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->readback_status, "NRFJPROG_readback_status", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_region_0_size_and_source, "NRFJPROG_read_region_0_size_and_source", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->debug_reset, "NRFJPROG_debug_reset", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->sys_reset, "NRFJPROG_sys_reset", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->pin_reset, "NRFJPROG_pin_reset", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->disable_bprot, "NRFJPROG_disable_bprot", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->erase_all, "NRFJPROG_erase_all", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->erase_page, "NRFJPROG_erase_page", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->erase_uicr, "NRFJPROG_erase_uicr", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->write_u32, "NRFJPROG_write_u32", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_u32, "NRFJPROG_read_u32", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->write, "NRFJPROG_write", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read, "NRFJPROG_read", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_halted, "NRFJPROG_is_halted", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->halt, "NRFJPROG_halt", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->run, "NRFJPROG_run", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->go, "NRFJPROG_go", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->step, "NRFJPROG_step", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_ram_sections_count, "NRFJPROG_read_ram_sections_count", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_ram_sections_size, "NRFJPROG_read_ram_sections_size", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_ram_sections_power_status, "NRFJPROG_read_ram_sections_power_status", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_ram_powered, "NRFJPROG_is_ram_powered", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->power_ram_all, "NRFJPROG_power_ram_all", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->unpower_ram_section, "NRFJPROG_unpower_ram_section", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_cpu_register, "NRFJPROG_read_cpu_register", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->write_cpu_register, "NRFJPROG_write_cpu_register", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_device_version, "NRFJPROG_read_device_version", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_device_family, "NRFJPROG_read_device_family", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_debug_port_register, "NRFJPROG_read_debug_port_register", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->write_debug_port_register, "NRFJPROG_write_debug_port_register", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->read_access_port_register, "NRFJPROG_read_access_port_register", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->write_access_port_register, "NRFJPROG_write_access_port_register", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_rtt_started, "NRFJPROG_is_rtt_started", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_set_control_block_address, "NRFJPROG_rtt_set_control_block_address", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_start, "NRFJPROG_rtt_start", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_is_control_block_found, "NRFJPROG_rtt_is_control_block_found", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_stop, "NRFJPROG_rtt_stop", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_read, "NRFJPROG_rtt_read", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_write, "NRFJPROG_rtt_write", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_read_channel_count, "NRFJPROG_rtt_read_channel_count", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->rtt_read_channel_info, "NRFJPROG_rtt_read_channel_info", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->is_qspi_init, "NRFJPROG_is_qspi_init", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->qspi_init, "NRFJPROG_qspi_init", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->qspi_uninit, "NRFJPROG_qspi_uninit", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->qspi_read, "NRFJPROG_qspi_read", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->qspi_write, "NRFJPROG_qspi_write", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->qspi_erase, "NRFJPROG_qspi_erase", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } - - if (!load_func_ptr(&dll_function->qspi_custom, "NRFJPROG_qspi_custom", nrfJproglibraryHandle)) { - return errorcode_t::CouldNotLoadDLL; - } + if (!nrfJproglibraryHandle) { + return errorcode_t::CouldNotLoadDLL; + } + + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->dll_version, "NRFJPROG_dll_version", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_dll_open, "NRFJPROG_is_dll_open", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->open_dll, "NRFJPROG_open_dll", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->close_dll, "NRFJPROG_close_dll", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->enum_emu_snr, "NRFJPROG_enum_emu_snr", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_connected_to_emu, "NRFJPROG_is_connected_to_emu", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->connect_to_emu_with_snr, "NRFJPROG_connect_to_emu_with_snr", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->connect_to_emu_without_snr, "NRFJPROG_connect_to_emu_without_snr", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_connected_emu_snr, "NRFJPROG_read_connected_emu_snr", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_connected_emu_fwstr, "NRFJPROG_read_connected_emu_fwstr", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->disconnect_from_emu, "NRFJPROG_disconnect_from_emu", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->recover, "NRFJPROG_recover", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_connected_to_device, "NRFJPROG_is_connected_to_device", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->connect_to_device, "NRFJPROG_connect_to_device", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->disconnect_from_device, "NRFJPROG_disconnect_from_device", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->readback_protect, "NRFJPROG_readback_protect", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->readback_status, "NRFJPROG_readback_status", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_region_0_size_and_source, "NRFJPROG_read_region_0_size_and_source", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->debug_reset, "NRFJPROG_debug_reset", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->sys_reset, "NRFJPROG_sys_reset", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->pin_reset, "NRFJPROG_pin_reset", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->disable_bprot, "NRFJPROG_disable_bprot", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->erase_all, "NRFJPROG_erase_all", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->erase_page, "NRFJPROG_erase_page", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->erase_uicr, "NRFJPROG_erase_uicr", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->write_u32, "NRFJPROG_write_u32", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_u32, "NRFJPROG_read_u32", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->write, "NRFJPROG_write", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read, "NRFJPROG_read", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_halted, "NRFJPROG_is_halted", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->halt, "NRFJPROG_halt", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->run, "NRFJPROG_run", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->go, "NRFJPROG_go", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->step, "NRFJPROG_step", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_ram_sections_count, "NRFJPROG_read_ram_sections_count", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_ram_sections_size, "NRFJPROG_read_ram_sections_size", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_ram_sections_power_status, "NRFJPROG_read_ram_sections_power_status", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_ram_powered, "NRFJPROG_is_ram_powered", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->power_ram_all, "NRFJPROG_power_ram_all", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->unpower_ram_section, "NRFJPROG_unpower_ram_section", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_cpu_register, "NRFJPROG_read_cpu_register", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->write_cpu_register, "NRFJPROG_write_cpu_register", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_device_version, "NRFJPROG_read_device_version", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_device_family, "NRFJPROG_read_device_family", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_debug_port_register, "NRFJPROG_read_debug_port_register", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->write_debug_port_register, "NRFJPROG_write_debug_port_register", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->read_access_port_register, "NRFJPROG_read_access_port_register", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->write_access_port_register, "NRFJPROG_write_access_port_register", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_rtt_started, "NRFJPROG_is_rtt_started", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_set_control_block_address, "NRFJPROG_rtt_set_control_block_address", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_start, "NRFJPROG_rtt_start", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_is_control_block_found, "NRFJPROG_rtt_is_control_block_found", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_stop, "NRFJPROG_rtt_stop", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_read, "NRFJPROG_rtt_read", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_write, "NRFJPROG_rtt_write", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_read_channel_count, "NRFJPROG_rtt_read_channel_count", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->rtt_read_channel_info, "NRFJPROG_rtt_read_channel_info", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->is_qspi_init, "NRFJPROG_is_qspi_init", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->qspi_init, "NRFJPROG_qspi_init", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->qspi_uninit, "NRFJPROG_qspi_uninit", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->qspi_read, "NRFJPROG_qspi_read", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->qspi_write, "NRFJPROG_qspi_write", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->qspi_erase, "NRFJPROG_qspi_erase", nrfJproglibraryHandle); + LOAD_FUNCTION_POINTER_RETURN_ON_ERROR(&dll_function->qspi_custom, "NRFJPROG_qspi_custom", nrfJproglibraryHandle); return errorcode_t::JsSuccess; } diff --git a/src/rtt.cpp b/src/rtt.cpp index c4052012..56b18a6b 100644 --- a/src/rtt.cpp +++ b/src/rtt.cpp @@ -37,6 +37,9 @@ #include "rtt.h" #include +#include +#include +#include #include "highlevel_common.h" #include "rtt_batons.h" @@ -47,8 +50,6 @@ #include "utility/errormessage.h" #include "utility/utility.h" -#include -#include Nan::Persistent RTT::constructor; std::string RTT::logMessage; @@ -137,7 +138,7 @@ void RTT::CallFunction(Nan::NAN_METHOD_ARGS_TYPE info, rtt_parse_parameters_func baton = parse(info, argumentCount); v8::Local callback = Convert::getCallbackFunction(info[argumentCount]); - baton->callback = new Nan::Callback(callback); + baton->callback = std::make_unique(callback); argumentCount++; if (info.Length() > argumentCount) @@ -181,7 +182,7 @@ void RTT::CallFunction(Nan::NAN_METHOD_ARGS_TYPE info, rtt_parse_parameters_func baton->executeFunction = execute; baton->returnFunction = ret; - uv_queue_work(uv_default_loop(), baton->req, ExecuteFunction, reinterpret_cast(ReturnFunction)); + uv_queue_work(uv_default_loop(), baton->req.get(), ExecuteFunction, reinterpret_cast(ReturnFunction)); } void RTT::ExecuteFunction(uv_work_t *req) @@ -251,9 +252,9 @@ void RTT::log(std::string msg) logItemCount++; } -void RTT::logCallback(const char *msg) +void RTT::log(const char *msg) { - log(msg); + log(std::string(msg)); } bool RTT::isStarted() @@ -268,6 +269,112 @@ bool RTT::isStarted() return started; } +RTTErrorcodes_t RTT::getDeviceInformation(RTTStartBaton *baton) +{ + DllFunctionPointersType highLevelFunctions; + + const nrfjprogdll_err_t loadHighlevelStatus = (nrfjprogdll_err_t)loadHighLevelFunctions(&highLevelFunctions); + + if (loadHighlevelStatus != SUCCESS) + { + baton->lowlevelError = loadHighlevelStatus; + return RTTCouldNotOpenHighlevelLibrary; + } + + const nrfjprogdll_err_t openHighlevelStatus = highLevelFunctions.dll_open(nullptr, &RTT::log, nullptr); + + if (openHighlevelStatus != SUCCESS) + { + releaseHighLevel(); + baton->lowlevelError = openHighlevelStatus; + return RTTCouldNotOpenHighlevelLibrary; + } + + Probe_handle_t probe; + const nrfjprogdll_err_t initProbeStatus = highLevelFunctions.probe_init(&probe, baton->serialNumber, nullptr); + + if (initProbeStatus != SUCCESS) + { + highLevelFunctions.dll_close(); + releaseHighLevel(); + baton->lowlevelError = initProbeStatus; + return RTTCouldNotGetDeviceInformation; + } + + probe_info_t probeInfo; + device_info_t deviceInfo; + library_info_t libraryInfo; + + RETURN_ERROR_ON_FAIL(highLevelFunctions.get_probe_info(probe, &probeInfo), RTTCouldNotGetDeviceInformation); + RETURN_ERROR_ON_FAIL(highLevelFunctions.get_device_info(probe, &deviceInfo), RTTCouldNotGetDeviceInformation); + RETURN_ERROR_ON_FAIL(highLevelFunctions.get_library_info(probe, &libraryInfo), RTTCouldNotGetDeviceInformation); + + RETURN_ERROR_ON_FAIL(highLevelFunctions.reset(probe, RESET_SYSTEM), RTTCouldNotGetDeviceInformation); + RETURN_ERROR_ON_FAIL(highLevelFunctions.probe_uninit(&probe), RTTCouldNotGetDeviceInformation); + highLevelFunctions.dll_close(); + + releaseHighLevel(); + + baton->clockSpeed = probeInfo.clockspeed_khz; + baton->family = deviceInfo.device_family; + baton->jlinkarmlocation = libraryInfo.file_path; + + return RTTSuccess; +} + +RTTErrorcodes_t RTT::waitForControlBlock(RTTStartBaton *baton) +{ + while (true) { + bool controlBlockFound = false; + RETURN_ERROR_ON_FAIL(dll_function.rtt_is_control_block_found(&controlBlockFound), RTTCouldNotCallFunction); + + if (controlBlockFound) { + return RTTSuccess; + } + + auto attemptedStartupTime = std::chrono::high_resolution_clock::now(); + + if (std::chrono::duration_cast(attemptedStartupTime - rttStartTime).count() > 10) { + cleanup(); + return RTTCouldNotFindControlBlock; + } + + std::this_thread::sleep_for(std::chrono::milliseconds(10)); + } + + return RTTSuccess; +} + +RTTErrorcodes_t RTT::getChannelInformation(RTTStartBaton *baton) +{ + uint32_t downChannelNumber; + uint32_t upChannelNumber; + + RETURN_ERROR_ON_FAIL(dll_function.rtt_read_channel_count(&downChannelNumber, &upChannelNumber), RTTCouldNotGetChannelInformation); + + for(uint32_t i = 0; i < downChannelNumber; ++i) + { + char channelName[32]; + uint32_t channelSize; + RETURN_ERROR_ON_FAIL(dll_function.rtt_read_channel_info(i, DOWN_DIRECTION, channelName, 32, &channelSize), RTTCouldNotGetChannelInformation); + + std::string name(channelName); + baton->downChannelInfo.push_back(std::make_unique(i, name, channelSize)); + } + + for(uint32_t i = 0; i < upChannelNumber; ++i) + { + char channelName[32]; + uint32_t channelSize; + RETURN_ERROR_ON_FAIL(dll_function.rtt_read_channel_info(i, UP_DIRECTION, channelName, 32, &channelSize), RTTCouldNotGetChannelInformation); + + std::string name(channelName); + baton->upChannelInfo.push_back(std::make_unique(i, name, channelSize)); + } + + return RTTSuccess; +} + NAN_METHOD(RTT::Start) { rtt_parse_parameters_function_t p = [&] (Nan::NAN_METHOD_ARGS_TYPE parameters, int &argumentCount) -> RTTBaton* { @@ -288,61 +395,19 @@ NAN_METHOD(RTT::Start) rtt_execute_function_t e = [&] (RTTBaton *b) -> RTTErrorcodes_t { auto baton = static_cast(b); - DllFunctionPointersType highLevelFunctions; + const RTTErrorcodes_t deviceInformationStatus = getDeviceInformation(baton); - const nrfjprogdll_err_t loadHighlevelStatus = (nrfjprogdll_err_t)loadHighLevelFunctions(&highLevelFunctions); - - if (loadHighlevelStatus != SUCCESS) - { - baton->lowlevelError = loadHighlevelStatus; - return RTTCouldNotOpenHighlevelLibrary; - } - - const nrfjprogdll_err_t openHighlevelStatus = highLevelFunctions.dll_open(nullptr, nullptr, nullptr); - - if (openHighlevelStatus != SUCCESS) - { - releaseHighLevel(); - baton->lowlevelError = openHighlevelStatus; - return RTTCouldNotOpenHighlevelLibrary; - } - - Probe_handle_t probe; - const nrfjprogdll_err_t initProbeStatus = highLevelFunctions.probe_init(&probe, baton->serialNumber, nullptr); - - if (initProbeStatus != SUCCESS) - { - highLevelFunctions.dll_close(); - releaseHighLevel(); - baton->lowlevelError = initProbeStatus; - return RTTCouldNotGetDeviceInformation; + if (deviceInformationStatus != RTTSuccess) { + return deviceInformationStatus; } - probe_info_t probeInfo; - device_info_t deviceInfo; - library_info_t libraryInfo; - - RETURN_ERROR_ON_FAIL(highLevelFunctions.get_probe_info(probe, &probeInfo), RTTCouldNotGetDeviceInformation); - RETURN_ERROR_ON_FAIL(highLevelFunctions.get_device_info(probe, &deviceInfo), RTTCouldNotGetDeviceInformation); - RETURN_ERROR_ON_FAIL(highLevelFunctions.get_library_info(probe, &libraryInfo), RTTCouldNotGetDeviceInformation); - - RETURN_ERROR_ON_FAIL(highLevelFunctions.reset(probe, RESET_SYSTEM), RTTCouldNotGetDeviceInformation); - RETURN_ERROR_ON_FAIL(highLevelFunctions.probe_uninit(&probe), RTTCouldNotGetDeviceInformation); - highLevelFunctions.dll_close(); - - releaseHighLevel(); - - uint32_t clockSpeed = probeInfo.clockspeed_khz; - device_family_t family = deviceInfo.device_family; - std::string jlinkarmlocation = libraryInfo.file_path; - RETURN_ERROR_ON_FAIL((nrfjprogdll_err_t)loadnRFjprogFunctions(&dll_function), RTTCouldNotLoadnRFjprogLibrary); libraryLoaded = true; - RETURN_ERROR_ON_FAIL(dll_function.open_dll(jlinkarmlocation.c_str(), &RTT::logCallback, family), RTTCouldNotOpennRFjprogLibrary); + RETURN_ERROR_ON_FAIL(dll_function.open_dll(baton->jlinkarmlocation.c_str(), &RTT::log, baton->family), RTTCouldNotOpennRFjprogLibrary); - RETURN_ERROR_ON_FAIL(dll_function.connect_to_emu_with_snr(baton->serialNumber, clockSpeed), RTTCouldNotConnectToDevice); + RETURN_ERROR_ON_FAIL(dll_function.connect_to_emu_with_snr(baton->serialNumber, baton->clockSpeed), RTTCouldNotConnectToDevice); RETURN_ERROR_ON_FAIL(dll_function.connect_to_device(), RTTCouldNotConnectToDevice); if (baton->hasControlBlockLocation) { @@ -352,76 +417,43 @@ NAN_METHOD(RTT::Start) rttStartTime = std::chrono::high_resolution_clock::now(); RETURN_ERROR_ON_FAIL(dll_function.rtt_start(), RTTCouldNotStartRTT); + const RTTErrorcodes_t waitStatus = waitForControlBlock(baton); - while (true) { - bool controlBlockFound = false; - RETURN_ERROR_ON_FAIL(dll_function.rtt_is_control_block_found(&controlBlockFound), RTTCouldNotCallFunction); - std::chrono::high_resolution_clock::time_point attemptedStartupTime = std::chrono::high_resolution_clock::now(); - - if (controlBlockFound) { - break; - } - - if (std::chrono::duration_cast(attemptedStartupTime - rttStartTime).count() > 10) { - cleanup(); - return RTTCouldNotFindControlBlock; - } - } - - uint32_t downChannelNumber; - uint32_t upChannelNumber; - - RETURN_ERROR_ON_FAIL(dll_function.rtt_read_channel_count(&downChannelNumber, &upChannelNumber), RTTCouldNotGetChannelInformation); - - for(uint32_t i = 0; i < downChannelNumber; ++i) - { - char channelName[32]; - uint32_t channelSize; - RETURN_ERROR_ON_FAIL(dll_function.rtt_read_channel_info(i, DOWN_DIRECTION, channelName, 32, &channelSize), RTTCouldNotGetChannelInformation); - - std::string name(channelName); - baton->downChannelInfo.push_back(new ChannelInfo(i, name, channelSize)); + if (waitStatus != RTTSuccess) { + return waitStatus; } - for(uint32_t i = 0; i < upChannelNumber; ++i) - { - char channelName[32]; - uint32_t channelSize; - RETURN_ERROR_ON_FAIL(dll_function.rtt_read_channel_info(i, UP_DIRECTION, channelName, 32, &channelSize), RTTCouldNotGetChannelInformation); - - std::string name(channelName); - baton->upChannelInfo.push_back(new ChannelInfo(i, name, channelSize)); - } + const RTTErrorcodes_t channelInformationStatus = getChannelInformation(baton); - return RTTSuccess; + return channelInformationStatus; }; - rtt_return_function_t r = [&] (RTTBaton *b) -> returnType { + rtt_return_function_t r = [&] (RTTBaton *b) -> std::vector> { auto baton = static_cast(b); - returnType vector; + std::vector> returnData; v8::Local downChannelInfo = Nan::New(); int i = 0; - for (auto element : baton->downChannelInfo) + for (auto& element : baton->downChannelInfo) { Nan::Set(downChannelInfo, Convert::toJsNumber(i), element->ToJs()); i++; } - vector.push_back(downChannelInfo); + returnData.push_back(downChannelInfo); v8::Local upChannelInfo = Nan::New(); i = 0; - for (auto element : baton->upChannelInfo) + for (auto& element : baton->upChannelInfo) { Nan::Set(upChannelInfo, Convert::toJsNumber(i), element->ToJs()); i++; } - vector.push_back(upChannelInfo); + returnData.push_back(upChannelInfo); - return vector; + return returnData; }; CallFunction(info, p, e, r); @@ -519,16 +551,16 @@ NAN_METHOD(RTT::Read) return RTTSuccess; }; - rtt_return_function_t r = [&] (RTTBaton *b) -> returnType { + rtt_return_function_t r = [&] (RTTBaton *b) -> std::vector> { auto baton = static_cast(b); - returnType vector; + std::vector> returnData; - vector.push_back(Convert::toJsString(baton->data.data(), baton->length)); - vector.push_back(Convert::toJsValueArray((uint8_t *)baton->data.data(), baton->length)); - vector.push_back(Convert::toTimeDifferenceUS(rttStartTime, baton->functionStart)); + returnData.push_back(Convert::toJsString(baton->data.data(), baton->length)); + returnData.push_back(Convert::toJsValueArray((uint8_t *)baton->data.data(), baton->length)); + returnData.push_back(Convert::toTimeDifferenceUS(rttStartTime, baton->functionStart)); - return vector; + return returnData; }; CallFunction(info, p, e, r); @@ -566,7 +598,7 @@ NAN_METHOD(RTT::Write) uint32_t writeLength = 0; - baton->functionStart = std::chrono::high_resolution_clock::now(); \ + baton->functionStart = std::chrono::high_resolution_clock::now(); RETURN_ERROR_ON_FAIL(dll_function.rtt_write(baton->channelIndex, baton->data, baton->length, &writeLength), RTTCouldNotCallFunction); baton->length = writeLength; @@ -574,15 +606,15 @@ NAN_METHOD(RTT::Write) return RTTSuccess; }; - rtt_return_function_t r = [&] (RTTBaton *b) -> returnType { + rtt_return_function_t r = [&] (RTTBaton *b) -> std::vector> { auto baton = static_cast(b); - returnType vector; + std::vector> returnData; - vector.push_back(Convert::toJsNumber(baton->length)); - vector.push_back(Convert::toTimeDifferenceUS(rttStartTime, baton->functionStart)); + returnData.push_back(Convert::toJsNumber(baton->length)); + returnData.push_back(Convert::toTimeDifferenceUS(rttStartTime, baton->functionStart)); - return vector; + return returnData; }; diff --git a/src/rtt.h b/src/rtt.h index 2a3e327b..4ce64e00 100644 --- a/src/rtt.h +++ b/src/rtt.h @@ -47,11 +47,11 @@ #include class RTTBaton; +class RTTStartBaton; -typedef std::vector > returnType; typedef std::function rtt_parse_parameters_function_t; typedef std::function rtt_execute_function_t; -typedef std::function rtt_return_function_t; +typedef std::function>(RTTBaton*)> rtt_return_function_t; class RTT : public Nan::ObjectWrap { @@ -81,13 +81,18 @@ class RTT : public Nan::ObjectWrap static void init(v8::Local tpl); + static RTTErrorcodes_t getDeviceInformation(RTTStartBaton *baton); + static RTTErrorcodes_t waitForControlBlock(RTTStartBaton *baton); + static RTTErrorcodes_t getChannelInformation(RTTStartBaton *baton); + static bool isStarted(); static void cleanup(); - static void logCallback(const char * msg); + static void log(const char * msg); static void log(std::string msg); static void resetLog(); + static std::string logMessage; static bool appendToLog; static int logItemCount; diff --git a/src/rtt_batons.h b/src/rtt_batons.h index e247486b..9c24fd25 100644 --- a/src/rtt_batons.h +++ b/src/rtt_batons.h @@ -41,31 +41,23 @@ #include "rtt.h" #include "rtt_helpers.h" -#define RTTBATON_CONSTRUCTOR(BatonType, name, returnParameterCount) BatonType() : RTTBaton(returnParameterCount, name) {} -#define RTTBATON_DESTRUCTOR(BatonType) ~BatonType() - class RTTBaton { public: - explicit RTTBaton(const uint32_t _returnParameterCount, const std::string _name) : + explicit RTTBaton(const std::string _name, const uint32_t _returnParameterCount) : returnParameterCount(_returnParameterCount), name(_name), result(JsSuccess), lowlevelError(SUCCESS) { - req = new uv_work_t(); + req = std::make_unique(); req->data = static_cast(this); callback = nullptr; } virtual ~RTTBaton() { - delete req; - - if (callback != nullptr) - { - delete callback; - callback = nullptr; - } + req.reset(); + callback.reset(); } virtual uint32_t returnParamterCount() @@ -79,8 +71,8 @@ class RTTBaton { uint32_t result; nrfjprogdll_err_t lowlevelError; - uv_work_t *req; - Nan::Callback *callback; + std::unique_ptr req; + std::unique_ptr callback; std::chrono::high_resolution_clock::time_point functionStart; @@ -91,25 +83,29 @@ class RTTBaton { class RTTStartBaton : public RTTBaton { public: - RTTBATON_CONSTRUCTOR(RTTStartBaton, "start rtt", 2); + RTTStartBaton() : RTTBaton("start rtt", 2) {} uint32_t serialNumber; bool hasControlBlockLocation; uint32_t controlBlockLocation; - std::vector upChannelInfo; - std::vector downChannelInfo; + uint32_t clockSpeed; + device_family_t family; + std::string jlinkarmlocation; + + std::vector> upChannelInfo; + std::vector> downChannelInfo; }; class RTTStopBaton : public RTTBaton { public: - RTTBATON_CONSTRUCTOR(RTTStopBaton, "stop rtt", 0); + RTTStopBaton() : RTTBaton("stop rtt", 0) {} }; class RTTReadBaton : public RTTBaton { public: - RTTBATON_CONSTRUCTOR(RTTReadBaton, "rtt read", 3); + RTTReadBaton() : RTTBaton("rtt read", 3) {} uint32_t channelIndex; uint32_t length; @@ -119,7 +115,7 @@ class RTTReadBaton : public RTTBaton class RTTWriteBaton : public RTTBaton { public: - RTTBATON_CONSTRUCTOR(RTTWriteBaton, "rtt write", 2); + RTTWriteBaton() : RTTBaton("rtt write", 2) {} ~RTTWriteBaton() { delete[] data; } diff --git a/src/utility/conversion.cpp b/src/utility/conversion.cpp index 2d93ae55..5a374899 100644 --- a/src/utility/conversion.cpp +++ b/src/utility/conversion.cpp @@ -492,64 +492,9 @@ v8::Handle Convert::valueToJsString(uint16_t value, name_map_t name_m return scope.Escape(Nan::New(it->second).ToLocalChecked()); } -v8::Handle Convert::toTimeDifference(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime) -{ - Nan::EscapableHandleScope scope; - - v8::Local timeObj = Nan::New(); - Utility::Set(timeObj, "min", Convert::toTimeDifferenceM(startTime, endTime)); - Utility::Set(timeObj, "s", Convert::toTimeDifferenceS(startTime, endTime, true)); - Utility::Set(timeObj, "ms", Convert::toTimeDifferenceMS(startTime, endTime, true)); - Utility::Set(timeObj, "us", Convert::toTimeDifferenceUS(startTime, endTime, true)); - - return scope.Escape(timeObj); -} - -v8::Handle Convert::toTimeDifferenceM(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justMinutePart) -{ - uint32_t duration = (uint32_t)std::chrono::duration_cast(endTime - startTime).count(); - - if (justMinutePart) - { - duration = duration % 60; - } - - return Convert::toJsNumber(duration); -} - -v8::Handle Convert::toTimeDifferenceS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justSecondPart) -{ - uint32_t duration = (uint32_t)std::chrono::duration_cast(endTime - startTime).count(); - - if (justSecondPart) - { - duration = duration % 60; - } - - return Convert::toJsNumber(duration); -} - -v8::Handle Convert::toTimeDifferenceMS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justMillisecondPart) -{ - uint32_t duration = (uint32_t)std::chrono::duration_cast(endTime - startTime).count(); - - if (justMillisecondPart) - { - duration = duration % 1000; - } - - return Convert::toJsNumber(duration); -} - -v8::Handle Convert::toTimeDifferenceUS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justMicrosecondPart) +v8::Handle Convert::toTimeDifferenceUS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime) { uint32_t duration = (uint32_t)std::chrono::duration_cast(endTime - startTime).count(); - - if (justMicrosecondPart) - { - duration = duration % 1000; - } - return Convert::toJsNumber(duration); } diff --git a/src/utility/conversion.h b/src/utility/conversion.h index a0f5df0d..e9d54788 100644 --- a/src/utility/conversion.h +++ b/src/utility/conversion.h @@ -94,11 +94,7 @@ class Convert static const char * valueToString(uint16_t value, name_map_t name_map, const char *defaultValue = "Unknown value"); static v8::Handle valueToJsString(uint16_t, name_map_t name_map, v8::Handle defaultValue = Nan::New("Unknown value").ToLocalChecked()); - static v8::Handle toTimeDifference(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime); - static v8::Handle toTimeDifferenceM(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justMinutePart = false); - static v8::Handle toTimeDifferenceS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justSecondPart = false); - static v8::Handle toTimeDifferenceMS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justMillisecondPart = false); - static v8::Handle toTimeDifferenceUS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime, bool justMicrosecondPart = false); + static v8::Handle toTimeDifferenceUS(std::chrono::high_resolution_clock::time_point startTime, std::chrono::high_resolution_clock::time_point endTime); static v8::Local getCallbackFunction(v8::Local js, const char *name); static v8::Local getCallbackFunction(v8::Local js);