VOGONS


Munt Reloaded - Development

Topic actions

Reply 940 of 964, by seren

User metadata
Rank Newbie
Rank
Newbie

Mmm, why didn't I see these Qt suggestions earlier. i ran into similar problems trying to add Munt Qt to patchbox OS. Another evening coming up trying this 😀

BTW is there something like Munt nightlies. I have the impression there is quite some Munt development going on, however the version I can find is 2.3.0 and if I'm correct that one is already at least a year old?

Additionally I came across an LV2 version of Munt: https://linuxmusicians.com/viewtopic.php?t=12937
It looks older, so no idea how to make this use the latest version of Munt and additionally how to add this to MODEP (e.g. in Zynthian)

Reply 941 of 964, by Kaminari

User metadata
Rank Oldbie
Rank
Oldbie
seren wrote:

I have the impression there is quite some Munt development going on

Where? Commits on GitHub are far and few between, maybe once every two or three months, mostly cosmetic (docs, copyrights). There have been two new developments in the past year (enhanced mixing and emulation of a bug from the MT-32 Gen 0). Nightly builds are hardly required.

Ryzen 2600X 4.0 GHz | Vega 56 8 GB | DDR4 16 GB | Win7-64 Ultimate | Win10-64 Pro

Reply 943 of 964, by Dominus

User metadata
Rank DOSBox Moderator
Rank
DOSBox Moderator

Well, there has been a lot going on at the time the thread started eight years ago. But since about three or two years, Munt is already exceptionally great and mostly cosmetic stuff needs to be done 😉

Windows 3.1x guide for DOSBox
60 seconds guide to DOSBox

Reply 944 of 964, by realnc

User metadata
Rank Member
Rank
Member

Other than the occasional fix for a bug report or the addition of some feature request (like the "better mixing than the real hardware" functionality), Munt is pretty much done with emulating the MT-32. It sounds identical to an actual MT-32.

Reply 945 of 964, by seren

User metadata
Rank Newbie
Rank
Newbie

Well I got the impression there were still some things on the to do list:
- Proper Jack support (at least for a n00b like me it's fairly impossible to get that working, e.g. do/don't I need portaudio on a Raspberry Pi)
- Building the Qt version for linux is also not straightforward as can be seen in this thread
- Is the experimental GM support still in development?

Reply 946 of 964, by Kaminari

User metadata
Rank Oldbie
Rank
Oldbie

- Experimental GM support

Maybe you're refering to the GM mode that is specific to the Munt VST plugin developed by Zoltán Bacskó.

Ryzen 2600X 4.0 GHz | Vega 56 8 GB | DDR4 16 GB | Win7-64 Ultimate | Win10-64 Pro

Reply 947 of 964, by Kisai

User metadata
Rank Member
Rank
Member

The Dosbox mt32emu patch can use a bit of polish as there are additional features that can be enabled.

First is a gain/reverb gain tweak in midi_mt32.cpp , I'm pretty darn sure this is something on this forum did, but don't recall where.

	/*begin gain and reverb tuning*/
service->setOutputGain(0.01f * section->Get_int("mt32.output.gain"));
service->setReverbOutputGain(0.01f * section->Get_int("mt32.reverb.output.gain"));
/*end reverb tuning*/

if (strcmp(section->Get_string("mt32.reverb.mode"), "auto") != 0) {
Bit8u reverbsysex[] = {0x10, 0x00, 0x01, 0x00, 0x05, 0x03};
reverbsysex[3] = (Bit8u)atoi(section->Get_string("mt32.reverb.mode"));
reverbsysex[4] = (Bit8u)section->Get_int("mt32.reverb.time");
reverbsysex[5] = (Bit8u)section->Get_int("mt32.reverb.level");
service->writeSysex(16, reverbsysex, 6);
service->setReverbOverridden(true);
}
else {
service->setReverbOverridden(false);
}

The second segment addresses features that were introduced in 2.2.0 and 2.3.0 SVN (but not in 2.3.0)

	service->setDACInputMode((MT32Emu::DACInputMode)section->Get_int("mt32.dac"));

service->setReversedStereoEnabled(section->Get_bool("mt32.reverse.stereo"));
#if MT32EMU_VERSION_MAJOR >= 2 && MT32EMU_VERSION_MINOR >1
service->setNiceAmpRampEnabled(section->Get_bool("mt32.niceampramp"));
#endif
//Feature only available in 2.3.0 SVN as of 2019-03-24
#if MT32EMU_VERSION_MAJOR >= 2 && MT32EMU_VERSION_MINOR >3

service->setNicePanningEnabled(section->Get_bool("mt32.nicepanning"));
service->setNicePartialMixingEnabled(section->Get_bool("mt32.nicepartials"));
#endif

This last fix is to address the difference in the thread handing in SDL1 and SDL2

		framesInBufferChanged = SDL_CreateCond();
#if SDL_VERSION_ATLEAST(2,0,0)
thread = SDL_CreateThread(processingThread,"MT32 Thread", NULL);
#else
thread = SDL_CreateThread(processingThread, NULL);
#endif
}

I tested these against every version of MUNT going back to 2.0.1, 2.0.x and below can not be compiled into DOSBOX.

mt32options.h

Fragment 1

Pint = secprop->Add_int("mt32.output.gain", Property::Changeable::WhenIdle, 100);
Pint->SetMinMax(0, 1000);
Pint->Set_help("Output gain of MT-32 emulation in percent, 100 is the default value, the allowed maximum is 1000.");

Pint = secprop->Add_int("mt32.reverb.output.gain", Property::Changeable::WhenIdle, 100);
Pint->SetMinMax(0, 1000);
Pint->Set_help("Reverb output gain of MT-32 emulation in percent, 100 is the default value, the allowed maximum is 1000.");

Fragment 2 (end of file)


const char *mt32srcQuality[] = {"0", "1", "2", "3",0};
Pint = secprop->Add_int("mt32.src.quality", Property::Changeable::WhenIdle, 2);
Pint->Set_values(mt32srcQuality);
Pint->Set_help("MT-32 sample rate conversion quality\n"
"Value '0' is for the fastest conversion, value '3' provides for the best conversion quality. Default is 2.");

Pbool = secprop->Add_bool("mt32.niceampramp", Property::Changeable::WhenIdle, true);
Pbool->Set_help("Toggles \"Nice Amp Ramp\" mode that improves amplitude ramp for sustaining instruments.\n"
"Quick changes of volume or expression on a MIDI channel may result in amp jumps on real hardware.\n"
"When \"Nice Amp Ramp\" mode is enabled, amp changes gradually instead.\n"
"Otherwise, the emulation accuracy is preserved.\n"
"Default is true.");

Pbool = secprop->Add_bool("mt32.nicepanning", Property::Changeable::WhenIdle, false);
Pbool->Set_help("Toggles \"Nice Panning\" mode.\n"
"Allows to toggle the NicePanning mode.\n"
"Despite the Roland\'s manual specifies allowed panpot values in range 0-14,\n"
"the LA - 32 only receives 3 - bit pan setting in fact.In particular, this\n"
"makes it impossible to set the \"middle\" panning for a single partial.\n"
"In the NicePanning mode, we enlarge the pan setting accuracy to 4 bits\n"
"making it smoother thus sacrificing the emulation accuracy.\n"
"This mode is disabled by default. Set to true to enable.\n");

Pbool = secprop->Add_bool("mt32.nicepartials", Property::Changeable::WhenIdle, false);
Pbool->Set_help("Toggles \"Nice Partials\" mode.\n"
"Allows to toggle the NicePartialMixing mode.\n"
"LA-32 is known to mix partials either in-phase (so that they are added)\n"
"or in counter-phase (so that they are subtracted instead).\n"
"In some cases, this quirk isn't highly desired because a pair of closely\n"
"sounding partials may occasionally cancel out.\n"
"In the NicePartialMixing mode, the mixing is always performed in-phase,\n"
"thus making the behaviour more predictable.\n"
"This mode is disabled by default. Set to true to enable.\n");

Attached are the files touched for context rather than a patch as MT32 and FluidSynth will stomp on each other in dosbox.cpp . Dosbox Build r4274. The mt32options.h and midi_mt32.cpp can be dropped in to replace the same files in an already patched dosbox. The platform/config.h reflects the current SVN dosbox with the C_MUNT put in, and this is how I disable/enable it in dosbox builds, this is not in the regular MUNT patch, and is in midi.cpp .

To the best of my knowledge there are no outstanding bugs in the files.

Attachments

Reply 948 of 964, by NewRisingSun

User metadata
Rank Oldbie
Rank
Oldbie

I believe that I have found a bug in smfwav, version 1.5.0, using Munt MT32Emu Library Version 2.3.0, libsmf Version 1.2.

The first attached file, 15-ORIG.MID when converted with smf2wav, gets the timing horribly wrong, yet the file loads and plays correctly in any MIDI file player. The second attached file, 15-FIXED.MID, is where I have added a meta event to the beggining of the last track, and lo, smf2wav suddenly plays the file correctly. For some reason, smf2wav's event parser is confused by tracks that begin with long wait times.

Attachments

Reply 949 of 964, by sergm

User metadata
Rank Oldbie
Rank
Oldbie
NewRisingSun wrote on 2019-12-28, 17:12:

I believe that I have found a bug in smfwav, version 1.5.0, using Munt MT32Emu Library Version 2.3.0, libsmf Version 1.2.

The first attached file, 15-ORIG.MID when converted with smf2wav, gets the timing horribly wrong, yet the file loads and plays correctly in any MIDI file player. The second attached file, 15-FIXED.MID, is where I have added a meta event to the beggining of the last track, and lo, smf2wav suddenly plays the file correctly. For some reason, smf2wav's event parser is confused by tracks that begin with long wait times.

Ugh, I'm close to nuking libsmf and backporting the MIDI parser class from mt32emu-qt...

Reply 950 of 964, by sergm

User metadata
Rank Oldbie
Rank
Oldbie
NewRisingSun wrote on 2019-12-28, 17:12:

I believe that I have found a bug in smfwav, version 1.5.0, using Munt MT32Emu Library Version 2.3.0, libsmf Version 1.2.

The first attached file, 15-ORIG.MID when converted with smf2wav, gets the timing horribly wrong, yet the file loads and plays correctly in any MIDI file player. The second attached file, 15-FIXED.MID, is where I have added a meta event to the beggining of the last track, and lo, smf2wav suddenly plays the file correctly. For some reason, smf2wav's event parser is confused by tracks that begin with long wait times.

Again, I was too curious why it failed, so the rewrite delayed 😀
mt32emu-smf2wav updated that seems to fix this issue.

Reply 951 of 964, by Spikey

User metadata
Rank Member
Rank
Member

Similar to NewRisingSun's post, I have a track that when converted is always wrong, but plays fine in MIDI players.

It's very simple, it's the forest SFX from King's Quest V. Two channels, bird tweet and whiporill. Somehow, the pitch is wrong after conversion, affecting both instruments (everything else is ok, timing etc), no matter what edits I make to the file, or what changes in output settings I use.

Using the latest versions of all binaries (I was still using 2.2, so I updated this and smf2wav, in case the fixes would help).

Attachments

  • Filename
    KQ5Woods.zip
    File size
    1.32 KiB
    Downloads
    26 downloads
    File license
    Public domain

Reply 952 of 964, by sergm

User metadata
Rank Oldbie
Rank
Oldbie

Hmm, both of these FXs are GEN0-specific, IIRC. Are you sure smf2wav is pointed to a ROM directory that does not contain e.g. CM-32L ROM set? AFAICT, there is no way to make smf2wav use specific ROM files so it picks "the best" available. (I'm considering adding an option for it, similar to one available in alsadrv)

Reply 954 of 964, by Spikey

User metadata
Rank Member
Rank
Member
sergm wrote on 2020-04-08, 06:53:

Hmm, both of these FXs are GEN0-specific, IIRC. Are you sure smf2wav is pointed to a ROM directory that does not contain e.g. CM-32L ROM set? AFAICT, there is no way to make smf2wav use specific ROM files so it picks "the best" available. (I'm considering adding an option for it, similar to one available in alsadrv)

Sergm,
Did you ever update SMF2WAV for this? 😀

Reply 955 of 964, by sergm

User metadata
Rank Oldbie
Rank
Oldbie
Spikey wrote on 2020-07-30, 18:10:
sergm wrote on 2020-04-08, 06:53:

Hmm, both of these FXs are GEN0-specific, IIRC. Are you sure smf2wav is pointed to a ROM directory that does not contain e.g. CM-32L ROM set? AFAICT, there is no way to make smf2wav use specific ROM files so it picks "the best" available. (I'm considering adding an option for it, similar to one available in alsadrv)

Sergm,
Did you ever update SMF2WAV for this? 😀

Well, not yet 😀
Basically, it may happen along with adding support for those 2.4.0 nice* options, but I'm on a fence if that is really useful. Couldn't one just have several ROM directories named like "mt32-1.07", "cm32-1.02", etc.? While alsadrv had trouble configuring the ROM dir in the past (now there is the "-f" option), it could be handy, but now is it?
Again, it's not really hard after all 😀

Reply 958 of 964, by clearcase

User metadata
Rank Newbie
Rank
Newbie
sergm wrote on 2018-09-29, 08:29:
At this point, we haven't dealt with CM-32P samples, so there isn't much I can help you with. The sample format may or may not b […]
Show full quote
BrillieMan wrote:

I'm still looking at how Roland compresses the samples. That's how I stumbled on this thread. Because I hope that the algorithm Roland used to compress samples for the MT-32 would be the same as for the D-110, and maybe also the U-110/U-220. They are all from the same time period. And as the MT-32 is very close to the D-110, the CM-32P is hopefully very close to the U-110.

At this point, we haven't dealt with CM-32P samples, so there isn't much I can help you with. The sample format may or may not be identical to the one used in MT-32, but I can describe it briefly in a hope that it may give you a clue.

Actually, in MT-32 the PCM samples are not compressed but converted sample-wise. Each 16-bit value stored is the "signed" base 2 logarithm of the linear sample with additional bit shuffling. The "signed" here means that the sign of the original sample is stored intact, and the logarithm is taken from the absolute value, obviously. The exact decoding algorithm can be seen in methods Synth::loadPCMROM() and LA32FloatWaveGenerator::getPCMSample().

I hope that helps 😀

My interest is decoding the Roland D-50 PCM ROMS which is how I stumbled upon this forum.
Don't know if this is helpful any more as that post I linked to is from a while back and I haven't read through the rest of this thread.

The Roland D-50 appears to encode the ROMs the same as MT-32 and the like.
The Roland D-50 VST emulation (made by Roland) has the decoded ROM data in the resource file of the VST DLL.

Having found the ROM dumps from the original synth online, I thought it might be interesting to see how close the various decoding code is to Roland's own decoded data.

I opened the ROM data in Sound Forge as raw, 16 bit signed little-endian.

I first tried the code posted here PCM ROM Loader -- Rehashed from 2004. Sounded good but inverting it and overlaying it with the known (presumably correct) data from the VST left low level data at about -43dB.

I then tried the same using la32_sampleparse.c posted below the post I linked to and the results were much better with about -76dB signal difference left.

If you read around the post I linked to there's discussion on whether a particular value should be 32767 or 32787. I changed the value in question to 32787 in la32_sampleparse.c, recompiled and re-did the test.

This had much higher difference signal of around 49dB. So 32767 was better.

I haven't tried using the code in munt as I don't know how to get a 16 bit signed int value from the float data that the conversion outputs. Not good at maths. Happy to test though if anyone can point me how to do that.

All this assumes though that the Roland data from the VST is decoded correctly (seems likely) and that the D-50 ROMs are encoded exactly the same as MT-32 and the like.

Reply 959 of 964, by sergm

User metadata
Rank Oldbie
Rank
Oldbie

If you're going to achieve bit-accurate decoding with la32_sampleparse.c, you should first of all get rid of powf and the other float math, which is quite obviously not present in the bare metal. As we've found, LA32 contains just two LUTs, one of them permits calculation of the binary exponent. Although, the implementation in LA32FloatWaveGenerator::getPCMSample is close enough to the integer algorithm.

As to the magic number 32787, I also heavily doubt we could find something like that in the chip (despite technically it must be easy to implement by why?). This constant was found by comparing samples produced by the emulator and captured at the DAC input pins, and KingGuppy promised that the results are accurate to degree of +-1. Still, there are other corners in the current implementation I'd like to clean up, like e.g. pan factor calculation, which also looks rather odd for implementing in hardware. These inaccuracies may happily overlap, so if making everything properly, 32787 might disappear. Therefore, it is rather an implementation detail that is in no way set in stone, feel free to ignore that.