MusicMaker SMOD Compatibility Issue
Angel Perez (2908) 84 posts |
The BASIC program, MusicMaker, from the Archimedes Gamemakers Manual, works like a charm but it shows signs of a needed upgrade due to compatibility issues over 32-bit processing when loading modules created with it. I am prompted, “(SMOD)-UserVoiceLib is not 32-bit compatible,” whenever I attempt to use any sound module created with it. |
Angel Perez (2908) 84 posts |
As far as I noticed in the BASIC DATA statement listing, MusicMaker was written to create 26-bit sound modules. I need either a new sound module creator, the MusicMaker BASIC program revised or a utility to convert the modules to 32-bit. |
Fred Graute (114) 645 posts |
I’ve only looked at this briefly but it might be that you only need to extend the module header that MusicMaker creates. In PROCmodule there is:
Change this to:
With luck that’s all that needs changing. |
Angel Perez (2908) 84 posts |
To install the new voices to my video game I program in BASIC, I bet you know this already, but once you create the sound module and it works, all you have to do is load it into memory with the * command; just type the name of the module file after the asterisk and the voices are installed for you! Otherwise, I must say, that MusicMaker sure is a time-saving, code-crunching tool for your custom music preload tones and sound effects! Before I edit the MusicMaker file, I need to be sure those lines of code you replied to me with fall in the correct place! |
Angel Perez (2908) 84 posts |
(Fred Graute) Fred – that did it! To signal compatibility with 32-bit modular processing, I renamed the copy of MusicMaker as “MusicMaker_32”. Those lines of code you provided me corrected the bug! |
Angel Perez (2908) 84 posts |
But Fred, though, there is still another bug: now the saved sound modules are pointing to the wrong indices! This time, when I load the module I get, “Illegal voice index” or “%” in module title. |
Angel Perez (2908) 84 posts |
Yet I don’t see any “%” out of place in the lines of code. |
Angel Perez (2908) 84 posts |
While you can think of something to solve that last detail, my diagnosis is that the modules written by MusicMaker attempt to write to an index past 32 after all voice generator indices are in use. One way to remedy is to add to my BASIC game programmes a routine to remove the installed voices when I exit that game. The indices would be once more empty, before the module is loaded and new voice generator index data replaces the old after all the indices have been cleared of the installed voices. |
Chris Hall (132) 3554 posts |
I know that I edited the machine code to cope with Pandaboard – let me have your programme and I can probably work out where the error is. |
Steve Fryatt (216) 2103 posts |
It’s been a while, but I’m fairly sure that “% in module title” relates to multiple instances of modules. I would check your module’s exit code carefully to see if there are any errors which stop it cleaning up and exiting correctly – IIRC, the message can get triggered in place of something more useful when multiple instances of a module arise by mistake. Remember that you’re trying to run example code out of a book from the RISC OS 2/3 era on a modern version of the OS. It’s very likely to need fixing in a number of places. ETA: The % relates to RISC OS’s handling of multiple instances of modules (see book 1 of the PRM for the gory details), so you’re very unlikely to find a stray “%” in your code. |
Fred Graute (114) 645 posts |
Steve’s right, the finalisation code looks iffy – it doesn’t check if a voice has failed to install. This can cause it to pass 0 for the voice number to Sound_RemoveVoice which triggers an abort. Try the code below, it should be more robust.
|
Angel Perez (2908) 84 posts |
Now Fred, I now learned and know much about the SWI call Sound_RemoveVoice but “XSound_RemoveVoice?” I don’t know what part does the “X” in the SWI (if Not Equal) call plays here but when I give MusicMaker another lookover, I’ll look into the code and examine that piece of code you provide. Otherwise, before I check that piece of code you provide here, MusicMaker works great but unless I clear all voice indices with the Sound_RemoveVoice SWI command, I can only load the sound module once. From that point onward you would get the “Illegal voice index” and following attempts to load the module will give you the “‘%’ in module title,” Again, thank you very much! |
Angel Perez (2908) 84 posts |
I am still getting “Illegal voice index” and “‘%’ in module title,” but this time it happenes whenever I attempt to load the sound module while running the MusicMaker program. When I am not using the program, right after booting RISC OS, the modules I create work fine as long as I first clear all voice generator indices with the Sound_RemoveVoice SWI call when no longer needed first and then I load the new sound module in its place. Sometimes I must clear all 32 voice generator indices, even the WaveSynth, StringLib and Percussion generators. Once you run MusicMaker, you will need to reboot RISC OS or you may get again a “‘%’ in module title,” message. Here the problem with the MusicMaker code is that loading the custom sound modules you create with it install the voices at the indices after the indices occupied by the sounds programmed by MusicMaker at the moment of running the programme rather than overwrite the indices. So instead of installing the voices starting at the index of 10, MusicMaker install the voices from the module you create starting at 22 (when you shell to BASIC and type *VOICES, you will see that the module you loaded up starts the index of the installed voices at 22. But since there is no index of 33, the last voice attempted to install is absent. So right now, once you create a sound module with MusicMaker, the sound system does not expect you to use it again with MusicMaker. |
Angel Perez (2908) 84 posts |
There is one more challenge to stand up to. What if you want to install new voices to all 32 indices in a module instead of the standard 12 with MusicMaker? It may take a bit more editing of the code but it’s not impossible. |
Chris Johnson (125) 825 posts |
The X preceding the SWI name is a flag that tells the OS how to deal RISC OS provides full error handling facilities for SWIs. In general, if a SWI has no errors, the V flag in R15 is clear as the routine exits; if there is an error, the V flag is set and R0 points to an error block on exit. As the routine exits, RISC OS checks the V flag. If it is set (meaning there was an error), then RISC OS looks at bit 17 (the X bit) of the SWI number: • If it is set then control returns to your program, and you should deal with the error yourself. • If it is clear control is passed to the system error handler, which reports the error to you. You can of course replace the system error handler with one of your own; indeed, most programs do. Therefore, if the SWI name has a preceding X, control will be passed backed to your program, to make of the error what you will. The normal SWI name will result in the OS itself raising the error. Hope that helps. |
Fred Graute (114) 645 posts |
Chris is right, and it’s how I assumed InstallVoice and RemoveVoice SWIs to work. It turns out however that both calls do not use this convention, instead they signal failure by returning with r1 = 0 (and ptr → error string in r0). So prefixing the SWI name with X is not necessary.
Yes, it seems that way.
MusicMaker checks how many unused voice numbers there are and install voices (up to a maximum of 12) into the free slots. To use all 32 voices you’d have to bypass this test. Doing so would, of course, lose all voices already installed. |
Angel Perez (2908) 84 posts |
Chris (125) Listen to this: MusicMaker can program, in of itself, in its current code writings, up to 12 sound generators. But if you ever wanted to use all 32 of the indices (“channels”) of voice generator instead of the usual 12 in MusicMaker? Among the purposes I have in mind is emulation of speech synthesis (for video games like Berzerk or Q*Bert) and music notation and music synthesiser programs. Due to the nature of MusicMaker in the way it is programmed, it should have been called “SynthMaker” rather than MusicMaker. It works more like a BASIC gaming workstation synthesiser rather than a dedicated music keyboard program. The “Music,” part of the title of BASIC programme only refers to its purpose of generating sound samples for music and sound effects. Since the MusicMaker’s voice generation module creator code is fixed at 12 indices, there has to be a way around if you only want fewer than 12. Reverting the finalisation portion of the code will only allow you to add 12 voice samples at a time subsequently. This piece of code edit for MusicMaker: (The text in bold indicate changes to the contents within that label in the assembler code.) .Finalise Causes the modules created in MusicMaker to overwrite the used indices every time you load a different module. The earlier code that contained: |