0

rtmidi library requires setting callback to static function, which should handle incoming midi messages. I found workaround (CinderMidiIn::callback function) but application crashes when I try to send signal after parsing. Here is shortened version of code:

void static callback(double deltatime, std::vector< unsigned char > *message, void *userData){
    ((CinderMidiIn*)userData)->newMidiMessage(deltatime * 1000, message);
}
void newMidiMessage(double deltatime, std::vector< unsigned char > *message){

    midiMessage newMsg(message);

                    //parse message

    //midiSignal(newMsg); /// THIS DOES NEITHER WORKS
    dispatch(newMsg);
}

void dispatch(midiMessage &msg){

    midiSignal(msg);
}

// Signal
boost::signals2::signal<void(midiMessage)> midiSignal;


//// MAIN FUNCTION    ////

void ciMidiIn::midiEvent(midiMessage msg){
cout << "value " << msg.value << endl;
}

void ciMidiIn::setup()
{
midi.midiSignal.connect(boost::bind(&ciMidiIn::midiEvent, this, boost::arg<1>::arg()));
}

I get a ton of warning during compilation and crashes on start (at sending signal at line 149-150) call-stack gives me no clue even where to start looking for solution:

 VanillaRTMidi.exe!boost::signals2::signal1<void,midiMessage,boost::signals2::optional_last_value<void>,int,std::less<int>,boost::function<void __cdecl(midiMessage)>,boost::function<void __cdecl(boost::signals2::connection const &,midiMessage)>,boost::signals2::mutex>::operator()(midiMessage arg1) Line 695 C++
VanillaRTMidi.exe!boost::shared_ptr<boost::signals2::detail::signal1_impl<void,midiMessage,boost::signals2::optional_last_value<void>,int,std::less<int>,boost::function<void __cdecl(midiMessage)>,boost::function<void __cdecl(boost::signals2::connection const &,midiMessage)>,boost::signals2::mutex> >::operator*() Line 646 C++

I've read a lot about static functions and I understand that non static variables cannot access static function, but still, I have no idea how to pass anything into signal and dispatch it from static function.

Disclaimer: Originally posted on Cinder Forums, with link to pastebin containing full code, but as I mentioned at top of original post, this is more likely question for Stack Overflow.

Igor R.
  • 14,716
  • 2
  • 49
  • 83
sphere42
  • 156
  • 1
  • 11
  • 1
    Check that `userData` is a valid pointer to `CinderMidiIn` instance. Make sure that the instance is "alive" (not destroyed) when the callback gets invoked. – Igor R. Feb 21 '14 at 13:40
  • Geez, you are absolutely right! It was even worse, as I forgot to add them completely, ehm... – sphere42 Feb 21 '14 at 14:18

1 Answers1

0

So finally problem was uninitialized user data (thanks Igor R. for pointing that out!) From rtmidi documentation:

void RtMidiIn::setCallback (RtMidiCallback callback, void * userData = 0);

As I was just wrapping rtmidi according to tutorial for midi input, there was no class (everything were just global functions outside of main() ), so I was not thinking about actually setting that pointer up.

Wow, I learned so much along the way...

sphere42
  • 156
  • 1
  • 11