--[[
  Copyright (c) 2025 by Plexim GmbH
  All rights reserved.

  A free license is granted to anyone to use this software for any legal
  non safety-critical purpose, including commercial applications, provided
  that:
  1) IT IS NOT USED TO DIRECTLY OR INDIRECTLY COMPETE WITH PLEXIM, and
  2) THIS COPYRIGHT NOTICE IS PRESERVED in its entirety.

  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
  OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  SOFTWARE.
--]]

local U = require('common.utils')
local debug = require('debug')

local errorMap = {}
-- Not enough RAM
errorMap['program will not fit into available memory'] =
'Program is too large for the selected memory. If program is being built for RAM, try moving it to Flash memory instead. Check your build configuration settings in the Coder Options menu, under the tabs "Target/General."'


local couldNotConnectMsg = 'Could not connect to the target device for programming. The device may be disconnected, not powered, or another debugger may be running.'

errorMap['Error initializing emulator:'] = couldNotConnectMsg -- Disconnected 28P55 generates this error
errorMap['Error connecting to the target:'] = couldNotConnectMsg -- Disconnected 2737x generates this error

errorMap['Cannot read System Setup data from XML file'] = 'Uniflash target configuration (ccxml) file provided could not be parsed.' -- Invalid XML in ccxml file generates this error

errorMap['/OneDrive/'] = 'It is recommended to avoid installing any of the TSP toolchain on a network drive such as OneDrive.'

errorMap['PLECSCockpit/plx-binutil: No such file or directory'] = 'Check that you have the correct version of PLECSCockpit installed, the files were not found.'

-- Eror detection for BANKMGMT Bank Mode not set appropriately for dual core.
-- See #1726 for full error messages
errorMap['error: C29xx_CPU1: Error during Flash Programming. Program command was not issued since address provided for Flash program operation is invalid. Address provided is 0xFFFFFFFF'] =
'This device supports multiple Flash bank modes to determine CPU access to Flash memory. It looks like your device is not configured for dual core operation. Please see the TSP user manual Quick Start -> Tips for Programming section for this device for instructions on how to set the bank mode appropriately.'
errorMap['error: C29xx_CPU1: Error occurred during flash operation: Timed out waiting for target to halt while executing'] =
'It looks like the connected device needs to be power cycled. Power cycle is required following bank mode updates.'


local function p_OnErrorFunction(fullTrace)
  local errorMsg = ''
  for errorKey, errorSummary in pairs(errorMap) do
    if string.find(fullTrace, errorKey, 1, true) then -- use plain flag to treat search strings as plain text.
      errorMsg = errorMsg..errorSummary..'\n' -- Concatenate summary messages if more than one triggered.
    end
  end
  if errorMsg ~= '' then
    U.error(errorMsg)
  end
end


local params = {...}
local fullTrace = params[1]

local ok, res = xpcall(p_OnErrorFunction, debug.traceback, fullTrace)

if ok then
  -- We did not detect a more detailed message to report.
  U.dumpLog()
  return res
else  
  --[[
      There was an error detected. OnErrorFunction has a unique implementation
      for reporting errors. 
      
      1) If thrown from code here via error(), it will show up as a warning 
      incident prior to the original error incident, which is reported as it 
      would be without this code running. 
      
      2) If the error message triggered a custom message above. We will return 
      the custom message with the original trace appended below, this will be 
      logged as an error incident in place of the original error.
   --]]
  return '\n'..U.stripTraceOrRethrowError(res)..[[

  
  ================ Full Trace ============
  
  ]]..fullTrace
end
