| 1 |  | 
|---|
| 2 | // Private oscillators used by Nes_Apu | 
|---|
| 3 |  | 
|---|
| 4 | // Nes_Snd_Emu 0.1.7. Copyright (C) 2003-2005 Shay Green. GNU LGPL license. | 
|---|
| 5 |  | 
|---|
| 6 | #ifndef NES_OSCS_H | 
|---|
| 7 | #define NES_OSCS_H | 
|---|
| 8 |  | 
|---|
| 9 | #include "Blip_Buffer.h" | 
|---|
| 10 |  | 
|---|
| 11 | class Nes_Apu; | 
|---|
| 12 |  | 
|---|
| 13 | struct Nes_Osc | 
|---|
| 14 | { | 
|---|
| 15 | unsigned char regs [4]; | 
|---|
| 16 | bool reg_written [4]; | 
|---|
| 17 | Blip_Buffer* output; | 
|---|
| 18 | int length_counter;// length counter (0 if unused by oscillator) | 
|---|
| 19 | int delay;      // delay until next (potential) transition | 
|---|
| 20 | int last_amp;   // last amplitude oscillator was outputting | 
|---|
| 21 |  | 
|---|
| 22 | void clock_length( int halt_mask ); | 
|---|
| 23 | int period() const { | 
|---|
| 24 | return (regs [3] & 7) * 0x100 + (regs [2] & 0xff); | 
|---|
| 25 | } | 
|---|
| 26 | void reset() { | 
|---|
| 27 | delay = 0; | 
|---|
| 28 | last_amp = 0; | 
|---|
| 29 | } | 
|---|
| 30 | int update_amp( int amp ) { | 
|---|
| 31 | int delta = amp - last_amp; | 
|---|
| 32 | last_amp = amp; | 
|---|
| 33 | return delta; | 
|---|
| 34 | } | 
|---|
| 35 | }; | 
|---|
| 36 |  | 
|---|
| 37 | struct Nes_Envelope : Nes_Osc | 
|---|
| 38 | { | 
|---|
| 39 | int envelope; | 
|---|
| 40 | int env_delay; | 
|---|
| 41 |  | 
|---|
| 42 | void clock_envelope(); | 
|---|
| 43 | int volume() const; | 
|---|
| 44 | void reset() { | 
|---|
| 45 | envelope = 0; | 
|---|
| 46 | env_delay = 0; | 
|---|
| 47 | Nes_Osc::reset(); | 
|---|
| 48 | } | 
|---|
| 49 | }; | 
|---|
| 50 |  | 
|---|
| 51 | // Nes_Square | 
|---|
| 52 | struct Nes_Square : Nes_Envelope | 
|---|
| 53 | { | 
|---|
| 54 | enum { negate_flag = 0x08 }; | 
|---|
| 55 | enum { shift_mask = 0x07 }; | 
|---|
| 56 | enum { phase_range = 8 }; | 
|---|
| 57 | int phase; | 
|---|
| 58 | int sweep_delay; | 
|---|
| 59 |  | 
|---|
| 60 | typedef Blip_Synth<blip_good_quality,15> Synth; | 
|---|
| 61 | const Synth* synth; // shared between squares | 
|---|
| 62 |  | 
|---|
| 63 | void clock_sweep( int adjust ); | 
|---|
| 64 | void run( cpu_time_t, cpu_time_t ); | 
|---|
| 65 | void reset() { | 
|---|
| 66 | sweep_delay = 0; | 
|---|
| 67 | Nes_Envelope::reset(); | 
|---|
| 68 | } | 
|---|
| 69 | }; | 
|---|
| 70 |  | 
|---|
| 71 | // Nes_Triangle | 
|---|
| 72 | struct Nes_Triangle : Nes_Osc | 
|---|
| 73 | { | 
|---|
| 74 | enum { phase_range = 16 }; | 
|---|
| 75 | int phase; | 
|---|
| 76 | int linear_counter; | 
|---|
| 77 | Blip_Synth<blip_good_quality,15> synth; | 
|---|
| 78 |  | 
|---|
| 79 | int calc_amp() const; | 
|---|
| 80 | void run( cpu_time_t, cpu_time_t ); | 
|---|
| 81 | void clock_linear_counter(); | 
|---|
| 82 | void reset() { | 
|---|
| 83 | linear_counter = 0; | 
|---|
| 84 | phase = phase_range; | 
|---|
| 85 | Nes_Osc::reset(); | 
|---|
| 86 | } | 
|---|
| 87 | }; | 
|---|
| 88 |  | 
|---|
| 89 | // Nes_Noise | 
|---|
| 90 | struct Nes_Noise : Nes_Envelope | 
|---|
| 91 | { | 
|---|
| 92 | int noise; | 
|---|
| 93 | Blip_Synth<blip_med_quality,15> synth; | 
|---|
| 94 |  | 
|---|
| 95 | void run( cpu_time_t, cpu_time_t ); | 
|---|
| 96 | void reset() { | 
|---|
| 97 | noise = 1 << 14; | 
|---|
| 98 | Nes_Envelope::reset(); | 
|---|
| 99 | } | 
|---|
| 100 | }; | 
|---|
| 101 |  | 
|---|
| 102 | // Nes_Dmc | 
|---|
| 103 | struct Nes_Dmc : Nes_Osc | 
|---|
| 104 | { | 
|---|
| 105 | int address;    // address of next byte to read | 
|---|
| 106 | int period; | 
|---|
| 107 | //int length_counter; // bytes remaining to play (already defined in Nes_Osc) | 
|---|
| 108 | int buf; | 
|---|
| 109 | int bits_remain; | 
|---|
| 110 | int bits; | 
|---|
| 111 | bool buf_empty; | 
|---|
| 112 | bool silence; | 
|---|
| 113 |  | 
|---|
| 114 | enum { loop_flag = 0x40 }; | 
|---|
| 115 |  | 
|---|
| 116 | int dac; | 
|---|
| 117 |  | 
|---|
| 118 | cpu_time_t next_irq; | 
|---|
| 119 | bool irq_enabled; | 
|---|
| 120 | bool irq_flag; | 
|---|
| 121 | bool pal_mode; | 
|---|
| 122 | bool nonlinear; | 
|---|
| 123 |  | 
|---|
| 124 | int (*rom_reader)( void*, cpu_addr_t ); // needs to be initialized to rom read function | 
|---|
| 125 | void* rom_reader_data; | 
|---|
| 126 |  | 
|---|
| 127 | Nes_Apu* apu; | 
|---|
| 128 |  | 
|---|
| 129 | Blip_Synth<blip_med_quality,127> synth; | 
|---|
| 130 |  | 
|---|
| 131 | void start(); | 
|---|
| 132 | void write_register( int, int ); | 
|---|
| 133 | void run( cpu_time_t, cpu_time_t ); | 
|---|
| 134 | void recalc_irq(); | 
|---|
| 135 | void fill_buffer(); | 
|---|
| 136 | void reload_sample(); | 
|---|
| 137 | void reset(); | 
|---|
| 138 | int count_reads( cpu_time_t, cpu_time_t* ) const; | 
|---|
| 139 | }; | 
|---|
| 140 |  | 
|---|
| 141 | #endif | 
|---|
| 142 |  | 
|---|
| 143 |  | 
|---|