On Tue, Apr 02, 2013 at 08:24:20PM +0200, Jan Stary wrote: > > If I run sndiod without any other options, and launch fluidsynth, > the MIDI notes I play on the MIDI keyboard do not make it to > the running fluidsynth. >
yes, because fluidsynth listens on midithu/0, while notes are available on rmidi/0 > (For people who use a MIDI keyboard to play fluidsynth: > how do you do it, in current?) > > Instead, this is what happens (sndiod -ddd). > Please comment if I am reading it wrong: > > > # sndiod -ddd > snd0 pst=cfg.default: rec=0:1 play=0:1 vol=23170 dup > listen(/tmp/aucat/aucat0|ini): created > > fluidsynth is started: > > sock(sock|ini): created > sock,rmsg,widl: AUTH message > sock,rmsg,widl: HELLO message > sock,rmsg,widl: hello from <fluidsynth>, mode = 1, ver 7 > sock,rmsg,widl: using snd0 pst=cfg.default, mode = 1 > fluidsy0: overwritten slot 0 > > fluidsynth asks for an audio device: > > snd0 pst=cfg: device requested > sio(rsnd/0|ini): created > snd0 pst=ini: 48000Hz, s16le, play 0:1, rec 0:1, 9 blocks of 960 frames > sock(sock|ini): processed in 39680us > > fluidsynth negotiates audio parameters: > > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: SETPAR message > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: playback channels 0:1 -> 0:1 > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: 44100Hz sample rate, 882 frame > blocks > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: 1764 frame buffer > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: GETPAR message > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: GETPAR message > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: GETPAR message > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: START message > fluidsy0 vol=127,pst=ini,mmc=off: playing s16le -> s16le > fluidsy0 vol=127,pst=ini,mmc=off: allocated 1764/9702 fr buffers > fluidsy0 vol=127,pst=sta,mmc=off: 44100Hz, s16le, play 0:1, 2 blocks of 882 > frames > fluidsy0 vol=127,pst=sta,mmc=off,rmsg,widl: building SETVOL message, vol = 127 > > fluidsynth connects again: what is this? > trying to connect to midithru/0? yes, it opens it's midi input (midithru/0) > > sock(sock|ini): created > sock,rmsg,widl: AUTH message > sock,rmsg,widl: HELLO message > sock,rmsg,widl: hello from <fluidsynth>, mode = 8, ver 7 audio starts: > snd0 pst=ini: device started > snd0 pst=run: started > fluidsy0 vol=127,pst=run,mmc=off: attached at -7938 > cmap: nch = 2, ostart = 0, onext = 0, istart = 0, inext= 0 > resamp: 882/960 > fluidsy0 vol=127,pst=run,mmc=off: set weight: 23170/23170 > sock(sock|ini): processed in 11250us > sio(rsnd/0|ini): processed in 11450us > > Now, without anything hapenning in fluidsynth: > > snd0 pst=run: write blocked at cycle start > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > [...] > snd0 pst=run: write blocked at cycle start > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > > Here I exit fluidsynth: > > midi1,rmsg,widl: BYE message > midi1,rmsg,widl: closing > sock(sock|bus): destroyed > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > fluidsy0 vol=127,pst=run,mmc=off,rmsg,widl: STOP message > fluidsy0 vol=127,pst=run,mmc=off: stopping > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: write blocked at cycle start > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: stopped > snd0 pst=run: write blocked at cycle start > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: building STOP message > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: BYE message > fluidsy0 vol=127,pst=ini,mmc=off,rmsg,widl: closing > snd0 pst=run: device released > sock(sock|bus): destroyed > snd0 pst=run: play hw xrun, pused = 6720/8640 > snd0 pst=run: rec hw xrun, rused = 1920/8640 > snd0 pst=run: device stopped > snd0 pst=run: stopped, load avg = 119135 / 6179276 > snd0 pst=ini: closing > snd0 pst=cfg: closed > sio(rsnd/0|bus): destroyed > sio(rsnd/0|bus): processed in 50941us > > Here I exit sndiod: > > ^Clisten(/tmp/aucat/aucat0|bus): destroyed > snd0 pst=cfg: draining > nothing to do... > snd0 pst=cfg: deleting > > > Occasionaly, I also see the above > with mplayer or ffplay playing a movie. > > > On Apr 02 10:05:31, a...@caoua.org wrote: > > > snd0: write blocked at cycle start > > > snd0: write blocked at cycle start > > > > The device didn't accept data to play when it was supposed to; > > probably a driver bug; is this uaudio? > > Yes. > > > If so, you can try this > > magic rate and block size options: > > > > sndiod -r 44100 -z 2940 <your_options> > > Yes; with these magic options, the above error messages disappear. > Fluidsynth can connect and disconnect repeatedly (while other clients > connect and disconnect), and the above never happens _with_fludisynth_ > - thank you. However, I still occasionally see it with ffplay or > mplayer. > > If this is a bug in uaudio(4), what can I do to help debug it? I've a mobile pre as well (the 16-bit one) and fixing this is on my todo list. But all this requires some free time. You can help by reading the usb spec and trying to understand the driver and to fix it to take into account sndio constraints. > (I have this M-Audio Mobile Pre, and an M-Audio Mobile MK II to test on.) > > Anyway, this does not solve the original problem, which is > a different issue: the MIDI events are not getting > to the running fluidsynth. > [...] > midi0 is indeed the MIDI keyboard. So: > sndiod exposes "midithru/0", fluidsynth listens to it, > but nothing ever happens on midithru/0; > fluidsynth needs to listen to rmidi/0 > - which happens automatically if sndiod is not running. > Right? > exactly. > Is there a way to tell (from sndiod debug, preferably) > to which exact midi port an application has connected? rmidi/N don't involve sndiod and the device is not logged in libsndio. midithru/N and midi/N are sndiod connections but they are not logged either. > The debug is detailed about _audio_ devices, as in > > snd0 pst=cfg: device requested > sio(rsnd/0|ini): created > snd0 pst=ini: 48000Hz, s16le, play 0:1, rec 0:1, 9 blocks of 960 frames > sock(sock|ini): processed in 39680us > > - is there a way to get such a detailed info > about connections (and disconnections) to the > exposed midi ports and midithru boxes? this is not logged either, and there's no utility to expose connections, unfortunately internally sndiod has 32 MIDI "endpoints" (struct midi) and any endpoint can be connected to any number of other endpoints, in which case data is propagated between them. They may be used for h/w ports (struct port), clients (struct sock) or for audio device control (struct dev); midithu boxes are simple lists (bitmaps) of connected endpoints. If you think that this is useful, feel free to roll a diff to that nicely logs midi connection changes when log_level >= 2 Having a tool to manage connections would be nice, but this would be much more work. > > > e.g.: (this is on OpenBSD 5.2) > > > I run sndiod with the -M option. AFAICT this gives me a MIDI through box > > > (midithru/0). > > This is supposed to happen automagically in current, right? Yes, sndiod always starts with 16 midithru ports. > At least, there is no -M option to sndiod, and the manpage says > > sndiod exposes MIDI thru boxes (hubs), allowing programs to > send MIDI messages to each other or to hardware MIDI ports in > a uniform way. > > > > fluidsynth will automatically connect to its output. > > Looking at the fluid_sndio.c patch file: > > /* get the device name. if none is specified, use the default device. */ > if (!fluid_settings_getstr(settings, "midi.sndio.device", &device)) { > device = NULL; > } > /* open the default hardware device. only use midi in. */ > dev->hdl = mio_open(device, MIO_IN, 0); > > In fluidsynth's settings, midi.sndio.device is "default". > So we are mio_open()ing "default", which by sndio(7) means > "any audio device or MIDI port". > > So the reason it connects to "midithru/0" > involves some _precedence_ in the following, right? > exactly, and it seems that the origin of your problems is the lack of documentation about this. libsndio tries midithru/0, if it doesn't work it tries rmidi/0 and if this doesn't work either, mio_open() fails. > rsnd Raw audio(4) device. > rmidi Raw midi(4) port. > snd Audio device exposed by sndiod(1). > midithru MIDI thru box created with sndiod(1). > midi MIDI port exposed by sndiod(1). > default Any audio device or MIDI port. > > > On Apr 02 12:54:09, s...@spacehopper.org wrote: > > > > My cases all involve sending midi messages, they're generated from a > > > > program rather than a controller, but definitely sent via sndiod to > > > > fluidsynth. > > > > > > Would you please kindly share your sndiod line? > > > > > > Do you simply start sndiod, launch fludisynth, > > > and then other apps can send midi messages to > > > (the sndio-exposed) midithru/0 and that gets > > > them to fluidsynth who plays them? > > > > Yes, this is all using default settings, I'm running sndiod as a > > system daemon with no flags, then in two terminals I run these: > > > > $ fluidsynth /usr/local/share/generaluser-gs/GeneralUser_GS.sf2 > > > > $ midiplay -vv -x > > > > (midiplay -x plays an internal test file, I can also explicitly > > force the device e.g. "-f midithru/0", it works either way.) > > Does this work for you? > > Yes it does. Which means fluidsynth really must be > listening to midithru/0, if that's what midiplay plays to > (it mio_open()s NULL). > > Which probably means that midithru/0 as exposed by sndiod > is not interconnected with rmidi/0 (which is the keyboard); > so an application that listens to midithru/0 cannot hear > the keyboards. exactly. > > > In my mind all you have to do is use a tool (aucat/midish) > > > to connect your keyboard to the MIDI through box. > > Yes. > > > > aucat -M -q midithru/0 -q rmidi/0 > > Yes, this works. > > But there should be a way to connect the output > of the MIDI keyboard (midi0) as an input to > midithru/0 (so that applications listening > to midithru/0, such as fluidsynth, can hear it) > _without_ running a separate 'aucat -M', right? > My problem is not specific to fluidsynth after all: > any other MIDI application (conecting to midithru/0) > will be interested in listening to those MIDI keyboards > (or any other MIDI HW for that matter). > Well, you must tell MIDI programs what port(s) to use. Programs can't guess which ports to use. While using multiple audio devices simultaneously doesn't make much sense, using plenty of MIDI ports simultaneously is quite common. The whole concept of "default MIDI port" is very limited. So, unless you're lucky MIDI is unlikly to work by default without some minimal setup. It's pretty much like network interfaces, some minimal configuration is necessary. The current "midithru/0" default is to allow games and/or simple MIDI players to work with softsynths, but this is an arbitrary choice. > Starting sndiod with '-q rmidi/0' doesn't do it - it exposes rmidi/0, > but does not connect it to the midithru/0 box > where I would like fluidsynth to find it. > Yeah, you can create a kind of midi-thru box with rmidi/0 subscribed to it with "-q rmidi/0", but this would require fluidsynth to use "midi/0" > > Please excuse the length, > I am still new to this whole MIDI thing. > No problem ;) -- Alexandre