diff options
| -rw-r--r-- | muse/ChangeLog | 3 | ||||
| -rw-r--r-- | muse/muse/midi.cpp | 7 | ||||
| -rw-r--r-- | muse/muse/midiinport.cpp | 44 | ||||
| -rw-r--r-- | muse/muse/midiinport.h | 8 | ||||
| -rw-r--r-- | muse/muse/synth.cpp | 1 | 
5 files changed, 52 insertions, 11 deletions
| diff --git a/muse/ChangeLog b/muse/ChangeLog index b3f2b6e5..65091471 100644 --- a/muse/ChangeLog +++ b/muse/ChangeLog @@ -1,3 +1,6 @@ +29.10 (ws) +      - fixed crash after some time of midi recording: made midi  +        input queue thread safe.  27.10 (ws)        - added a MESS port of the Zynaddsubfx software synthesizer  25.10 (ws) diff --git a/muse/muse/midi.cpp b/muse/muse/midi.cpp index 987567ce..0eaeceb4 100644 --- a/muse/muse/midi.cpp +++ b/muse/muse/midi.cpp @@ -639,15 +639,16 @@ void Audio::initDevices()  void Audio::processMidi()        { +      MidiInPortList* il = song->midiInPorts(); +      for (iMidiInPort id = il->begin(); id != il->end(); ++id) +            (*id)->beforeProcess(); +                    MidiOutPortList* ol = song->midiOutPorts();        for (iMidiOutPort id = ol->begin(); id != ol->end(); ++id) {              (*id)->process(_curTickPos, _nextTickPos, _pos.frame(), _pos.frame() + segmentSize);              } - -      MidiInPortList* il = song->midiInPorts();        for (iMidiInPort id = il->begin(); id != il->end(); ++id) {              MidiInPort* port = *id; -              //              // process routing to synti              // diff --git a/muse/muse/midiinport.cpp b/muse/muse/midiinport.cpp index 8d2db3c9..42fe2677 100644 --- a/muse/muse/midiinport.cpp +++ b/muse/muse/midiinport.cpp @@ -36,7 +36,10 @@  MidiInPort::MidiInPort()     : MidiTrackBase(MIDI_IN)        { -      _channels = 1; +      _channels   = 1; +      recordRead  = 0; +      recordWrite = 0; +      recordCount = 0;        }  //--------------------------------------------------------- @@ -88,6 +91,7 @@ void MidiInPort::read(QDomNode node)  //---------------------------------------------------------  //   midiReceived +//    called from midiSeq context  //---------------------------------------------------------  #ifndef __APPLE__ @@ -96,6 +100,7 @@ void MidiInPort::eventReceived(snd_seq_event_t* ev)        MidiEvent event;        event.setB(0);        event.setTime(audioDriver->framePos()); +        switch(ev->type) {              case SND_SEQ_EVENT_NOTEON:                    event.setChannel(ev->data.note.channel); @@ -173,7 +178,15 @@ void MidiInPort::eventReceived(snd_seq_event_t* ev)              if (i->type() == ME_NOTEON)                    addMidiMeter(i->dataB());              song->putEvent(*i); -            _recordEvents.add(*i); +            if (recordCount == RECORD_FIFO_SIZE) { +                  printf("MusE: eventReceived(): fifo overflow\n"); +                  continue; +                  } +            recordFifo[recordWrite] = *i; +            ++recordWrite; +            if (recordWrite == RECORD_FIFO_SIZE) +                  recordWrite = 0; +            ++recordCount;              }        }  #endif @@ -185,19 +198,36 @@ void MidiInPort::eventReceived(snd_seq_event_t* ev)  void MidiInPort::afterProcess()        { -      _recordEvents.clear(); +      while (tmpRecordCount--) { +            ++recordRead; +            if (recordRead >= RECORD_FIFO_SIZE) +                  recordRead = 0; +            --recordCount; +            } +      } + +//--------------------------------------------------------- +//   beforeProcess +//--------------------------------------------------------- + +void MidiInPort::beforeProcess() +      { +      tmpRecordCount = recordCount;        }  //---------------------------------------------------------  //   getEvents +//    called from jack process context  //---------------------------------------------------------  void MidiInPort::getEvents(unsigned, unsigned, int ch, MPEventList* dst)        { -      for (iMPEvent i = _recordEvents.begin(); i != _recordEvents.end(); ++i) { -            if (i->channel() == ch || ch == -1) -                  dst->insert(*i); +      int tmpRecordRead = recordRead; +      for (int i = 0; i < tmpRecordCount; ++i) { +            dst->insert(recordFifo[tmpRecordRead]); +            ++tmpRecordRead; +            if (tmpRecordRead >= RECORD_FIFO_SIZE) +                  tmpRecordRead = 0;              }        } - diff --git a/muse/muse/midiinport.h b/muse/muse/midiinport.h index d1c294eb..9f2d5134 100644 --- a/muse/muse/midiinport.h +++ b/muse/muse/midiinport.h @@ -23,6 +23,8 @@  #include "track.h" +static const int RECORD_FIFO_SIZE = 512; +  //---------------------------------------------------------  //   MidiInPort  //--------------------------------------------------------- @@ -30,7 +32,10 @@  class MidiInPort : public MidiTrackBase {        Q_OBJECT -      MPEventList _recordEvents; +      MidiEvent recordFifo[RECORD_FIFO_SIZE]; +      int recordRead, recordWrite; +      volatile int recordCount; +      int tmpRecordCount;     public:        MidiInPort(); @@ -47,6 +52,7 @@ class MidiInPort : public MidiTrackBase {        void eventReceived(snd_seq_event_t*);  #endif        virtual void getEvents(unsigned from, unsigned to, int channel, MPEventList* dst); +      void beforeProcess();        void afterProcess();        }; diff --git a/muse/muse/synth.cpp b/muse/muse/synth.cpp index 0e75dad5..1adf3c7b 100644 --- a/muse/muse/synth.cpp +++ b/muse/muse/synth.cpp @@ -554,6 +554,7 @@ iMPEvent MessSynthIF::getData(MPEventList* el, iMPEvent i, unsigned pos, int por  bool MessSynthIF::putEvent(const MidiEvent& ev)        { +// printf("put event %x %x %x\n", ev.type(), ev.dataA(), ev.dataB());        if (midiOutputTrace)              ev.dump();        if (_mess) | 
