diff --git a/Lib/YMF262-HAL/Inc/GPIO.hpp b/Lib/YMF262-HAL/Inc/GPIO.hpp index cad421d..3a0cfbb 100644 --- a/Lib/YMF262-HAL/Inc/GPIO.hpp +++ b/Lib/YMF262-HAL/Inc/GPIO.hpp @@ -1,20 +1,27 @@ +/** + * @file GPIO.hpp + * @brief Logical types for the YMF262 pin-control interface (used by GPIO policies). + */ #ifndef GPIO_HPP #define GPIO_HPP +/** @brief Logical activation state of a control line (CS, WR, IC...). */ enum class State{ - ACTIVE, - INACTIVE + ACTIVE, ///< Line asserted (the policy maps this to the correct electrical level) + INACTIVE ///< Line deasserted }; +/** @brief Selects what the data bus carries (drives the A0 line). */ enum class Port{ - DATA, - ADDRESS + DATA, ///< Bus carries a data value + ADDRESS ///< Bus carries a register address }; +/** @brief Selects the register bank / array (drives the A1 line). */ enum class Bank{ - BANK_0, - BANK_1, + BANK_0, ///< First register array + BANK_1, ///< Second register array (OPL3 extended registers) }; #endif \ No newline at end of file diff --git a/Lib/YMF262-HAL/Inc/YMF262-HAL.hpp b/Lib/YMF262-HAL/Inc/YMF262-HAL.hpp index d647b29..2fad9f7 100644 --- a/Lib/YMF262-HAL/Inc/YMF262-HAL.hpp +++ b/Lib/YMF262-HAL/Inc/YMF262-HAL.hpp @@ -1,3 +1,8 @@ +/** + * @file YMF262-HAL.hpp + * @brief Hardware Abstraction Layer for the Yamaha YMF262 (OPL3). + */ + #ifndef YMF262_HAL_HPP #define YMF262_HAL_HPP @@ -5,24 +10,42 @@ #include "GPIO.hpp" #include "YMF262-Types.hpp" + +/** + * @brief Hardware Abstraction Layer for the Yamaha YMF262 (OPL3) integrated circuit. + * + * Choreographs the control protocol between the synthesizer IC and the + * microcontroller. The electrical handling of the pins is delegated to the + * GPIOPolicy (template parameter), allowing the logic to be tested with a + * mock without real hardware. + * + * @tparam GPIOPolicy Class type implementing the verbs for electrical pin control + * (set_a0, set_a1, set_cs, set_wr, set_ic, set_data_bus, delay_ticks). + */ template class YMF262_HAL{ private: - GPIOPolicy& _gpio; - uint32_t _t_icw_ticks; - uint32_t _t_as_ticks; - uint32_t _t_ah_ticks; - uint32_t _t_csw_ticks; - uint32_t _t_csr_ticks; - uint32_t _t_ww_ticks; - uint32_t _t_wds_ticks; - uint32_t _t_wdh_ticks; - uint32_t _t_rw_ticks; - uint32_t _t_acc_ticks; - uint32_t _t_rdh_ticks; - uint32_t _t_recovery_ticks; + GPIOPolicy& _gpio; ///< Reference (not a copy) so tests can inspect the same policy instance + uint32_t _t_icw_ticks; ///< Reset Pulse Width + uint32_t _t_as_ticks; ///< Address Setup Time + uint32_t _t_ah_ticks; ///< Address Hold Time + uint32_t _t_csw_ticks; ///< Chip Select Write Width + uint32_t _t_csr_ticks; ///< Chip Select Read Width + uint32_t _t_ww_ticks; ///< Write Pulse Width + uint32_t _t_wds_ticks; ///< Write Data Setup Time + uint32_t _t_wdh_ticks; ///< Write Data Hold Time + uint32_t _t_rw_ticks; ///< Read Pulse Width + uint32_t _t_acc_ticks; ///< Read Data Access Time + uint32_t _t_rdh_ticks; ///< Read Data Hold Time + uint32_t _t_recovery_ticks; ///< Recovery between writes (32 φM cycles of the chip) + /** + * @brief Performs a single bus write cycle (one of the two in a register write). + * @param bank Register bank (drives A1). + * @param port ADDRESS or DATA phase (drives A0). + * @param data Byte to place on the data bus. + */ void write_bus(Bank bank, Port port, uint8_t data){ _gpio.set_a0(port); _gpio.set_a1(bank); @@ -57,20 +80,57 @@ class YMF262_HAL{ _t_rdh_ticks = (uint32_t)(10 * ticks_per_ns); }; + + /** + * @brief Boots the chip: resets it, then selects the operating mode. + * + * Order matters: the chip must be reset first (known state), then the + * mode is set explicitly. After reset the chip defaults to OPL2, so the + * mode is always set deliberately rather than relying on the default. + * + * @param mode Operating mode to configure after reset. + */ void initialize(OPLMode mode){ initial_clear(); set_OPL_Mode(mode); } + + /** + * @brief Writes a value to a YMF262 register. + * + * Performs the chip's two-cycle write protocol: first the register + * address is latched, then the data value. + * + * @param bank Register bank to target (BANK_0 or BANK_1). + * @param reg Register address (0x00–0xFF). + * @param data Value to write. + */ void write(Bank bank, uint8_t reg, uint8_t data){ write_bus(bank,Port::ADDRESS,reg); write_bus(bank,Port::DATA,data); }; + + /** + * @brief Selects OPL2 (compatibility) or OPL3 mode. + * + * Writes the OPL3-enable bit in register 0x105 (bank ARRAY1). + * OPL3 mode unlocks the 4-operator channels and extra waveforms. + * + * @param mode OPLMode::OPL2 or OPLMode::OPL3. + */ void set_OPL_Mode(OPLMode mode){ write(Bank::BANK_1, 0x105, (mode == OPLMode::OPL3) ? 0x01 : 0x00); }; + + /** + * @brief Resets the chip via the /IC (Initial Clear) line. + * + * Holds /IC active for the required Initial Clear Width, then releases it. + * Leaves the chip in a known default state (OPL2 mode). + */ void initial_clear(){ _gpio.set_ic(State::ACTIVE); diff --git a/Lib/YMF262-HAL/Inc/YMF262-Types.hpp b/Lib/YMF262-HAL/Inc/YMF262-Types.hpp index addcfc2..ca70830 100644 --- a/Lib/YMF262-HAL/Inc/YMF262-Types.hpp +++ b/Lib/YMF262-HAL/Inc/YMF262-Types.hpp @@ -1,9 +1,14 @@ -#ifndef YMF262_MODES_HPP -#define YMF262_MODES_HPP +/** + * @file YMF262-Types.hpp + * @brief Chip-level types for the YMF262 (operating mode, and future chip concepts). + */ +#ifndef YMF262_TYPES_HPP +#define YMF262_TYPES_HPP -enum class OPLMode{ - OPL3, - OPL2 +/** @brief YMF262 operating mode. */ +enum class OPLMode { + OPL3, ///< Full OPL3: 4-operator channels and extended waveforms + OPL2 ///< OPL2 compatibility mode (chip default after reset) }; #endif \ No newline at end of file