#pragma once
#include <PSX/System/IOPorts/interrupt_io.hpp>
#include <PSX/System/IOPorts/periphery_io.hpp>
#include <PSX/Periphery/periphery.hpp>
#include <stdio.hpp>

extern "C" void busy_loop(int count);

namespace JabyEngine {
    namespace Periphery {
        using namespace Periphery_IO;

        static void connect_to(uint16_t port) {
            JOY_CTRL.write(Periphery_IO_Values::JOY_CTRL::create_for(port));
            busy_loop(500);
        }

        static void close_connection() {
            JOY_CTRL.write(Periphery_IO_Values::JOY_CTRL::close());
        }

        static void send_byte(uint8_t byte) {
            while(!JOY_STAT.is_ready_transfer());
            JOY_TX_DATA.write(Periphery_IO_Values::JOY_TX_DATA::create(byte));
        }

        static uint8_t read_byte() {
            while(!JOY_STAT.has_response());
            return JOY_RX_DATA.read().raw;
        }

        static void acknowledge() {
            while(JOY_STAT.read().is_set(Periphery_IO_Values::JOY_STAT::ACKIrqLow));
            JOY_CTRL.write(JOY_CTRL.read().set(Periphery_IO_Values::JOY_CTRL::ACK));
            
            Interrupt::ack_irq(Interrupt::Periphery);
        }
    }
}