#include "cli.h"
#include "cli_inter_actor.h"
#include "cli_inter_preter.h"
#include "flash.h"
#include <stdint.h>
#include <stdio.h>
// #include "led.h"
// #include "usart.h"
// #include <stdio.h>

#define CLI_ANSI_ENABLE 1

void command_help(void);
void command_version(void);
void command_clear(void);
void command_reset(void);
void command_ps(void);
void command_led_control(void);

command_entry main_table[] = {
    CLI_COMPONENTS_LIST

        command_entry_action_with_detail("help", command_help, "", "help infomation", (const char *const *)NULL),
    command_entry_action_with_detail("version", command_version, "", "show version", (const char *const *)NULL),
    command_entry_action_with_detail("reset", command_reset, "", "reset system", (const char *const *)NULL),
    command_entry_action_with_detail("clear", command_clear, "", "clear screen", (const char *const *)NULL),
    command_entry_action_with_detail("ps", command_ps, "", "print string", (const char *const *)NULL),

    command_entry_terminator()};

command_entry command_debug_table[] = {
    command_entry_action_with_detail("led", command_led_control, "u", "led_control", (const char *const *)0),
    command_entry_terminator()};

uint8_t led_states;
void    command_led_control(void)
{
    if (cli_ipt_arg_list[0][0] == 1)
    {
        // LED2;
        led_states = 1;
    }
    else if (cli_ipt_arg_list[0][0] == 2)
    {
        led_states = 2;
    }
    else
    {
        led_states = 0;
    }
}

command_entry command_ble_table[] = {
    command_entry_terminator()};

command_entry command_eeprom_table[] = {
    command_entry_terminator()};

void command_flash_read(void)
{
    uint32_t read_byte     = 0;
    uint16_t read_buf[100] = {0};
    if (cli_ipt_arg_list[0][0] == 1)
    {
        fmc_clear_flag_star();
        read_byte = fmc_read_byte(cli_ipt_arg_list[1][0]);
        fmc_clear_flag_end();
        CLI_PRINTF("%x\r\n", read_byte);
    }
    else if (cli_ipt_arg_list[0][0] == 2)
    {
        fmc_clear_flag_star();
        read_byte = fmc_read_half_word(cli_ipt_arg_list[1][0]);
        fmc_clear_flag_end();
        CLI_PRINTF("%x\r\n", read_byte);
    }
    else if (cli_ipt_arg_list[0][0] == 3)
    {
        fmc_clear_flag_star();
        read_byte = fmc_read_n_half_word(cli_ipt_arg_list[1][0], read_buf, 10);
        fmc_clear_flag_end();
        CLI_PRINTF("%x\r\n", read_buf);
    }
    else
    {
        led_states = 0;
    }
}

void command_flash_write(void)
{
    uint32_t read_byte     = 0;
    uint16_t read_buf[100] = {0};
    if (cli_ipt_arg_list[0][0] == 1)
    {
        fmc_clear_flag_star();
        read_buf[0] = cli_ipt_arg_list[2][0] >> 8;
        read_buf[1] = cli_ipt_arg_list[2][0];
        read_byte   = fmc_erase_pages(cli_ipt_arg_list[1][0], cli_ipt_arg_list[3][0]);
        CLI_PRINTF("%x\r\n", read_byte);
        read_byte = fmc_write_n_half_word(cli_ipt_arg_list[1][0], read_buf, cli_ipt_arg_list[3][0]);
        fmc_clear_flag_end();
        CLI_PRINTF("%x\r\n", read_byte);
    }
    // else if (cli_ipt_arg_list[0][0] == 2)
    // {
    //     fmc_clear_flag_star();
    //     read_byte = fmc_read_half_word(cli_ipt_arg_list[1][0]);
    //     fmc_clear_flag_end();
    //     CLI_PRINTF("%x\r\n", read_byte);
    // }
    // else if (cli_ipt_arg_list[0][0] == 3)
    // {
    //     fmc_clear_flag_star();
    //     read_byte = fmc_read_n_half_word(cli_ipt_arg_list[1][0], read_buf, 10);
    //     fmc_clear_flag_end();
    //     CLI_PRINTF("%x\r\n", read_buf);
    // }
}

command_entry command_flash_table[] = {
    command_entry_action_with_detail("r", command_flash_read, "uu", "command_flash_read", (const char *const *)0),
    command_entry_action_with_detail("w", command_flash_write, "uuuu", "command_flash_write", (const char *const *)0),
    command_entry_terminator()};

void command_version(void)
{
    CLI_PRINTF("version 3.0.16. CC by[" __DATE__ " " __TIME__ "] \r\n");
}

void command_reset(void)
{
    cli_reset();
}

void command_help(void)
{
    print_entry(main_table);
}

void command_clear(void)
{
#if CLI_ANSI_ENABLE == 1
    CLI_PRINTF("%c[2J", '\033');
    CLI_PRINTF("%c[41A", '\033');
#else
    for (uint8_t i = 0; i < 40; i++)
    {
        CLI_PRINTF("# \r\n");
    }
#endif
}

void command_ps(void)
{
    CLI_PRINTF("%s\r\n", &cli_ipt_arg_list[0][0]);
}

void cli_init(void)
{
    // CLI_COMPONENTS_INIT
}

int  ch = 0;
void cli_loop(void)
{
    // CLI_COMPONENTS_LOOP

    ch = getchar();
    if (ch != -1)
    {
        cli_itt_input(CLI_CHL_COM, ch);
    }
}
