#!/usr/bin/env python3
#
# Copyright (c) 2020 Nuvoton Technology Corporation
#
# SPDX-License-Identifier: Apache-2.0

# This script will append/paste specific header to tell ROM code (Booter) of
# NPCX EC series how to load the firmware from flash to code ram
# Usage python3 ${ZEPHYR_BASE}/scripts/ecst.py
#                    -i in_file.bin -o out_file.bin
#                    [-chip <name>] [-v|-vv]
#                    [-nohcrc] [-nofcrc] [-ph <offset>]
#                    [-flashsize <1|2|4|8|16>]
#                    [-spimaxclk <20|25|33|40|50>]
#                    [-spireadmode <normal|fast|dual|quad>]

import sys
from colorama import init, Fore
from ecst_args import EcstArgs, exit_with_failure
from pathlib import Path

# ECST Version
ECST_VER = "2.0.1"

# Offsets inside the header
HDR_ANCHOR_OFFSET = 0
HDR_EXTENDED_ANCHOR_OFFSET = 4
HDR_SPI_MAX_CLK_OFFSET = 6
HDR_SPI_READ_MODE_OFFSET = 7
HDR_ERR_DETECTION_CONF_OFFSET = 8
HDR_FW_LOAD_START_ADDR_OFFSET = 9
HDR_FW_ENTRY_POINT_OFFSET = 13
HDR_FW_ERR_DETECT_START_ADDR_OFFSET = 17
HDR_FW_ERR_DETECT_END_ADDR_OFFSET = 21
HDR_FW_LENGTH_OFFSET = 25
HDR_FLASH_SIZE_OFFSET = 29
OTP_WRITE_PROTECT_OFFSET = 30
KEY_VALID_OFFSET = 31
FIRMWARE_VALID_OFFSET = 32
RESERVED_BYTES_OFFSET = 33
HDR_FW_HEADER_SIG_OFFSET = 56
HDR_FW_IMAGE_SIG_OFFSET = 60
FW_IMAGE_OFFSET = 64

SIGNATURE_OFFSET = 0
POINTER_OFFSET = 4
ARM_FW_ENTRY_POINT_OFFSET = 4

# Header field known values
FW_HDR_ANCHOR = 0x2A3B4D5E
FW_HDR_EXT_ANCHOR_ENABLE = 0xAB1E
FW_HDR_EXT_ANCHOR_DISABLE = 0x54E1
FW_HDR_CRC_DISABLE = 0x00
FW_HDR_CRC_ENABLE = 0x02
FW_CRC_DISABLE = 0x00
FW_CRC_ENABLE = 0x02
HDR_PTR_SIGNATURE = 0x55AA650E

BOOTLOADER_TABLE_MODE = "bt"

# SPI related values
SPI_MAX_CLOCK_20_MHZ_VAL = "20"
SPI_MAX_CLOCK_25_MHZ_VAL = "25"
SPI_MAX_CLOCK_33_MHZ_VAL = "33"
SPI_MAX_CLOCK_40_MHZ_VAL = "40"
SPI_MAX_CLOCK_50_MHZ_VAL = "50"

SPI_MAX_CLOCK_20_MHZ = 0x00
SPI_MAX_CLOCK_25_MHZ = 0x01
SPI_MAX_CLOCK_33_MHZ = 0x02
SPI_MAX_CLOCK_40_MHZ = 0x03
SPI_MAX_CLOCK_50_MHZ = 0x04

SPI_CLOCK_RATIO_1_VAL = 1
SPI_CLOCK_RATIO_2_VAL = 2

SPI_CLOCK_RATIO_1 = 0x00
SPI_CLOCK_RATIO_2 = 0x08

SPI_NORMAL_MODE_VAL = 'normal'
SPI_SINGLE_MODE_VAL = 'fast'
SPI_DUAL_MODE_VAL = 'dual'
SPI_QUAD_MODE_VAL = 'quad'

SPI_NORMAL_MODE = 0x00
SPI_SINGLE_MODE = 0x01
SPI_DUAL_MODE = 0x03
SPI_QUAD_MODE = 0x04

# Flash related values
FLASH_SIZE_1_MBYTES_VAL = "1"
FLASH_SIZE_2_MBYTES_VAL = "2"
FLASH_SIZE_4_MBYTES_VAL = "4"
FLASH_SIZE_8_MBYTES_VAL = "8"
FLASH_SIZE_16_MBYTES_VAL = "16"

FLASH_SIZE_1_MBYTES = 0x01
FLASH_SIZE_2_MBYTES = 0x03
FLASH_SIZE_4_MBYTES = 0x07
FLASH_SIZE_8_MBYTES = 0x0f
FLASH_SIZE_8_MBYTES = 0x0f
FLASH_SIZE_16_MBYTES = 0x1f

MAX_FLASH_SIZE = 0x03ffffff

# Header fields default values.
ADDR_16_BYTES_ALIGNED_MASK = 0x0000000f
ADDR_4_BYTES_ALIGNED_MASK = 0x00000003
ADDR_4K_BYTES_ALIGNED_MASK = 0x00000fff

NUM_OF_BYTES = 32
INVALID_INPUT = -1
HEADER_SIZE = 64
PAD_BYTE = b'\x00'
BYTES_TO_PAD = HDR_FW_HEADER_SIG_OFFSET - RESERVED_BYTES_OFFSET

# Verbose related values
NO_VERBOSE = 0
REG_VERBOSE = 1
SUPER_VERBOSE = 1

# Success/failure codes
EXIT_SUCCESS_STATUS = 0
EXIT_FAILURE_STATUS = 1

def _bt_mode_handler(ecst_args):
    """creates the bootloader table using the provided arguments.

    :param ecst_args: the object representing the command line arguments.
    """

    output_file = _set_input_and_output(ecst_args)
    _check_chip(output_file, ecst_args)

    if ecst_args.paste_firmware_header != 0:
        _check_firmware_header_offset(output_file, ecst_args)

    _copy_image(output_file, ecst_args)
    _set_anchor(output_file, ecst_args)
    _set_extended_anchor(output_file, ecst_args)
    _set_spi_flash_maximum_clock(output_file, ecst_args)
    _set_spi_flash_mode(output_file, ecst_args)
    _set_error_detection_configuration(output_file, ecst_args)
    _set_firmware_load_start_address(output_file, ecst_args)
    _set_firmware_entry_point(output_file, ecst_args)
    _set_firmware_crc_start_and_size(output_file, ecst_args)
    _set_firmware_length(output_file, ecst_args)
    _set_flash_size(output_file, ecst_args)
    _set_reserved_bytes(output_file, ecst_args)
    _set_firmware_header_crc_signature(output_file, ecst_args)
    _set_firmware_image_crc_signature(output_file, ecst_args)

    _exit_with_success()

def _set_input_and_output(ecst_args):
    """checks the input file and output and sets the output file.

    checks input file existence, creates an output file according
    to the 'output' argument.

    Note: input file size has to be greater than 0, and named differently
    from output file

    :param ecst_args: the object representing the command line arguments.

    :returns: output file path object, or -1 if fails
    """
    input_file = ecst_args.input
    output = ecst_args.output
    input_file_size = 0

    if not input_file:
        exit_with_failure("Define input file, using -i flag")

    input_file_path = Path(input_file)

    if not input_file_path.exists():
        exit_with_failure(f'Cannot open {input_file}')
    elif input_file_path.stat().st_size == 0:
        exit_with_failure(f'BIN Input file ({input_file}) is empty')
    else:
        input_file_size = input_file_path.stat().st_size

    if not output:
        output_file = Path("out_" + input_file_path.name)
    else:
        output_file = Path(output)

    if output_file.exists():
        if output_file.samefile(input_file_path):
            exit_with_failure(f'Input file name {input_file} '
                              f'should be differed from'
                              f' Output file name {output}')
        output_file.unlink()

    output_file.touch()

    if ecst_args.verbose == REG_VERBOSE:
        print(Fore.LIGHTCYAN_EX + f'\nBIN file: {input_file}, size:'
              f' {input_file_size} bytes')
        print(f'Output file name: {output_file.name} \n')

    return output_file

def _check_chip(output, ecst_args):
    """checks if the chip entered is a legal chip, generates an error
    and closes the application, deletes the output file if the chip name
    is illegal.

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """

    if ecst_args.chip_name == INVALID_INPUT:
        message = f'Invalid chip name, '
        message += "should be npcx9m8, npcx9m7, npcx9m6, npcx7m7," \
                   " npcx7m6, npcx7m5, npcx5m5 or npcx5m6."
        _exit_with_failure_delete_file(output, message)

def _set_anchor(output, ecst_args):
    """writes the anchor value to the output file

    :param output: the output file object.
    :param ecst_args: the object representing the command line arguments.
    """

    with output.open("r+b") as output_file:
        output_file.seek(HDR_ANCHOR_OFFSET + ecst_args.paste_firmware_header)
        output_file.write(FW_HDR_ANCHOR.to_bytes(4, "little"))
        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - FW Header ANCHOR                 - Offset '
                  f'{HDR_ANCHOR_OFFSET}  -  {_hex_print_format(FW_HDR_ANCHOR)}')

    output_file.close()

def _set_extended_anchor(output, ecst_args):
    """writes the extended anchor value to the output file

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """

    with output.open("r+b") as output_file:
        output_file.seek(HDR_EXTENDED_ANCHOR_OFFSET + \
        ecst_args.paste_firmware_header)
        if ecst_args.firmware_header_crc is FW_HDR_CRC_ENABLE:
            output_file.write(FW_HDR_EXT_ANCHOR_ENABLE.to_bytes(2, "little"))
            anchor_to_print = _hex_print_format(FW_HDR_EXT_ANCHOR_ENABLE)
        else:
            output_file.write(FW_HDR_EXT_ANCHOR_DISABLE.to_bytes(2, "little"))
            anchor_to_print = _hex_print_format(FW_HDR_EXT_ANCHOR_DISABLE)

        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - Header EXTENDED ANCHOR           - Offset'
                  f' {HDR_EXTENDED_ANCHOR_OFFSET}  -  {anchor_to_print}')
        output_file.close()


def _check_firmware_header_offset(output, ecst_args):
    """checks if the firmware header offset entered is valid.
    proportions:

    firmware header offset is a non-negative integer.
    firmware header offset is 16 bytes aligned
    firmware header offset equals/smaller than input file minus
    FW HEADER SIZE (64 KB)
    input file size is bigger than FW HEADER SIZE (64 KB)

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """

    input_file = Path(ecst_args.input)
    paste_fw_offset = ecst_args.paste_firmware_header
    input_file_size = input_file.stat().st_size

    if paste_fw_offset == INVALID_INPUT:
        _exit_with_failure_delete_file(output, "Cannot read paste"
                                               " firmware offset")

    paste_fw_offset_to_print = _hex_print_format(paste_fw_offset)

    if paste_fw_offset & ADDR_16_BYTES_ALIGNED_MASK != 0:
        message = f'Paste firmware address ({paste_fw_offset_to_print}) ' \
            f'is not 16 bytes aligned'
        _exit_with_failure_delete_file(output, message)

    if input_file_size <= HEADER_SIZE:
        message = f' input file size ({input_file_size} bytes) ' \
            f'should be bigger than fw header size ({HEADER_SIZE} bytes)'
        _exit_with_failure_delete_file(output, message)

    if input_file_size - HEADER_SIZE < paste_fw_offset:
        message = f'FW offset ({paste_fw_offset_to_print})should be less ' \
            f'than input file size ({input_file_size}) minus fw header size' \
            f' {HEADER_SIZE}'
        _exit_with_failure_delete_file(output, message)

def _set_spi_flash_maximum_clock(output, ecst_args):
    """Sets the maximum allowable clock frequency (for firmware loading);
    also sets the ratio between the Core clock
    and the SPI clock for the specified mode.
    writes the data into the output file.
    the application is closed, and an error is generated
    if the fields are not valid.

    Bits 2-0 - SPI MAX Clock
    Bit 3: SPI Clock Ratio

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    spi_max_clock_to_write = 0

    with output.open("r+b") as output_file:
        output_file.seek(HDR_SPI_MAX_CLK_OFFSET +
                         ecst_args.paste_firmware_header)
        spi_max_clock = ecst_args.spi_flash_maximum_clock
        spi_clock_ratio = ecst_args.spi_flash_clock_ratio

        if spi_clock_ratio == SPI_CLOCK_RATIO_1_VAL:
            spi_clock_ratio = SPI_CLOCK_RATIO_1
        elif spi_clock_ratio == SPI_CLOCK_RATIO_2_VAL:
            spi_clock_ratio = SPI_CLOCK_RATIO_2
        elif spi_clock_ratio == INVALID_INPUT:
            message = f'Cannot read SPI Clock Ratio'
            output_file.close()
            _exit_with_failure_delete_file(output, message)
        else:
            message = f'Invalid SPI Core Clock Ratio (3) - it should be 1 or 2'
            output_file.close()
            _exit_with_failure_delete_file(output, message)

        if spi_max_clock == SPI_MAX_CLOCK_20_MHZ_VAL:
            spi_max_clock_to_write = SPI_MAX_CLOCK_20_MHZ | spi_clock_ratio
            output_file.write(spi_max_clock_to_write.to_bytes(1, "little"))

        elif spi_max_clock == SPI_MAX_CLOCK_25_MHZ_VAL:
            spi_max_clock_to_write = SPI_MAX_CLOCK_25_MHZ | spi_clock_ratio
            output_file.write(spi_max_clock_to_write.to_bytes(1, "little"))

        elif spi_max_clock == SPI_MAX_CLOCK_33_MHZ_VAL:
            spi_max_clock_to_write = SPI_MAX_CLOCK_33_MHZ | spi_clock_ratio
            output_file.write(spi_max_clock_to_write.to_bytes(1, "little"))

        elif spi_max_clock == SPI_MAX_CLOCK_40_MHZ_VAL:
            spi_max_clock_to_write = SPI_MAX_CLOCK_40_MHZ | spi_clock_ratio
            output_file.write(spi_max_clock_to_write.to_bytes(1, "little"))

        elif spi_max_clock == SPI_MAX_CLOCK_50_MHZ_VAL:
            spi_max_clock_to_write = SPI_MAX_CLOCK_50_MHZ | spi_clock_ratio
            output_file.write(spi_max_clock_to_write.to_bytes(1, "little"))

        elif not str(spi_max_clock).isdigit():
            output_file.close()
            _exit_with_failure_delete_file(output,
                                           "Cannot read SPI Flash Max Clock")
        else:
            message = f'Invalid SPI Flash MAX Clock size ({spi_max_clock}) '
            message += '- it should be 20, 25, 33, 40 or 50 MHz'
            output_file.close()
            _exit_with_failure_delete_file(output, message)

        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - SPI flash MAX Clock              - Offset '
                  f'{HDR_SPI_MAX_CLK_OFFSET}  -  '
                  f'{_hex_print_format(spi_max_clock_to_write)}')
        output_file.close()

def _set_spi_flash_mode(output, ecst_args):
    """Sets the read mode used for firmware loading and enables
    the Unlimited Burst functionality.
    writes the data into the output file.
    the application is closed, and an error is generated
    if the fields are not valid.

    Bits 2-0 - SPI Flash Read Mode
    Bit 3: Unlimited Burst Mode

    Note: unlimburst is not relevant for npcx5mn chips family.

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """

    spi_flash_read_mode = ecst_args.spi_flash_read_mode
    spi_unlimited_burst_mode = ecst_args.unlimited_burst_mode
    spi_read_mode_to_write = 0

    with output.open("r+b") as output_file:
        output_file.seek(HDR_SPI_READ_MODE_OFFSET +
                         ecst_args.paste_firmware_header)
        if spi_flash_read_mode == SPI_NORMAL_MODE_VAL:
            spi_read_mode_to_write = SPI_NORMAL_MODE | spi_unlimited_burst_mode
            output_file.write(spi_read_mode_to_write.to_bytes(1, "little"))
        elif spi_flash_read_mode == SPI_SINGLE_MODE_VAL:
            spi_read_mode_to_write = SPI_SINGLE_MODE | spi_unlimited_burst_mode
            output_file.write(spi_read_mode_to_write.to_bytes(1, "little"))
        elif spi_flash_read_mode == SPI_DUAL_MODE_VAL:
            spi_read_mode_to_write = SPI_DUAL_MODE | spi_unlimited_burst_mode
            output_file.write(spi_read_mode_to_write.to_bytes(1, "little"))
        elif spi_flash_read_mode == SPI_QUAD_MODE_VAL:
            spi_read_mode_to_write = SPI_QUAD_MODE | spi_unlimited_burst_mode
            output_file.write(spi_read_mode_to_write.to_bytes(1, "little"))
        else:
            message = f'Invalid SPI Flash Read Mode ({spi_flash_read_mode}),'
            message += 'it should be normal, fast, dual, quad'
            output_file.close()
            _exit_with_failure_delete_file(output, message)

        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - SPI flash Read Mode              - Offset '
                  f'{HDR_SPI_READ_MODE_OFFSET}  -  '
                  f'{_hex_print_format(spi_read_mode_to_write)}')

    output_file.close()

def _set_error_detection_configuration(output, ecst_args):
    """writes the error detection configuration value (enabled/disabled)
    to the output file

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    with output.open("r+b") as output_file:
        output_file.seek(HDR_ERR_DETECTION_CONF_OFFSET +
                         ecst_args.paste_firmware_header)
        if ecst_args.firmware_crc == FW_CRC_ENABLE:
            err_detect_config_to_print = _hex_print_format(FW_CRC_ENABLE)
            output_file.write(FW_CRC_ENABLE.to_bytes(1, "little"))
        else:
            err_detect_config_to_print = _hex_print_format(FW_CRC_DISABLE)
            output_file.write(FW_CRC_DISABLE.to_bytes(1, "little"))

        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - FW CRC Enabled                   - Offset '
                  f'{HDR_ERR_DETECTION_CONF_OFFSET}  -  '
                  f'{err_detect_config_to_print}')

        output_file.close()

def _set_firmware_load_start_address(output, ecst_args):
    """writes the fw load address to the output file

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    start_ram = ecst_args.chip_ram_address
    end_ram = start_ram + ecst_args.chip_ram_size
    fw_load_addr = ecst_args.firmware_load_address
    fw_length = ecst_args.firmware_length
    fw_end_addr = fw_load_addr + fw_length

    start_ram_to_print = _hex_print_format(start_ram)
    end_ram_to_print = _hex_print_format(end_ram)
    fw_load_addr_to_print = _hex_print_format(fw_load_addr)
    fw_length_to_print = _hex_print_format(fw_length)
    fw_end_addr_to_print = _hex_print_format(fw_end_addr)

    if fw_length == INVALID_INPUT:
        message = f'Cannot read firmware length'
        _exit_with_failure_delete_file(output, message)

    if fw_length & ADDR_16_BYTES_ALIGNED_MASK != 0:
        message = f'Firmware length ({fw_length_to_print}) ' \
            f'is not 16 bytes aligned'
        _exit_with_failure_delete_file(output, message)

    if fw_load_addr is INVALID_INPUT:
        message = f'Cannot read FW Load start address'
        _exit_with_failure_delete_file(output, message)

    if fw_load_addr & ADDR_16_BYTES_ALIGNED_MASK != 0:
        message = f'Firmware load address ({fw_load_addr_to_print}) ' \
            f'is not 16 bytes aligned'
        _exit_with_failure_delete_file(output, message)

    if (fw_load_addr > end_ram) or (fw_load_addr < start_ram):
        message = f'Firmware load address ({fw_load_addr_to_print}) ' \
            f'should be between start ({start_ram_to_print}) '\
            f'and end ({end_ram_to_print}) of RAM'
        _exit_with_failure_delete_file(output, message)

    if fw_end_addr > end_ram:
        message = f'Firmware end address ({fw_end_addr_to_print}) should be '
        message += f'less than end of RAM address ({end_ram_to_print})'
        _exit_with_failure_delete_file(output, message)

    with output.open("r+b") as output_file:
        output_file.seek(HDR_FW_LOAD_START_ADDR_OFFSET +
                         ecst_args.paste_firmware_header)
        output_file.write(ecst_args.firmware_load_address.
                          to_bytes(4, "little"))

        output_file.seek(HDR_FW_LENGTH_OFFSET +
                         ecst_args.paste_firmware_header)
        output_file.write(fw_length.to_bytes(4, "little"))

        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - FW load start address            - Offset '
                  f'{HDR_FW_LOAD_START_ADDR_OFFSET}  -  '
                  f'{fw_load_addr_to_print}')
    output_file.close()

def _set_firmware_entry_point(output, ecst_args):
    """writes the fw entry point to the output file.
    proportions:

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    entry_pt_none = False
    input_file_path = Path(ecst_args.input)
    fw_entry_pt = ecst_args.firmware_entry_point
    fw_use_arm_reset = ecst_args.use_arm_reset
    fw_length = ecst_args.firmware_length
    fw_load_addr = ecst_args.firmware_load_address
    fw_end_addr = fw_load_addr + fw_length

    # check if fwep flag wasn't set and set it to fw load address if needed
    if fw_entry_pt is None:
        entry_pt_none = True
        fw_entry_pt = ecst_args.firmware_load_address

    if not entry_pt_none and fw_use_arm_reset:
        message = f'-usearmrst not allowed, FW entry point already set using '\
            f'-fwep !'
        _exit_with_failure_delete_file(output, message)

    with input_file_path.open("r+b") as input_file:
        with output.open("r+b") as output_file:
            if fw_use_arm_reset:
                input_file.seek(ARM_FW_ENTRY_POINT_OFFSET +
                                ecst_args.paste_firmware_header)
                fw_entry_byte = input_file.read(4)
                fw_entry_pt = int.from_bytes(fw_entry_byte, "little")

            if fw_entry_pt < fw_load_addr or fw_entry_pt > fw_end_addr:
                output_file.close()
                input_file.close()
                message = f'Firmware entry point ' \
                    f'({_hex_print_format(fw_entry_pt)}) ' \
                    f'should be between the FW load address ' \
                    f'({_hex_print_format(fw_load_addr)})' \
                    f' and FW end address ({_hex_print_format(fw_end_addr)})'

                _exit_with_failure_delete_file(output, message)

            output_file.seek(HDR_FW_ENTRY_POINT_OFFSET +
                             ecst_args.paste_firmware_header)
            output_file.write(fw_entry_pt.to_bytes(4, "little"))
        output_file.close()
    input_file.close()

    if ecst_args.verbose == REG_VERBOSE:
        print(f'- HDR - FW Entry point                   - Offset '
              f'{HDR_FW_ENTRY_POINT_OFFSET} -  '
              f'{_hex_print_format(fw_entry_pt)}')

def _set_firmware_crc_start_and_size(output, ecst_args):
    """writes the fw crc start address and the crc size to the output file.
    proportions:
    --crc start address should be 4 byte aligned, bigger than crc end address
    --crc size should be 4 byte aligned, and be set to firmware length minus
    crc start offset by default
    --crc end address is crc start address + crc size bytes

    the application is closed, and an error is generated if the mentioned
    fields not comply with the proportions.

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    fw_crc_size = ecst_args.firmware_crc_size
    fw_crc_start = ecst_args.firmware_crc_start

    if fw_crc_size is None:
        fw_crc_end = ecst_args.firmware_length - 1
        # default value for crc size
        fw_crc_size = ecst_args.firmware_length - fw_crc_start
        ecst_args.firmware_crc_size = fw_crc_size
    else:
        fw_crc_end = fw_crc_start + fw_crc_size - 1

    fw_crc_start_to_print = _hex_print_format(fw_crc_start)
    fw_crc_end_to_print = _hex_print_format(fw_crc_end)
    fw_length_to_print = _hex_print_format(ecst_args.firmware_length)
    fw_crc_size_to_print = _hex_print_format(fw_crc_size)

    if fw_crc_start & ADDR_4_BYTES_ALIGNED_MASK != 0:
        message = f'Firmware crc offset address ' \
            f'({fw_crc_start_to_print}) is not 4 bytes aligned'
        _exit_with_failure_delete_file(output, message)

    if fw_crc_start > fw_crc_end:
        message = f'CRC start address ({fw_crc_start_to_print}) should' \
            f' be less or equal to CRC end address ({fw_crc_end_to_print}) \n'
        _exit_with_failure_delete_file(output, message)

    if fw_crc_size & ADDR_4_BYTES_ALIGNED_MASK != 0:
        message = f'Firmware crc size ({fw_crc_size_to_print}) ' \
            f'is not 4 bytes aligned'
        _exit_with_failure_delete_file(output, message)

    if fw_crc_end > ecst_args.firmware_length - 1:
        message = f'CRC end address ({fw_crc_end_to_print}) should be less' \
            f' than the FW length ({fw_length_to_print}) \n'
        _exit_with_failure_delete_file(output, message)

    with output.open("r+b") as output_file:
        output_file.seek(HDR_FW_ERR_DETECT_START_ADDR_OFFSET +
                         ecst_args.paste_firmware_header)
        output_file.write(fw_crc_start.to_bytes(4, "little"))

        output_file.seek(HDR_FW_ERR_DETECT_END_ADDR_OFFSET +
                         ecst_args.paste_firmware_header)
        output_file.write(fw_crc_end.to_bytes(4, "little"))
        output_file.close()

    if ecst_args.verbose == REG_VERBOSE:
        print(f'- HDR - FW CRC Start                     - Offset '
              f'{HDR_FW_ERR_DETECT_START_ADDR_OFFSET} -  '
              f'{fw_crc_start_to_print}')

        print(f'- HDR - FW CRC End                       - Offset '
              f'{HDR_FW_ERR_DETECT_END_ADDR_OFFSET} -  '
              f'{fw_crc_end_to_print}')

def _set_firmware_length(output, ecst_args):
    """writes the flash size value to the output file
    Note: the firmware length value has already been checked before
    this method

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """

    fw_length = ecst_args.firmware_length
    fw_length_to_print = _hex_print_format(fw_length)

    with output.open("r+b") as output_file:
        output_file.seek(HDR_FW_LENGTH_OFFSET +
                         ecst_args.paste_firmware_header)
        output_file.write(fw_length.to_bytes(4, "little"))
        if ecst_args.verbose == REG_VERBOSE:
            print(f'- HDR - FW Length                        - Offset '
                  f'{HDR_FW_LENGTH_OFFSET} -  '
                  f'{fw_length_to_print}')
    output_file.close()

def _set_flash_size(output, ecst_args):
    """writes the flash size value to the output file
    valid values are 1,2,4,8 or 16 (default is 16).
    the application is closed and the output file is deleted
    if the flash size is invalid

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    flash_size_to_print = ""

    with output.open("r+b") as output_file:
        output_file.seek(HDR_FLASH_SIZE_OFFSET +
                         ecst_args.paste_firmware_header)
        flash_size = ecst_args.flash_size

        if flash_size == FLASH_SIZE_1_MBYTES_VAL:
            output_file.write(FLASH_SIZE_1_MBYTES.to_bytes(4, "little"))
            flash_size_to_print = _hex_print_format(FLASH_SIZE_1_MBYTES)
        elif flash_size == FLASH_SIZE_2_MBYTES_VAL:
            output_file.write(FLASH_SIZE_2_MBYTES.to_bytes(4, "little"))
            flash_size_to_print = _hex_print_format(FLASH_SIZE_2_MBYTES)
        elif flash_size == FLASH_SIZE_4_MBYTES_VAL:
            output_file.write(FLASH_SIZE_4_MBYTES.to_bytes(4, "little"))
            flash_size_to_print = _hex_print_format(FLASH_SIZE_4_MBYTES)
        elif flash_size == FLASH_SIZE_8_MBYTES_VAL:
            output_file.write(FLASH_SIZE_8_MBYTES.to_bytes(4, "little"))
            flash_size_to_print = _hex_print_format(FLASH_SIZE_8_MBYTES)
        elif flash_size == FLASH_SIZE_16_MBYTES_VAL:
            output_file.write(FLASH_SIZE_16_MBYTES.to_bytes(4, "little"))
            flash_size_to_print = _hex_print_format(FLASH_SIZE_16_MBYTES)
        elif not flash_size.isdigit():
            output_file.close()
            _exit_with_failure_delete_file(output, "Cannot read Flash size")
        else:
            message = f'Invalid flash size ({flash_size} MBytes), ' \
                f' it should be 0.5, 1, 2, 4, 8, 16 MBytes \n' \
                f' please note - for 0.5 MBytes flash, enter \'1\' '
            output_file.close()
            _exit_with_failure_delete_file(output, message)

    if ecst_args.verbose == REG_VERBOSE:
        print(f'- HDR - Flash size                       - Offset '
              f'{HDR_FLASH_SIZE_OFFSET} - '
              f' {flash_size_to_print}')
    output_file.close()

def _set_reserved_bytes(output, ecst_args):
    """fills the reserved part of the image at the relevant offset
    with the PAD_BYTE

    :param output: the output file object
    :param ecst_args: the object representing the command line arguments.
    """
    with output.open("r+b") as output_file:
        for i in range(BYTES_TO_PAD):
            output_file.seek(RESERVED_BYTES_OFFSET +
                             ecst_args.paste_firmware_header + i)
            output_file.write(PAD_BYTE)
    output_file.close()

def _set_firmware_header_crc_signature(output, ecst_args):
    """writes the firmware header crc signature (4 bytes)
    to the output file

    :param output: the output file object
    :param ecst_args: the object representing the command line arguments.
    """
    crc_to_print = _hex_print_format(0)

    # calculating crc only if the header crc check is enabled
    if ecst_args.firmware_header_crc != FW_HDR_CRC_DISABLE:

        with output.open("r+b") as output_file:
            crc_calc = 0xffffffff
            table = _create_table()

            for i in range(HDR_FW_HEADER_SIG_OFFSET):
                output_file.seek(ecst_args.paste_firmware_header + i)
                current = output_file.read(1)
                crc_calc = _crc_update(
                    int.from_bytes(current, "little"), crc_calc, table)

            crc = _finalize_crc(crc_calc)
            crc_to_write = crc.to_bytes(4, "little")
            crc_to_print = _hex_print_format(crc)
            output_file.seek(ecst_args.paste_firmware_header +
                             HDR_FW_HEADER_SIG_OFFSET)
            output_file.write(crc_to_write)

        output_file.close()

    if ecst_args.verbose == REG_VERBOSE:
        print(f'- HDR - Header CRC                       - Offset '
              f'{HDR_FW_HEADER_SIG_OFFSET} - '
              f' {crc_to_print}')

def _set_firmware_image_crc_signature(output, ecst_args):
    """writes the firmware image crc signature (4 bytes)
    to the output file.

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    # calculating crc only if the image crc check is enabled
    crc_to_print = _hex_print_format(0)
    if ecst_args.firmware_crc != FW_CRC_DISABLE:

        with output.open("r+b") as output_file:
            crc_calc = 0xffffffff
            table = _create_table()

            output_file.seek(FW_IMAGE_OFFSET + ecst_args.paste_firmware_header +
                             ecst_args.firmware_crc_start)
            for _ in range(ecst_args.firmware_crc_size):
                current = output_file.read(1)
                crc_calc = _crc_update(int.from_bytes(current, "little"), \
                crc_calc, table)

            crc = _finalize_crc(crc_calc)
            crc_to_write = crc.to_bytes(4, "little")
            crc_to_print = _hex_print_format(crc)
            output_file.seek(HDR_FW_IMAGE_SIG_OFFSET +
                             ecst_args.paste_firmware_header)
            output_file.write(crc_to_write)

        output_file.close()

    if ecst_args.verbose == REG_VERBOSE:
        print(f'- HDR - Header CRC                       - Offset '
              f'{HDR_FW_IMAGE_SIG_OFFSET} - '
              f' {crc_to_print}')

def _copy_image(output, ecst_args):
    """copies the fw image from the input file to the output file
    if firmware header offset is defined, just copies the input file to the
    output file

    :param output: the output file object,
    :param ecst_args: the object representing the command line arguments.
    """
    with open(ecst_args.input, "rb") as firmware_image:
        with open(output, "r+b") as output_file:
            if ecst_args.paste_firmware_header == 0:
                output_file.seek(FW_IMAGE_OFFSET)
            else:
                output_file.seek(0)
            for line in firmware_image:
                output_file.write(line)
        output_file.close()
    firmware_image.close()

    # pad fw image to be 16 byte aligned if needed
    input_file_size = Path(ecst_args.input).stat().st_size
    bytes_to_pad_num = abs((16 - input_file_size) % 16)

    with open(output, "r+b") as output_file:
        i = bytes_to_pad_num
        while i != 0:
            output_file.seek(0, 2)  # seek end of file
            output_file.write(PAD_BYTE)
            i -= 1
    output_file.close()

    # update firmware length if needed
    fw_length = ecst_args.firmware_length
    if fw_length is None:
        if ecst_args.paste_firmware_header == 0:
            ecst_args.firmware_length = input_file_size + bytes_to_pad_num
        else:
            ecst_args.firmware_length = input_file_size - HEADER_SIZE - \
                                                ecst_args.paste_firmware_header

def _merge_file_with_bt_header(ecst_args):
    """Merge the BT with the BH according to the bhoffset and pointer flags

    :param ecst_args: the object representing the command line arguments.
    """
    bh_index = ecst_args.bh_offset
    file_name_to_print = ""

    if not ecst_args.input:
        exit_with_failure('No input BIN file selected for'
                          'Bootloader header file.')
    else:
        input_file = Path(ecst_args.input)
        if not input_file.exists():
            exit_with_failure(f'Cannot open {ecst_args.input}')

        if input_file.stat().st_size < bh_index:

            message = f'Bootloader header offset ({bh_index} bytes) should be '
            message += f'less than file size ' \
                f'({input_file.stat().st_size } bytes)'
            exit_with_failure(message)

        # create a file if the output parameter is not None,
        # otherwise write to the input file
        if ecst_args.output is not None:
            output_file = Path(ecst_args.output)
            output_file.touch()
            with input_file.open("r+b") as firmware_image:
                with output_file.open("r+b") as output_file:
                    file_name_to_print = output_file.name
                    for line in firmware_image:
                        output_file.write(line)
                    output_file.seek(bh_index)
                    output_file.write(HDR_PTR_SIGNATURE.to_bytes(4, "little"))
                    output_file.seek(bh_index + 4)
                    output_file.write(ecst_args.pointer.to_bytes(4, "little"))
                output_file.close()
            firmware_image.close()

        else:
            with input_file.open("r+b") as file_to_merge:
                file_name_to_print = file_to_merge.name
                file_to_merge.seek(bh_index + SIGNATURE_OFFSET)
                file_to_merge.write(HDR_PTR_SIGNATURE.to_bytes(4, "little"))
                file_to_merge.seek(bh_index + POINTER_OFFSET)
                file_to_merge.write(ecst_args.pointer.to_bytes(4, "little"))
            file_to_merge.close()

    if ecst_args.verbose == REG_VERBOSE:
        print(Fore.LIGHTCYAN_EX + f'BootLoader Header file:'
              f' {file_name_to_print}')
        print(f'Offset: {_hex_print_format(ecst_args.bh_offset)},'
              f' Signature: {_hex_print_format(HDR_PTR_SIGNATURE)},'
              f' Pointer: {_hex_print_format(ecst_args.pointer)}')

def _create_bt_header(ecst_args):
    """create bootloader table header, consist of 4 bytes signature and
    4 bytes pointer

    :param ecst_args: the object representing the command line arguments.
    """
    if not ecst_args.output:
        exit_with_failure("No output file selected for "
                          "Bootloader header file.")
    else:
        output_file = Path(ecst_args.output)
        if not output_file.exists():
            output_file.touch()
        with open(output_file, "r+b") as boot_loader_header_file:
            boot_loader_header_file.seek(SIGNATURE_OFFSET)
            boot_loader_header_file.write(HDR_PTR_SIGNATURE.to_bytes(4, \
            "little"))
            boot_loader_header_file.seek(POINTER_OFFSET)
            boot_loader_header_file.write(ecst_args.pointer.to_bytes(4, \
            "little"))
        boot_loader_header_file.close()
        if ecst_args.verbose == REG_VERBOSE:
            print(Fore.LIGHTCYAN_EX + f'BootLoader Header file:'
                  f' {output_file.name}')
            print(f'Signature: {_hex_print_format(HDR_PTR_SIGNATURE)}, '
                  f'Pointer: {_hex_print_format(ecst_args.pointer)}')

def _create_table():
    """helper for crc calculation"""
    table = []
    for i in range(256):
        k = i
        for _ in range(8):
            if k & 1:
                k = (k >> 1) ^ 0xEDB88320
            else:
                k >>= 1
        table.append(k)
    return table

def _crc_update(cur, crc, table):
    """helper for crc calculation

    :param cur
    :param crc
    :param table
    """
    l_crc = (0x000000ff & cur)

    tmp = crc ^ l_crc
    crc = (crc >> 8) ^ table[(tmp & 0xff)]
    return crc

def _finalize_crc(crc):
    """helper for crc calculation

    :param crc
    """
    final_crc = 0
    for j in range(NUM_OF_BYTES):
        current_bit = crc & (1 << j)
        current_bit = current_bit >> j
        final_crc |= current_bit << (NUM_OF_BYTES - 1) - j
    return final_crc

def _hex_print_format(value):
    """hex representation of an integer

    :param value: an integer to be represented in hex
    """
    return "0x{:08x}".format(value)

def _exit_with_failure_delete_file(output, message):
    """formatted failure message printer, prints the
    relevant error message, deletes the output file,
    and exits the application.

    :param message: the error message to be printed
    """
    output_file = Path(output)
    if output_file.exists():
        output_file.unlink()

    message = '\n' + message
    message += '\n'
    message += '******************************\n'
    message += '***        FAILED          ***\n'
    message += '******************************\n'
    print(Fore.RED + message)

    sys.exit(EXIT_FAILURE_STATUS)

def _exit_with_success():
    """formatted success message printer, prints the
    success message and exits the application.
    """
    message = '\n'
    message += '******************************\n'
    message += '***        SUCCESS         ***\n'
    message += '******************************\n'
    print(Fore.GREEN + message)

    sys.exit(EXIT_SUCCESS_STATUS)

def main():
    """main of the application
    """
    init()  # colored print initialization for windows

    if len(sys.argv) < 2:
        sys.exit(EXIT_FAILURE_STATUS)

    ecst_obj = EcstArgs()

    if ecst_obj.error_args:
        for err_arg in ecst_obj.error_args:
            message = f'unKnown flag: {err_arg}'
            exit_with_failure(message)
        sys.exit(EXIT_SUCCESS_STATUS)

    # Start to handle booter header table
    _bt_mode_handler(ecst_obj)

if __name__ == '__main__':
    main()
