-- Copyright (c) 2024 Huawei Technologies Co., Ltd.
-- openUBMC is licensed under Mulan PSL v2.
-- You can use this software according to the terms and conditions of the Mulan PSL v2.
-- You may obtain a copy of Mulan PSL v2 at: http://license.coscl.org.cn/MulanPSL2
-- THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
-- EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
-- MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
-- See the Mulan PSL v2 for more details.

local bs = require 'mc.bitstring'
local log = require 'mc.logging'
local core = require 'network.core'
local ncsi_utils = require 'ncsi.ncsi_protocol.ncsi_utils'
local ncsi_def = require 'ncsi.ncsi_protocol.ncsi_def'

local ncsi_packet = {}

local COMMON_RSP_LEN = 4

local commom_rsp_bs = bs.new([[<<
    rsp_code:16,
    reason_code:16,
    check_sum:32,
    data:22/string,
    fcs:32
>>]])

function ncsi_packet.read_common_rsp(rsp, cmd_name)
    if (rsp.packet_head.payload_len_lo | (rsp.packet_head.payload_len_hi << 8)) ~= COMMON_RSP_LEN then
        log:error('Invalid %s response length', cmd_name)
        return ncsi_def.NCSI_FAIL
    end
    local data = commom_rsp_bs:unpack(rsp.payload, true)
    if not data then
        log:error('Failed to unpack %s response payload', cmd_name)
        return ncsi_def.NCSI_FAIL
    end
    local check_sum = data.check_sum
    -- check_sum为0时不校验
    if check_sum ~= 0 then
        local tmp_check_sum = ncsi_utils.get_checksum(rsp, ncsi_def.PACKET_HEAD_LEN + COMMON_RSP_LEN)
        if check_sum ~= core.htonl(tmp_check_sum) then
            log:error('%s response checksum validation failed', cmd_name)
            return ncsi_def.NCSI_FAIL
        end
    end
    local rsp_code = data.rsp_code
    if rsp_code == ncsi_def.CMD_COMPLETED then
        return ncsi_def.NCSI_SUCCESS
    end

    ncsi_utils.common_respcode_parse(rsp_code)
    ncsi_utils.common_reasoncode_parse(data.reason_code)
    return ncsi_def.NCSI_FAIL
end

function ncsi_packet.create_request_packet(package_id, channel_id, packet_type)
    local req_packet = {frame_head = {}, packet_head = {}, payload = ''}
    req_packet.packet_head.package_id = package_id
    req_packet.packet_head.channel_id = channel_id
    req_packet.packet_head.packet_type = packet_type
    return req_packet
end

return ncsi_packet