All notes off overkill?

• Jun 18, 2021 - 17:03

When MuseScore commences play, or after play is ended, it sends, on every MIDI channel used in the score, a MIDI All Notes Off message. The need for this before play is questionable - it would seem to only take care of the case in which, when play commences, the synthesizer is already sounding a "stuck" note (what an organist would call a "cipher") - not a likely (or tolerable) situation. But perhaps it is good to be scrupulous - "you can't be too careful."

But, as there is apparently insufficient faith in the power of the MIDI All Notes Off command, MuseScore, before play commences, and after play, also sends MIDI Note OFF messages for all 128 possible MIDI "notes" (pitches), over all MIDI channels in use for the score - a potential prefatory utterance of 2048 Note OFF messages.

At the very least, this result in a sometimes mystifying delay of couple of seconds before we really hear any of the notes of the score.

But that is only part of the "problem". "We" often have to employ, for several reasons (including the forensic testing so beloved to this office) a "MIDI loopback driver" (e.g., MIDI Yoke, LoopBe) that allows two MIDI-capable applications to interconnect (an otherwise impermissible same-gender coupling). If this setup is done improvidently, the result can be a "feedback loop" around which a MIDI message or a group of same can mindlessly course at the highest rate accommodated by the players.

To guard against this, many such drivers incorporate a "feedback loop circuit breaker" feature. This is often implemented in a simple way: if the flow of MIDI messages is at an average rate above some threshold for a certain period of time, the driver "mutes" the path to interrupt the phenomenon. The user is given some indication of this (often too subtle) and has to reset the mute (hopefully after correcting the improvident configuration) before the driver will work again.

Some "loopback" drivers allow us to disable this "feedback loop circuit breaker" functionality if it is not needed (and is troublesome), but others don't.

The flood of MIDI Note OFF messages that comes at the start of play (or at the end of play), especially when multiple MIDI channels are involved) can well trip the "circuit breaker" of a loopback driver.

I suggest that the sending of MIDI Note OFF messages for all 128 MIDI "notes" at the beginning and end of play be re-examined.

Doug


Comments

Hi Doug,

Nicely said!

Doug Kerr wrote >> When MuseScore commences play, or after play is ended, it sends, on every MIDI channel used in the score, a MIDI All Notes Off message.

Doug Kerr wrote >> But, as there is apparently insufficient faith in the power of the MIDI All Notes Off command, MuseScore, before play commences, and after play, also sends MIDI Note OFF messages for all 128 possible MIDI "notes" (pitches), over all MIDI channels in use for the score - a potential prefatory utterance of 2048 Note OFF messages.

Here on the Mac, when monitoring with MIDIMonitor 1.4, I too always see these flurries of all notes sent on all channels.

Doug Kerr wrote>> The need for this before play is questionable - it would seem to only take care of the case in which, when play commences, the synthesizer is already sounding a "stuck" note (what an organist would call a "cipher") - not a likely (or tolerable) situation. But perhaps it is good to be scrupulous - "you can't be too careful."

Doug Kerr wrote>> "We" often have to employ, for several reasons (including the forensic testing so beloved to this office) a "MIDI loopback driver" (e.g., MIDI Yoke, LoopBe)

Agreed. I wonder if this cautionary pre-play and post-play behavior is an archaic Musescore safeguard that's now a needless anachronism. The pre-play flurry seems particularly unneeded.

I haven't encountered a "feedback loop short-circuit" interruption, but I do find it annoying that there's always such a large chuck of sent MIDI messages preceding and following the actual state of play. Because it makes it harder to see "what just happened" on the real stage ... and means I'll do some scrolling to find out.

If Musescore feels strongly about retaining this safeguard perhaps we could have a preference for those of us —with enough faith in the All Notes OFF command—who are willing to take our fate in our own hands?

> scorster

In reply to by scorster

In the interest of thoroughness, I point out that, per the MIDI Specification, there are some limitations in the working of the All Notes Off command. The All Sound Off command overcomes some of those limitations. but not all.

The MIDI Note OFF message has some of those same limitations.

I am not at all familiar with the behavior of lots of synthesizers in response to either of those commands.

I just hope that MuseScore does not have to deal with this problem (maybe with respect to the commencement of play it is a non-problem) both "the easy way" and "the hard way".

Doug

I've noticed the behavior and I think it's wreaking a lot of havoc. I'm still investigating, and it's probably worse with JACK because multiple transports are being engaged at the same time (in my case MuseScore/Ardour/xjadeo). And at the very moment the transports are being engaged, a flurry of needless MIDI messages are being sent. And JACK likely has fixed buffers (32kB). It looks like the buffers get filled and that leads to weird behavior and crashes. I wonder if the buffers getting filled is what's occurring when "circuit breaker" is being triggered in the original post.

I think the problems are:

  1. MIDI buffers are being filled and then unexpected behavior occurs
  2. The transports are being started before all the MIDI messages are processed.
  3. I think loops are particularly problematic, cause the same flood of messages are sent when it loops
  4. The exact same frame position is outputted for every MIDI message which might help overload the buffers (I'm guessing)

In the source code,
state = Transport::STOP;
// Muting all notes
stopNotes(-1, true);
initInstruments(true);

And Transport::STOP is called every time transport::PLAY is called.

And then we have this controller data in initInstruments() is sent which is on top of other controller data sent in stopNotes():
// Setting pitch bend sensitivity to 12 semitones for external synthesizers
sendEvent(NPlayEvent(ME_CONTROLLER, channel->channel(), CTRL_LRPN, 0));
sendEvent(NPlayEvent(ME_CONTROLLER, channel->channel(), CTRL_HRPN, 0));
sendEvent(NPlayEvent(ME_CONTROLLER, channel->channel(), CTRL_HDATA,12));
sendEvent(NPlayEvent(ME_CONTROLLER, channel->channel(), CTRL_LRPN, 127));
sendEvent(NPlayEvent(ME_CONTROLLER, channel->channel(), CTRL_HRPN, 127));

Finally, we also can call stopNotes and initInstruments to NOT be in "realtime" but I'm not sure of the implications of that. It ends up calling putEvent(), instead of sendEvent();
void Seq::initInstruments(bool realTime)
void Seq::stopNotes(int channel, bool realTime)

I could start by just bypassing all the code and see if the expected smoothness of playback returns, and then maybe figure out more elegant ways to handle it.
I think we probably want a separate MIDI Panic button, but we also shouldn't expect buffers to be infinite. MIDI has some limitations.

In reply to by oscarcar

Hi, Oscar,

You wrote:

"I wonder if the buffers getting filled is what's occurring when 'circuit breaker' is being triggered in the original post."

No, the "circuit breaker" in a "MIDI loopback driver" is triggered when there is a flow of MIDI messages above some (quite high) average rate for some period of time. (The driver thinks that might be the result of, and thus an indication of, an inadvertent "loop", which the driver feels obligated to quash.)

And that activity occurs when MuseScore sends a MIDI Note OFF message for each of the 128 MIDI pitches on each possible MIDI channel at the commencement, or cessation, of play.

Doug

In reply to by AndreasKågedal

I didn't, but I don't think it's likely that the 3.x branch will get the fix, but I think I've already fixed the code.
I'm just having trouble compiling it correctly. It runs and the MIDI message flood is no longer present, but I'm missing the palette which seems like a fairly common QT compilation issue.

In reply to by Doug Kerr

Just by way of clarification, as observed with MuseScore 3.6.2.548021803, revision 3225f34, I find:

The flurry of MIDI Note OFF messages occurs:
• At the commencement of play
• When play ends naturally at the end of the score.
• When play is stopped before the end of the score.
• When I use the Rewind button.

The set of 128 Note OFF messages seems to be sent on all the MIDI channels that are assigned to a voice. For a default score, all voices are assigned MIDI channel 1, and the set of 128 Note OFF messages is only sent on MIDI channel 1.

As to what happens when there are different MIDI channels assigned, to have different MIDI channels for the different voices, I must first make the voices have different "MuseScore channels", and I don't have the energy just now to fool with that. Maybe after supper.

Doug

In reply to by Doug Kerr

Yes, technically I think it's at transport STOP.
And transport PLAY does transport STOP before starting.
And transport REWIND does transport STOP too.
You point out it does it at the end of score too which is probably not good when integrating with a DAW and recording.

I think it also might do it when you mouse click on a note in the score too, but I'm not sure about that one.

I know that with JACK, if you set any instrument in the mixer to PORT 16, then it'll create all the PORTS in between, so I suspect just setting a single MIDI port to 16 will likely do the trick. Now that's MIDI "PORT", but if you want to see if channel 16 creates messages on all 16, I think you can move just one instrument/voice to channel 16.
There are 16 MIDI ports, and each MIDI port has 16 channels, and each channel has 128 notes.

In reply to by Doug Kerr

[Edited to correct errors]
Well, my biomedical instrumentation showed that my blood glucose level was such that I must have enough energy to do this, so I made a test score with a single staff I assigned an instrument for which there were three MuseScore channels, and they were already assigned MIDI channels 1, 2, and 3. When I played the score, on the occasions I mentioned above, 128 Note OFF messages were sent, first (all 128 of them) on MIDI channel 1, then on MIDI channel 2, then on MIDI channel 3.

Doug

In reply to by oscarcar

I used the Violin instrument, which has three MuseScore channels. I set them to use MIDI ports/channels 1/1, 1/2, and 16/16.

On the various occasions of interest, 128 MIDI Note OFF messages were went, first on MIDI channel 1, then on MIDI channel 2, and then on MIDI channel 16.

The MIDI port assignment does not seem to have any effect on the transmitted MIDI stream; that is, channels 1, 2, and 16 send to the single identified MIDI output "device". We do not have the option, as we do in some other notation programs, to assign different MIDI ports to different MIDI output devices

Encore, for example, has two MIDI ports ("A" and "B)", which can separately be set to different MIDI destination devices.

In Overture, different voices can be set to use different MIDI channels, but for one track (part) everything must go to the same MIDI destination device. (I think!)

And of course there is no concept in the MIDI syntax itself of "ports". That is entirely a construct of a sending device.

I am not sure what use MuseScore makes of the MIDI port assignment of a given stream. Again, I am not aware of any provision in MuseScore for determining which of several possible MIDI destination devices will "MIDI port 1", "MIDI port 2", etc. go to. But there is a lot I don't know!

Doug

In reply to by Doug Kerr

Hi,

Thanks I was actually able to get it up to see. It was a little easier than I was thinking.
You can use Musescore's MIDI port to route to a specific MIDI port in a DAW, but Musescore and the DAW must be using JACK. This is what I was doing, when I was hit with this problem quite dramatically.

Apparently, as you experienced, only if the MIDI port/channel has an instrument/articulation/voice or whatever assigned to it, will it send note offs on them. I was able to verify that it does send it out to other MIDI ports if using JACK.

I also see that there's an extra pitchbend reset sent too, but I'm not sure if that's really needed either.

In reply to by oscarcar

Hi, oscarcar,

Sure, that all makes sense.

Yes, there are many collateral curiosities in this area.

By the way, it is perhaps the most important to send an effective "quiet all" sequence at the end of play, as if a synthesizer has a note pitch stuck on, it is at the end of play they we are most anxious to quiet it.

It is in fact hard for me to see the advantage of sending an "all quiet" sequence at the start of play. If the synthesizer has a note stuck on, we certainly don't want to cure that by starting to play something that will send a quieting sequence on the needed channel(s).

So would it be handy for MuseScore to have a "quiet all" button? Yes.

That's why my initial message on this did not ask for some specific change, but rather that this matter be "rethought".

Thanks again for your work on this.

Doug

In reply to by Doug Kerr

Sure. So with 4 active MIDI channels I see this output now, which is what I gathered it should be:

0: bf 40 00 control change (channel 15): controller 64, value 0
0: bf 7b 00 control change (channel 15): controller 123, value 0
0: bf 79 00 control change (channel 15): controller 121, value 0
0: b0 40 00 control change (channel 0): controller 64, value 0
0: b0 7b 00 control change (channel 0): controller 123, value 0
0: b0 79 00 control change (channel 0): controller 121, value 0
0: b2 40 00 control change (channel 2): controller 64, value 0
0: b2 7b 00 control change (channel 2): controller 123, value 0
0: b2 79 00 control change (channel 2): controller 121, value 0
0: b3 40 00 control change (channel 3): controller 64, value 0
0: b3 7b 00 control change (channel 3): controller 123, value 0
0: b3 79 00 control change (channel 3): controller 121, value 0

The 3 messages on each MIDI channel are:
CTRL_SUSTAIN<64> = 0
CTRL_ALL_NOTES_OFF<123> = 0
CTRL_RESET_ALL_CTRL<121> = 0

After the messages above, the notes start playing:

0: 9f 47 50 note on (channel 15): pitch 71, velocity 80
0: bf 02 50 control change (channel 15): controller 2, value 80
0: 90 43 50 note on (channel 0): pitch 67, velocity 80
0: b0 02 50 control change (channel 0): controller 2, value 80
222: 9f 47 00 note on (channel 15): pitch 71, velocity 0
398: 90 43 00 note on (channel 0): pitch 67, velocity 0
448: 9f 47 50 note on (channel 15): pitch 71, velocity 80
448: bf 02 50 control change (channel 15): controller 2, value 80
670: 9f 47 00 note on (channel 15): pitch 71, velocity 0
896: 9f 47 50 note on (channel 15): pitch 71, velocity 80
94: 9f 47 00 note on (channel 15): pitch 71, velocity 0
320: 9f 4a 50 note on (channel 15): pitch 74, velocity 80
542: 9f 4a 00 note on (channel 15): pitch 74, velocity 0

Oh, and yes I was thinking it would be nice to put this into a midiPanic() function so that it could be reused and no one would need to guess what messages to send. Should be easier for someone to add a !MidiPanic button in the editor.

In reply to by oscarcar

Just wanted to add, it looks like when you tap on any note in the score, it actually does this sequence:

  1. Sends the all note offs on all used MIDI channels
  2. plays the note
  3. Sends the all note offs on all used MIDI channels

Which kind of makes sense, but with #1 and #2 being tons of messages, it's a wonder it plays a note at all. It would often come out garbled for me. I think it would be better to just silence the MIDI channel it's on though, if at all.

In reply to by oscarcar

I like it!

We still should probably revisit when it is sent.

My suggestion:

• When play stops at end of score
• When play is stopped before the end of the score

But if changing the code is easier, or it would make you more comfortable, to also still do this at the commencement of play, that would still be no problem.

Would you always send this on all 16 MIDI channels, or just in the channels that are in use (as at present)? The latter would still make sense.

Doug

In reply to by Doug Kerr

Musescore only sends on channels in use, which I think is great.

Yes, I'd like to remove this from commencement of play, but there should really be a midi panic button I think to handle the scenario of a note left on. What we have now is when a MIDI Panic button ... panics. :)

The thing is, it doesn't sound like MS3.6 is going to get another update, and I've never contributed anything to the project before, so I'm not sure if this is going to get in. Is there a version of like a nightly for the 3.6 branch?
And MS4 audio/midi stuff is getting completely rewritten, so I'm not sure it's useful for the MS4 branch either.

I'll have to inquire and see what the best route is. I still also have to see how to compile for windows, which I'm really not looking forward to, but that's actually the version I need to work.

In reply to by oscarcar

I'm not familiar with the whole development environment, so I don't know what stands where. But I commend you for diving into the code on this matter.

Probably what is really needed is to encourage the developers of MS4 to treat this issue "thoughtfully". Otherwise, even if that area is "completely rewritten", it can inherit (intact) inappropriate notions from the past.

Doug

In reply to by Doug Kerr

More careful reading of the MIDI monitor log shows the following MIDI sequence (described here in its entirety) for the play by MuseScore of a test score comprising only four quarter notes, with an instrument assigned having three MuseScore channels (with separate MIDI channels) and the Dynamics Method at the default:

  1. For each of the MuseScore channels, on the corresponding MIDI channel, an initialization block, comprising:
    • Bank Select MSB, LSB
    • PC (patch select)
    • CC Volume
    • CC Pan Position
    • CC chorus Depth
    • CC Reverb Depth
     
  2. For each of the assigned MIDI channels, this sequence:
    • CC Pedal (sustain) = 0
    • Note OFF messages for all 128 MIDI note numbers
    • CC All Notes Off
    • Pitch Bend = 64 [zero]
     
  3. The notes themselves, for each a Note ON message followed by a Note OFF message. Also, after the Note ON message for the first note, a CC2=80 (part of the dynamics control scheme)
     
  4. For each of the assigned MIDI channels, the sequence described in (2), above.
     
  5. For each of the MuseScore channels, on the corresponding MIDI channel: The sequence described in (1), above.
     
  6. For each of the assigned MIDI channels, the sequence described in (2), above. [Yes, this is a third such utterance.]
     

Doug

In reply to by Doug Kerr

That's helpful. I'm not that clear on #1. I have a lot of stuff turned off for now.
I don't see chorus/reverb stuff but I'm not sure what I'm looking for yet.

There's something in the code inside that sends some CC messages, I'm guessing this also pan stuf:
// Setting pitch bend sensitivity to 12 semitones for external synthesizers:
CTRL_LRPN, 0
CTRL_HRPN, 0
CTRL_HDATA,12
CTRL_LRPN, 127
CTRL_HRPN, 127

In reply to by oscarcar

That stuff apparently sets the pitch bend sensitivity by way of RPN 0. I have to find out more about that. In the "initialization" code I showed, the pitch bend sensitivity is set by way of a dedicated Pitch Bend control message.

I haven't yet seen any RPN messages out of MuseScore.

Interesting.

In reply to by Doug Kerr

Looking at it more, I think I know the main problem.
Every time there is a "set position" call, it will do the MIDI Panic with all the CC changes and the 128 note offs. If I just remove that one, it will do it at STOP but not at PLAY.

I'd like to remove that one, and also to remove the 128 note off too. And the CC changes should be more standard 3 CC changes, and I can leave the pitchbend stuff although I'm a little confused about that, because it looks to me that the midi spec is a 14-bit value, and 8192 would be centered, but musescore has 64 value.

The only problem about removing it from "setPos" is that I'm not sure of all the implications of this. It's probably why we get the flood of MIDI messages at various times which leads to repeats and even by tapping on a note in the score (moves to that note). Actually tapping a note in the score will get you a MIDI panic followed by a single note, followed by another MIDI Panic.

Ok, another thing that is not efficient. If you have 10 instruments and they are all using the exact same MIDI channel, you'll send 10 sets of CC messages and note offs on that same MIDI channel. I probably need to understand better how setPos() fits into the codebase.

The safest thing would be to just remove the 128 note loop part, and maybe make the CC reset more standard.

In reply to by oscarcar

Hi, oscar,

[Edited to correct various errors and clarify some concepts]

You say:

"I can leave the pitchbend stuff although I'm a little confused about that, because it looks to me that the midi spec is a 14-bit value, and 8192 would be centered, but musescore has 64 value."

Well, like so many MIDI things, there are actually both a "big" and "small" part to setting pitch bend, each with 7 bits. Both parts are conveyed by the pitch bend sensitivity message, the low 7 bits in the second byte and the high 7 bits in the third byte.

This then gives us a 14-bit number, and the middle would be 8192 (on a 0-16383 scale basis).

But MuseScore only uses the "big part" (the high 7 bits of the 14), always setting the low part to zero. And in that case, it is common to speak of the value of the message as just the value of those 7 bits (like describing a large number of feet in "hundreds"), and so it looks like we are working on a 0-127 scale, for which the center would be 64 . (That is actually a value of 8192 out of 16383.)

There is of course further confusion in that there are two ways to set pitch bend sensitivity, the pitch bend message and the RPN scheme.

You say:

"Ok, another thing that is not efficient. If you have 10 instruments and they are all using the exact same MIDI channel, you'll send 10 sets of CC messages and note offs on that same MIDI channel."

Yes, and I hate to say it, but none of the other notation programs I have worked on seriously do things like that.

However, it will not usually end well if we have multiple instruments using the same MIDI channel. If they are different instruments (trumpet and violin, for example), we cannot make the synthesizer use different patches for them, and all the notes will have the same timbre.

In any case, I think the 128 x Note OFF needs to go, overall.

Doug

In reply to by Doug Kerr

For example, here:
MS_pitch-bend-02.jpg
is the entry on my MIDI monitor (MIDI-Ox) for the pitch bend command sent as part of the MuseScore initialization routine.

We note that Data Byte 1 (the low part of the 14-bit pitch bend sensitivity value) is 0, and Data Byte 2 (the high part of the pitch bend sensitivity value) is 64. MIDI-Ox does not attempt to report the "value" of this message.

Given that MuseScore only really uses the high part, whose value is 64, it would be common to say that the value of this message was 64. The actual value is of course 8192.

Doug

In reply to by oscarcar

Oscar,

[Am in error to address you as "oscar"?]

No, I would prefer you do it - you are closer to understanding the development environment than I am.

Proposed lead: "Flood of MIDI messages saturates MIDI bus. Avoid sending MIDI reset messages at transport play."

I'm concerned about "saturates the MIDI bus". It is a nice metaphor, but I'm not sure it is technically meaningful.

It also does not address the basic matter of the 128 Note OFF messages probably being bad at any juncture.

We need to be able to concisely articulate what (perhaps in the plural) is wrong with the present working.

I'll see if any better suggestion comes to me overnight!

Doug

In reply to by oscarcar

Oscar,

This seems to relate to the code snippet you showed for initialization of pitch bend sensitivity by way of an RPN. (I did not at the time know when that code would be used.) The code sets the RPN to 0 (the RPN for the pitch bend sensitivity value) with two messages, one for the high part of the RPN and one for the low part of the RPN, then the actual value is sent, with a (single) data entry message, then the RPN arsenal is disabled (by setting the RPN to "all 1s", the RPN for "no RPN").

The complaint is that, in the data entry stage, the data entry should be, as is familiar, done with two messages, one for the "high part" and one for the "low part", However, in MuseScore's implementation, the the "low part" message is not included. (That is because here, as with ordinary the pitch bend message, MuseScore only deals with the high part. The assumption is that if the low part message is not sent, the receiving synthesizer will take it to be 0.

Either the reporter here has reason to believe that, in practice, that may not be the case (and thus the result may be incorrect), or he might just be philosophically disturbed that the entire value is not sent explicitly.

It would certainly be safest to send both the low and high parts of the data entry for an RPM message series.

At least with the Windows version of MuseScore, the pitch bend sensitivity is not initialized (or, as in this example, restored) with the RPN sequence but rather with the "ordinary" pitch bend sensitivity message. But perhaps this form is used when the MIDI interface is specified to use the JACK facility.

The MIDI specification seems to suggest (albeit unclearly, as usual) that the inclusion of the low part data entry message is "optional".

Doug

In reply to by Doug Kerr

INTRODUCTION
I write to propose a framework for study of the matter of MIDI initialization. In fact, at least initially (!) I will limit the discussion to only actual "initialization"; that is, to establishing the initial state of the synthesizer at the commencement of play. The matter of establishing the stet of the synthesizer at the end of play, though perhaps closely related, is different.

CATEGORIZATION OF PROPERTIES
I will categorize the properties of the synthesizer that should perhaps be established through initialization in the following way. I recognize that the assignment of a property to a category is somewhat arbitrary.

Properties that the program allows to be given different values

The scorist may not intentionally set the values of all these properties, but if not, the program provides a default value. Here are important examples of this category:
• Channel volume
• Bank
• Program ("Patch")
• Pan position
• Reverb depth
• Chorus effect depth

Properties that the program does not allow us to give different properties, but whose state we assume

There are many properties in this category, some very obscure. It is not necessarily worthwhile to expressly initialize all of these, since it would be rare that the synthesizer, when we first speak to it, has earlier been set to an "unusual" value of most of these. For some of these, it may in fact be able to set a specific value by some special maneuver in the score. A prominent property of this category is:

• Pitch bend (range, or sensitivity)

Silencing of stuck notes
One property we probably want the synthesizer to have at the commencement of play is that no notes are already sounding.

How might it be that one or more notes are already sounding? Perhaps through some misadventure the last time the synthesizer was spoken to (by "this" program or another having access to the synthesizer as a MIDI destination device).

Is it likely that we would want to terminate such a catastrophe by starting the play of some MuseScore score? Perhaps not. Nevertheless, this category has to be considered (if only because MuseScore currently has a rather bizarre way of dealing with such a situation).

BEHAVIOR OF SYNTHESIZERS
How are we to know how whatever synthesizer is in use will respond to various commands we might consider issuing to properly "initialize" i?. If we assume that the synthesizer is actually conformal to the MIDI Specification General MIDI Specification, then its response to certain messages of interest is known, but for other messages, the MIDI Specification and or the General MIDI Specification are (intentionally?) ambiguous.

But the synthesizer that becomes of interest may not in fact properly conform to the two specifications (it may not even be described as General MIDI compliant, or it may not be operating in its General MIDI mode.

In fact, as to the latter, there are messages in the MIDI repertoire that will direct the synthesizer to adopt its General MIDI mode, if it has other modes. So perhaps this should become part of initialization.

But otherwise, if a synthesizer, nominally General MIDI compliant, does not conform to the specification (at least as we understand the specification!)

But if we recognize that a certain "important" synthesizer (whatever that would be these days) or "many synthesizers" do not respond properly to the preferred way to initialize a certain property, but may respond to another way to initialize that property, then of course we might decide to issue both, "just in case".

AT THE END OF PLAY
A closely related, but certainly separate, issue is, "In what state should we leave the synthesizer when we are, for now; done asking it to speak" There are both philosophical and pragmatic issues here. For example, we should absolutely not leave it "speaking". And perhaps ideally, we should put it in the state it was in when first installed - to restore its virginity. But we have no reasonable way to do that absolutely. Nor should we feel any obligation to do so. After all, when we next speak to it, or when some other program next speaks to it, the synthesizer should initialized before any notes are sent.

That probably does not mean to set certain properties to the values we wanted for the "play job" just completed. It is no convenience to whatever program might next speak to this synthesizer to leave MIDI channel 2 set to the Shamisen patch just because MuseScore had just finished playing a score with a part for the Shamisen.

Doug

In reply to by oscarcar

It is important that we keep separate these two aspects of the issues here

• When should the Great Initialization Sequence should be sent (part of it is now sent three time per play job, and it is sent if we do Rewind).

• Is sending 128 Note OFF messages a reasonable way to insure that the synthesizer does not have a stuck note. (Note that, with respect to the start of play initialization, this is not foolproof is the stuck note is on a MIDI channel not used by the score that is about to be played but got stuck due to some other misadventure.)

Doug

In reply to by Doug Kerr

MIDI Recommended Practice 15 (RP-15) has this to say about the Reset All Controllers message (CC121):


DETAILS:
Upon receipt of Reset All Controllers message (Controller #121) the following actions are taken for the specified MIDI
channel:
• Set Expression (#11) to 127
• Set Modulation (#1) to 0
• Set Pedals (#64, #65, #66, #67) to 0
• Set Registered and Non-registered parameter number LSB and MSB (#98-#101) to null value (127)
• Set pitch bender to center (64/0)
• Reset channel pressure to 0
• Reset polyphonic pressure for all notes to 0.
• Do NOT reset Bank Select (#0/#32)
• Do NOT reset Volume (#7)
• Do NOT reset Pan (#10)
• Do NOT reset Program Change
• Do NOT reset Effect Controllers (#91-#95)
• Do NOT reset Sound Controllers (#70-#79)
• Do NOT reset other channel mode messages (#120-#127)
• Do NOT reset registered or non-registered parameters.
Any other controllers that a device can respond to should be set to 0, or the behavior should be specified and/or documented. If the manufacturer does not want the Reset All Controllers message to affect a particular controller, that is also permissible, as long as the behavior is documented.


Note that this is a per-MIDI-channel effect.

Doug

In reply to by Doug Kerr

[Edited to correct error: in the first paragraph,"CC123" was incorrectly "CC121"; reference to CC123 added in next-to-last paragraph.]
If, before play starts, we are concerned about stuck notes (which might have happened in any number of ways), we should send CC123 on all 16 MIDI channels at the start of play. If we are not concerned about stuck notes, we should not send it at all.

My own thought is that this is not needed at the start of play. If I am sitting here at my computer and one of my synthesizers is sounding a stuck note (for whatever reason), my first thought is not to start MuseScore and play some score hoping that its initialization sequence would cover the channel on which the note was stuck. My first thought is to use the panic control for that synthesizer.

On the other hand,. if that synthesizer is one intimately associated with MuseScore, there might not be any accessible "panic button" (but there probably should be).

But at the end of play, I think it would be desirable to send CC121 (and maybe CC123 as well), perhaps only on the MIDI channels that were supposed to be used in this score, or maybe on all 16 MIDI channels.

We have to be careful not to invent problems that can be solved with tools we see laying in front of us.

Doug

In reply to by Doug Kerr

Yes, this is why anything sending midi messages needs to have a MIDI Panic button. There is no way to guarantee that something didn't behave properly. Someone could unplug the midi cable before a MIDI message completes, a midi buffer could have been overrun with messages and gets dropped (like what's happening now with musescore sending a flood of messages), etc.

And a MIDI Panic button I believe sends on all 16 MIDI channels.

Now I'm not sure what I should include :)

In reply to by oscarcar

For what it's worth, in Cakewalk Home Studio (the "lite" version of the famous Cakewalk MIDI handlers, before they morphed into DAWs and than almost died), with no MIDI sequence loaded, if we punch the Panic/Reset button (of course with nothing playing) the following is sent in the output MIDI stream.

Each of these is sent on MIDI channels 1-16, in that order, before the next is sent:

Pitch Bend = 64:0 ["64"] [zero] +
CC1 = 0 [Modulation] +
CC7 = 127 [Channel volume] (wide open)
CC10 = 64 [Pan position] (center)
CC64 = 0 [Pedal (sustain)] (off) +
CC66 = 0 [Sostenuto] (off) +
CC67 = 0 [Pedal - soft] (off) +
CC121 (= 0) [Reset all controllers]*
CC123 (= 0) [All notes off]
   * Among other things, that should set CC11 = 127 [Expression]
   + This setting should also be made by Reset all controllers

Doug

In reply to by Doug Kerr

Doug Kerr wrote > My own thought is that [ CC121 on all 16 MIDI channels at the start of play] is not needed at the start of play. If I am sitting here at my computer and one of my synthesizers is sounding a stuck note (for whatever reason), my first thought is not to start MuseScore and play some score hoping that its internalization sequence would cover the channel on which the note was stuck. My first thought is to use the panic control for that synthesizer.

Well said, Doug. Your comments reflect my reactions and questions.

I'm glad to see this in discussion again. I find MuseScore's giant initial MIDI "role call" obfuscates working with a MIDI monitor because I have to find the end of the role just to inspect MIDI messages sent at a particular measure or phrase. Collaterally, due to this issue, when using a MIDI monitor to look under the hood the resulting logs are pointlessly flooded by the MIDI roll call, which makes monitor use far less fun.

But back to the core issue: When working sans trepidation on a well behaved piece I'd certainly like the option to eliminate the overzealous (superfluous?) flurry of MIDI messages on Play and on Stop ..., but particularly on Play.

MuseScore could eliminate the role call flurry via a preference setting ... or a command key (like Control-space).

The addition of a toolbar Panic Button would all be alleviate the need for such verbose and unsolicited interventions. That said, I've used MuseScore's synths extensively for over a year and have never encountered a stuck note or controller state.

scorster

In reply to by scorster

I think we are all in agreement with how it should behave.
But w/o a MIDI Panic button, should we add any extra onto the STOP transport?
External MIDI (software or hardware that is getting MIDI messages from musescore) is treated mostly separately from Internal MIDI, so I can make the changes only on External MIDI, in case we are worried about creating problems for users who aren't working with external MIDI.

Can any of you confirm on what you see when a note is clicked on in the score.
I see these MIDI messages

1.
Starts with this on the MIDI channel related to the instrument:
0: bf 02 50 control change (channel 15): controller 2, value 80

2.
For each midi channel in use:
0: bf 40 00 control change (channel 15): controller 64, value 0
-All 128 NOTE OFF

3.
single NOTE ON with velocity 80

4.
For each midi channel in use:
0: bf 40 00 control change (channel 15): controller 64, value 0
-All 128 NOTE OFF

The problem with this one, is I'm having a hard time finding where this gets called in the code. And it's a little unnerving knowing that there's another piece of code somewhere doing something similar. And it behaves differently than just tapping on a note in the piano keyboard. And if you leave a note highlighted in the score, the piano keyboard will stay lightly highlighted, which makes me a little uncomfortable. In addition, sometimes I see the MIDI output actually get stuck at 120th note, and doesn't get to 127 (notes being 0-127).

In reply to by oscarcar

Hi, Oscar,

There are a number of curious and complicated things I would like to pass on that might be helpful (maybe even vital) as you get into these (and related) areas (and I am so glad that you are doing that).

But the formatting and other idiosyncrasies of this forum setup make that rather tedious, and I could do it much more readily via email. If you would send me a note at:

doug@dougkerr.net

then I can pick it up on that basis.

Thanks.

Doug

Do you still have an unanswered question? Please log in first to post your question.