MidiMon 1.00, a USB MIDI app
Peter Everett (9846) 59 posts |
I don’t think so. My experience of USB device microcontrollers is that this is handled by the hardware. If there are no bytes in the IN endpoint to send, a NAK is returned to the host in response to the IN Token request. When data is finally available it will just stay in the endpoint until the next IN Token is received. What does the usb_wakeuprx actual do ? I would have thought it needs to trigger sending IN Tokens at regular intervals until a packet is received. If not then it is up to us to send usb_wakeuprx calls at regular intervals until we get data. I think this will happen automatically for Interrupt endpoints governed by the bInterval field in the endpoint descriptor but this field is ignored for Bulk endpoints, so the USB spec says. |
Peter Everett (9846) 59 posts |
I got the first part a bit wrong, the micro will respond with NAKS until told to send data in the endpoint by the device software. So it is possible to send zero length packets. It’s just that I’ve never done that. |
Colin (478) 2433 posts |
Yes that is the normal way but as I said I have seen a device where this was configurable and I think defaulted to not waiting for data.
It’s equivalent to The process starts on line 3029 in this file, where it sets str→delayed_read and str→nextcount and calls start_read() at line 2510. In start_read() if usb is busy it returns otherwise the transfer is started. When the current usbtransfer completes start_read is called again and the transfer queued by wakeuprx is run. |
Rick Murray (539) 13850 posts |
You mean Jean-Michel? My keyboard is fine, because it never shuts up.
So there’s no harm in dropping it in there too see if it improves things. Anybody know why MIDI, dealing with a series of four byte packets, decided to use the bulk method rather than the interrupt one as would be expected by serial data? |
Peter Everett (9846) 59 posts |
I think it’s meant to carry large amounts of data as well as just notes etc. The MIDI spec defines the DownLoadable Sound format (DLS files) which can be big. |
Colin (478) 2433 posts |
Ok so I plugged in a keyboard run the midi module which showed the keyboard detected. Run simpletest in a taskwindow and nothing. Compiled a debug version of the module with the RXDEBUG flag set and a couple of lines appeared then nothing. I was getting buffer overflow on all keypresses – the keypresses were being received. Tried increasing the callback buffer size but had a few crashes and still no output through the simpletest though I wasn’t getting overflow anymore. Have a feeling the buffer wasn’t emptying. I’ll investigate further. |
Rick Murray (539) 13850 posts |
Which MIDI module? Mine or his?
Sounds like one of my options, but good to clarify. |
Colin (478) 2433 posts |
yours |
Rick Murray (539) 13850 posts |
Okay, cool. |
Jean-Michel BRUCK (3009) 362 posts |
Hi all MIDI users But…now it doesn’t work anymore:-( Colin, thanks for your help and I hope you can clarify the issue. @Rick I tested the Simpletest program with Peter’s module and I still have the right information. The default Tempo value is 120 BPM, and it is not displayed by the score editor. If you need to change it you have to do it manually. The markers allow you to have variations and what I find good is the possibility of modifying the tempo dynamically, for example slowing down over three bars. I spent a lot of time trying to get my keyboard to work, and when it works the result in Rhapsody is not good except for the pitches of the notes… I hope to find it. |
Colin (478) 2433 posts |
Did you add -DRXDEBUG to CDFLAGS in the makefile.
I too am experiencing intermittent problems. Initially I wasn’t getting ticker events and the buffer was overflowing simpletest did nothing, now the ticker event is working and I’m getting data aborts when I press a key while the ticker_handler is processing the buffer – still nothing appears in simpletest. The odd thing is the change happened with Ricks compiled module too. I’ve not seen a problem with usb receiving data. |
Colin (478) 2433 posts |
I don’t know anything about the midi standard so perhaps Rick you can explain the output below. The upcall receives 38 bytes per transfer and you process it 4 bytes at a time in the ticker handler. Looking at the data on the ‘returning packet’ lines, could the data be decoded on a variable length basis – I’m not sure if the ‘padding’ bytes in each 4 byte command are valid packets – if you see what I mean. In any case 4 doesn’t go in to 38 so something doesn’t look right.
|
Colin (478) 2433 posts |
Don’t know what happened in the printout earlier but I did a dump in the incoming packets and they were just 4 bytes followed by 34 0’s I’ll have to look for the header.tick time tommorrow. I changed the code to treat the incoming packet as a byte stream, as opposed to a word stream that ends with a 0 first byte, before I discovered this. I just need to generate a code that uses less than 4 bytes to see if that is correct. |
Rick Murray (539) 13850 posts |
MIDI sends packets that are four bites long. There’s a prefix byte (specific to USB) that provides additional data as, IIRC, USB can support multiple “cables” (because it’s the 21st century and we can do better than being limited to 16 channels per device). Page 16 of https://www.usb.org/sites/default/files/midi10.pdf explains what to expect. And yes, you’ve discovered the problem with the padding. ;)
To get the timing working, there’s a variable at the top that is set to something like CLOCKTICK_MIDIBEAT, change it to the one that means the fast clock (probably …_FASTCLOCK, but check in the header) and it’ll default to the millisecond ticker. I’ve done that in the one I posted here for JMB. But what I am sure about is MIDI being 4 bytes / 32 bits. Refer to the spec linked above for details.
Are these actually sent over MIDI? If so, they ought to be broken into chunks 64-128 bytes in length and then sent byte by byte as SysEx. Which means a ton of four byte USB packets. ;) There appears to be an option “Association Control” that can be used for high speed data transfer, but as far as I can determine from the brief description, it appears to hijack the endpoint (effectively replacing the MIDI stream). I’m not sure if it is undoable either as the docs seem to imply that the endpoint is terminated at the end (so reconnect in order to get MIDI back?). At any rate, that’s not MIDI… and to be honest, it probably should have been something like MTP working alongside streaming MIDI rather than sort of on top of it, maybe. The docs aren’t clear (how does one even know the remote device supports this?) because whatever it is, it isn’t MIDI. ;) |
Rick Murray (539) 13850 posts |
Follow-up – Yamaha keyboards can often support a program called “Musicsoft Downloader” to send data to the keyboard and read it back. It uses painful amounts of SysEx… https://sandsoftwaresound.net/hidden-arranger-smarts-file-system-sysex/ |
Lauren Etc. (8147) 52 posts |
Something I’ve noticed while I was working:
In USB MIDI 0.10, it seems to always return the manufacturer name even if the product name is available; for instance, here is the output from *MidiUSBInfo for my two devices:
Using 0.08, the second device there previously would show “USB2.0-MIDI” whereas now it’s the blank string from Manufacturer. Similarly, the MicroFreak always just shows as “Arturia”. This does make me realize though that I need to put in a fall-back to use the device number if the manufacturer is also blank. I need to get caught up on this thread but similarly, I haven’t had any luck so far with multiple devices yet; if there are any device changes, so far both devices just stop working with both the test program and !MidiMon until the module is restarted. But I haven’t looked into it much more than that yet. |
Rick Murray (539) 13850 posts |
There’s been some private discussion about this as some devices don’t bother to set up the information correctly. It’s not unique to MIDI, mind you… I would say, as that call is specifically providing product and manufacturer IDs, that if the product name is blank, we fix it up by constructing a fake name, so software using this information can get something sensible (we shouldn’t leave the product blank, that’s just kicking the can down the road – remember that this stuff is exposed via an API call to read the device info). Note: If the product name is the manufacturer ID (I’ve seen this with cheap keyboards), then we’ll do nothing, just fake up a product name if necessary. It’s not up to us to try to make sense of the info, just to make sure that there’s something useful in the product field as that’s the most likely to appear on screen. It’s not ideal, but it’s not our job to fix other people’s half-arsed implementations. |
Lauren Etc. (8147) 52 posts |
Right, although maybe I’m not understanding but in this case it’s not that the product name is blank, it’s that it’s always returning the manufacturer ID no matter what… Also, I’m poking at trying to get monitor input working with MidiSupport but I can’t seem to clear the buffers or get any kind of events for incoming MIDI… it looks like MidiSMon is using some MidiSupport specific SWIs instead of using the Acorn ones directly? Not sure. it’s late here so I’ll probably have to leave it tonight. |
Peter Everett (9846) 59 posts |
@Rick Sound font or sample files DLS,SF2 etc. are binary. To send via midi protocol (7bit data) would be tedious to say the least (I’d say stupid). There’s probably a number of methods from a number of manufacturers but in answer to your question, @Lauren MidiSMon does indeed talk directly to Midi Support and is displayed as a driver in the routing window of MidiMan. |
Colin (478) 2433 posts |
Ok so the 0 time appears to be correct in the default mode. In case I’ve broken something would anyone like to try colin1midi. Just double click on ‘runsimpletest’ the module will load and program run. |
Peter Everett (9846) 59 posts |
Right done that, seems to work fine. Simple MIDI test ================ Play something, ESC to quit. Port Bytes Data Time Annotation ---- ----- ----------- ------- -------------------------------------- 0 3 &90, 60, 98 0 Note on (channel 1) 0 3 &90, 60, 0 0 Note off (channel 1) 0 3 &90, 62, 106 0 Note on (channel 1) 0 3 &90, 62, 0 0 Note off (channel 1) 0 3 &90, 64, 109 0 Note on (channel 1) 0 3 &90, 64, 0 0 Note off (channel 1) 0 3 &90, 65, 109 0 Note on (channel 1) 0 3 &90, 65, 0 0 Note off (channel 1) 0 3 &90, 67, 106 0 Note on (channel 1) 0 3 &90, 67, 0 0 Note off (channel 1) 0 3 &90, 69, 106 0 Note on (channel 1) 0 3 &90, 69, 0 0 Note off (channel 1) 0 3 &90, 71, 103 0 Note on (channel 1) 0 3 &90, 71, 0 0 Note off (channel 1) 0 3 &90, 72, 110 0 Note on (channel 1) 0 3 &90, 72, 0 0 Note off (channel 1) Escape *midiusbinfo MIDI USB information: Timestamp type is MIDI clock MIDI Clock is 0 (Song Position = 0) Current TX channel is 0 (real channel 1 on real port 0). MIDI device (#0) is USB7, VID 0A4D, PID 129D, Manufacturer Keystation Mini 32 Product Keystation Mini 32 using IN file handle 252 Endpoint 1 Size 64, and OUT file handle 251 Endpoint 2 Size 64. number of cables 1. * |
Jean-Michel BRUCK (3009) 362 posts |
Bonjour, One positive thing is that now RxCommand returns the note, but the timestamp (FastClock value) is not added. I am continuing the tests to see which version of the module (Rick) will be the most effective with my keyboard. For information about the MidiSupport philosophy |
Lauren Etc. (8147) 52 posts |
@Peter: Nope, have been doing a clean boot between switching between MIDI modules. Still no luck on input, though. MIDI_Init doesn’t empty any of the buffers, no events ever fire, and Rx_Command doesn’t seem to fetch anything… it’s probably something on my end I’m sure but dunno what yet. Output works fine though! |
Jean-Michel BRUCK (3009) 362 posts |
@Peter
It is therefore normal that SimpleTest does not return any Timestamp. For SysEx, I think ESP had already done the job (lost, gr!!!) I tested their SysExy program with the ESP version of MIDISupport and it works with MIDI files that have SysEx data, the KeyStation keyboard does not generate any to my knowledge. On the other hand, Rick’s keyboard generates a lot… @Rick Bonne vacances. |
Jean-Michel BRUCK (3009) 362 posts |
@Lauren With the Keystation keyboard, I had to do a full reset of the keyboard itself:
|