gtaylormb / opl3_fpga

Reverse engineered SystemVerilog RTL version of the Yamaha OPL3 (YMF262) FM Synthesizer
GNU Lesser General Public License v3.0
359 stars 43 forks source link

[feature request] User-defined waveforms #5

Open sdsnatcher opened 8 years ago

sdsnatcher commented 8 years ago

The OPL3 core has 8 hardcoded waveforms in ROM. It would be great if a small improvement could be done to this core: to allow the programmer to rewrite the waveforms with new ones at any given time, just like the Konami SCC/SCC+ soundchips (and the similar PC-Engine soundchip). This way much richer sounds could be created at very little additional cost.

Expand E0h~F5h register to allow 16 waveforms, or even 256 waveforms wouldn't be bad too.

Backwards compatibility would be maintained, since the usual waveforms would be loaded on reset, and existing software could even take advantage of the new waveforms if the user loads a new set of waveforms before running the old software.

References: http://en.wikipedia.org/wiki/Konami_SCC http://en.wikipedia.org/wiki/Konami_Sound_Cartridge http://bifi.msxnet.org/msxnet/tech/scc http://bifi.msxnet.org/msxnet/tech/soundcartridge

gtaylormb commented 8 years ago

Some clarification on the 6 waveforms in the OPL3:

There is a lot of block RAM left in the FPGA for introducing new waveforms. These block RAMs can be configured as ROMs using hardcoded values, which is how the two existing ROM tables are implemented (see https://github.com/gtaylormb/opl3_fpga/blob/master/fpga/modules/operator/src/opl3_log_sine_lut.sv for an example). The easiest way to implement additional waveforms would be to hardcode them in the same way, then introduce an additional register to select them.

I think what you want however is the ability to write ROMs after FPGA configuration using a software interface. This is a fairly more complicated approach from a hardware standpoint. Definitely a cool project idea.

sdsnatcher commented 8 years ago

Thanks for your quick reply!

I've read the nice "OPLx decapsulated" document some time ago, and was aware that the waveforms were stored somewhat compressed in the ROMs. Very nifty! :)

You deduced it correctly: I would like to allow client software to write new waveforms using a software interface. This single modification is able to vastly improve the OPL3 capability of producing incredible synthetic sounds. I wonder why Yamaha themselves haven't done this for the FM block of the OPL4.

Keeping all that and the backward compatibility in mind, I humbly suggest the custom-waveform extension to be implemented in the following way:

1) Modify the engine a bit, to play all waveforms uncompressed, from RAM instead of the ROM. Each waveform should be 1024 words long. (thus 2KB)

2) Expand the E0h~F5h registers (Waveform select) to allow selection of as many waveforms as the FPGA has enough RAM to contain, up to 256 IDs.

3) Upon reset, the original OPL3 waveforms are decompressed from the waveform-ROM to their respective positions in waveform-RAM.

4) To allow client-software to modify the waveforms in RAM, 4 new registers must be created

1FCh: Set the waveform address LSB 1FDh: Set the waveform address MSB (bit9~bit10) 1FEh: Select the waveform to be written. 1FFh: Waveform data (LSB, then MSB). Each MSB written here will autoincrement the waveform address

Of course this is only still a draft, maybe there are some issues that I'm not aware. Feel free to throw your tomatoes. :)