While writing my VGM parser and investigating the VGMPlay source and surveying the VGMs (BTW if anybody wants to host that all the VGMs on something I can actually download from without the download failing I'd be very happy) I've found a number of errors or things that could use clarification. Here's the list as of the time I'm writing this message (it may grow) - note that these are notes to myself, and may not be entirely clear to other people:
Add missed chip flags
Description of SN76489 variants in the SN76489 flags
Clarify GD3 text encoding
*Look into AY-3-8910 flag meanings
*Clarify interaction between loop modifier and loop base
*Clarify commands 0-0x2f
*Clarify default for YM2203/YM2608 AY-3-8910 flags
* means I don't currently have the knowledge to do it
What is the procedure for updating the spec? Should I do it myself on the wiki (but what about the TXT file in the source code?)? Or does somebody approved have to make the changes?
Updates to the VGM Spec
Technical discussion about the VGM format, and all the software you need to handle VGM files.
Moderator: Staff
- ValleyBell Offline
- Posts: 4783
- Joined: 2011-12-01, 20:20:07
- Location: Germany
You can just edit the wiki.
Please note that the current reference implementation for a VGM player is here:
https://github.com/ValleyBell/libvgm/bl ... player.cpp
https://github.com/ValleyBell/libvgm/bl ... andler.cpp
There are some cases where the old VGMPlay code may be easier to nagivate, but in libvgm I finally removed a few hacks and made the command handling a lot cleaner.
Please note that the current reference implementation for a VGM player is here:
https://github.com/ValleyBell/libvgm/bl ... player.cpp
https://github.com/ValleyBell/libvgm/bl ... andler.cpp
There are some cases where the old VGMPlay code may be easier to nagivate, but in libvgm I finally removed a few hacks and made the command handling a lot cleaner.
Some questions from today's research:
1. It looks like opcode 0 is considered 1-byte and unknown, while 1-0x2f are invalid. Is there any reason these weren't put in the spec as reserved ranges?
2. For Oki M6258 flags bit 2 (ADPCM bits) the spec says that 0 = 4-bit (as it says 0 is the default and it says 4-bit is the default) and 1 = 3-bit. But the code appears to be the opposite. Is the error in the spec or the code?
3. Can you explain the MultiPCM clock and why it's multiplied by 224/180?
4. Can you explain the 4 MHz vs 60 MHz clock for the QSound DSP16A? What systems run them at these rates?
1. It looks like opcode 0 is considered 1-byte and unknown, while 1-0x2f are invalid. Is there any reason these weren't put in the spec as reserved ranges?
2. For Oki M6258 flags bit 2 (ADPCM bits) the spec says that 0 = 4-bit (as it says 0 is the default and it says 4-bit is the default) and 1 = 3-bit. But the code appears to be the opposite. Is the error in the spec or the code?
3. Can you explain the MultiPCM clock and why it's multiplied by 224/180?
4. Can you explain the 4 MHz vs 60 MHz clock for the QSound DSP16A? What systems run them at these rates?
- ValleyBell Offline
- Posts: 4783
- Joined: 2011-12-01, 20:20:07
- Location: Germany
The original VGM v1.50 specification by Maxim defined all the reserved ranges that are in the current spec. and left 00..2F undefined.Quantam wrote:1. It looks like opcode 0 is considered 1-byte and unknown, while 1-0x2f are invalid. Is there any reason these weren't put in the spec as reserved ranges?
Leaving 00 as "no-operation" opcode is mainly to make it not close immediately when you screw up the VGM while hex-editing.
All code I wrote (VGM loggers + players) go by the MAME constants, which are:Quantam wrote:2. For Oki M6258 flags bit 2 (ADPCM bits) the spec says that 0 = 4-bit (as it says 0 is the default and it says 4-bit is the default) and 1 = 3-bit. But the code appears to be the opposite. Is the error in the spec or the code?
Code: Select all
TYPE_3BITS = 0;
TYPE_4BITS = 1;
If I would define this today, I would explicitly make "4-bit = 0", as the current OKI6258 emulator supports only 4-bit ADPCM, so that should be the default.
When MultiPCM support was added about 10 years ago, we assumed a clock divider of 180.Quantam wrote:3. Can you explain the MultiPCM clock and why it's multiplied by 224/180?
Thanks to recent research we were able to figure out the correct clock divider: 224.
Now we have lots of VGMs that assume a clock divider of 180, but the sound emulation code wants 224. Thus we assume /180 for the VGM header and fix the clock to work properly with the new emulation.
The same applies to various other chips like C140 and K054539.
Similarly to MultiPCM, we assumed that the QSound chip runs at 4 MHz.Quantam wrote:4. Can you explain the 4 MHz vs 60 MHz clock for the QSound DSP16A? What systems run them at these rates?
At some point the DSP ROM was dumped and the correct DSP clock was found.
In order to keep compatibility with old VGM rips, we fix the clock if it is 4 MHz.
Oh dear. So some of these are correcting for clock dividers inside the chip, resulting in a frequency that is not what the chip actually runs at? In my case (and it should probably be for the spec as well) I need to know the actual clock rate of the chip (or effective clock rate in cases like the VDP's SSG).
- ValleyBell Offline
- Posts: 4783
- Joined: 2011-12-01, 20:20:07
- Location: Germany
Yes, the clock rates in the VGM header may be different from the (based on current knowledge) real clock rates that the chips run at.
The VGM header clock values were based on the existing knowledge back when the respective chips were added - and for most chips that was 5-10 years ago.
I have to go with certain fallback solutions to prevent existing VGMs on the site from randomly breaking due to a new discovery and fixed emulators.
The VGM header clock values were based on the existing knowledge back when the respective chips were added - and for most chips that was 5-10 years ago.
I have to go with certain fallback solutions to prevent existing VGMs on the site from randomly breaking due to a new discovery and fixed emulators.
- ValleyBell Offline
- Posts: 4783
- Joined: 2011-12-01, 20:20:07
- Location: Germany
Just look at the function VGMPlayer::GenerateDeviceConfig.
That one does all the clock patching in libvgm.
That one does all the clock patching in libvgm.
Yeah, I was doing that yesterday, but I don't know why the adjustments are being made (whether the clock on the input pin is different, or they're compensating for internal division of the clock)ValleyBell wrote:Just look at the function VGMPlayer::GenerateDeviceConfig.
That one does all the clock patching in libvgm.
- ValleyBell Offline
- Posts: 4783
- Joined: 2011-12-01, 20:20:07
- Location: Germany