// SPDX-License-Identifier: MPL-2.0
#include "irq/idt.h"
#include "cpu/asm.h"
sh_idt_IDT_ENTRY sh_idt_fill_idt_entry(sh_uint64 offset,sh_uint16 selector,sh_uint8 ist,sh_uint8 type_attr) {
  sh_idt_IDT_ENTRY entry;
  entry.offset_low=(sh_uint16)(offset&0xFFFF);
  entry.selector=selector;
  entry.ist=(sh_uint8)(ist&0x7);
  entry.type_attr=type_attr;
  entry.offset_mid=(sh_uint16)((offset>>16)&0xFFFF);
  entry.offset_high=(sh_uint32)((offset>>32)&0xFFFFFFFF);
  entry.reserved=0;
  return entry;
}
extern void sh_irq_noerr_0(void);
extern void sh_irq_noerr_1(void);
extern void sh_irq_noerr_2(void);
extern void sh_irq_noerr_3(void);
extern void sh_irq_noerr_4(void);
extern void sh_irq_noerr_5(void);
extern void sh_irq_noerr_6(void);
extern void sh_irq_noerr_7(void);
extern void sh_irq_err_8(void);
extern void sh_irq_noerr_9(void);
extern void sh_irq_err_10(void);
extern void sh_irq_err_11(void);
extern void sh_irq_err_12(void);
extern void sh_irq_err_13(void);
extern void sh_irq_err_14(void);
extern void sh_irq_noerr_16(void);
extern void sh_irq_err_17(void);
extern void sh_irq_noerr_18(void);
extern void sh_irq_noerr_19(void);
extern void sh_irq_noerr_20(void);
extern void sh_irq_err_21(void);
extern void sh_irq_noerr_28(void);
extern void sh_irq_err_29(void);
extern void sh_irq_err_30(void);
extern void sh_irq_noerr_32(void);
extern void sh_irq_noerr_33(void);
extern void sh_irq_noerr_34(void);
extern void sh_irq_noerr_35(void);
extern void sh_irq_noerr_36(void);
extern void sh_irq_noerr_37(void);
extern void sh_irq_noerr_38(void);
extern void sh_irq_noerr_39(void);
extern void sh_irq_noerr_40(void);
extern void sh_irq_noerr_41(void);
extern void sh_irq_noerr_42(void);
extern void sh_irq_noerr_43(void);
extern void sh_irq_noerr_44(void);
extern void sh_irq_noerr_45(void);
extern void sh_irq_noerr_46(void);
extern void sh_irq_noerr_47(void);
extern void sh_irq_noerr_254(void);
extern void sh_irq_noerr_255(void);
SH_STATUS sh_idt_fill_idt(sh_idt_IDT *idt) {
  idt->entries[0]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_0,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[1]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_1,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[2]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_2,0x08,2,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[3]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_3,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xF));
  idt->entries[4]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_4,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xF));
  idt->entries[5]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_5,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[6]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_6,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[7]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_7,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[8]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_8,0x08,1,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[9]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_9,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[10]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_10,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[11]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_11,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[12]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_12,0x08,4,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[13]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_13,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[14]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_14,0x08,3,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[16]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_16,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[17]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_17,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[18]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_18,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[19]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_19,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[20]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_20,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[21]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_21,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[28]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_28,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[29]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_29,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[30]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_err_30,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[32]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_32,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[33]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_33,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[34]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_34,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[35]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_35,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[36]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_36,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[37]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_37,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[38]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_38,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[39]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_39,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[40]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_40,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[41]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_41,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[42]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_42,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[43]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_43,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[44]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_44,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[45]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_45,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[46]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_46,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[47]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_47,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[254]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_254,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  idt->entries[255]=sh_idt_fill_idt_entry((sh_uint64)sh_irq_noerr_255,0x08,0,sh_idt_fill_type_attr_byte(SH_TRUE,0,0xE));
  return SH_STATUS_SUCCESS;
}
SH_STATUS sh_idt_load_idtr(sh_idt_IDT *idt) {
  if (idt==SH_NULLPTR) return SH_STATUS_INVALID_PARAMETER;
  sh_idt_IDTR idtr;
  idtr.limit=(sh_uint16)(sizeof(sh_idt_IDT)-1);
  idtr.base=(sh_uint64)idt;
  sh_asm_lidt(idtr);
  return SH_STATUS_SUCCESS;
}
