Re: MIDI send problems.
Re: MIDI send problems.
- Subject: Re: MIDI send problems.
- From: Doug Wyatt <email@hidden>
- Date: Tue, 7 Aug 2001 07:29:46 -0700
Below is a small command-line tool that creates a virtual destination
and then calls MIDISend to send to it. I can't reproduce any problems
with it ... can you? If not, then it's something for the author of the
driver to investigate.
Doug
#define DEBUG 1
#include <CoreMIDI/MIDIServices.h>
#include <CoreAudio/HostTime.h>
void ClientProc(const MIDINotification *message, void *refCon)
{
}
#define NSMS(x) (long)((x / 1000000ULL) & 0x7FFFFFF) // nanos to 32 bits
of millis
void MIDIPacketListDump(const MIDIPacketList *pktlist)
{
const MIDIPacket *pkt = pktlist->packet;
UInt64 nowHW = AudioGetCurrentHostTime();
UInt64 nowNS = AudioConvertHostTimeToNanos(nowHW);
for (unsigned int i = 0; i < pktlist->numPackets; ++i) {
printf("ld ld: ", NSMS(nowNS),
NSMS(AudioConvertHostTimeToNanos(pkt->timeStamp)));
for (unsigned int j = 0; j < pkt->length; ++j)
printf("X ", pkt->data[j]);
printf("\n");
pkt = MIDIPacketNext(pkt);
}
}
void VirtualReadProc(const MIDIPacketList *pktlist, void
*readProcRefCon, void *srcConnRefCon)
{
MIDIPacketListDump(pktlist);
}
int main(int argc, char *argv[])
{
MIDIClientRef clientRef;
MIDIPortRef outPort;
MIDIEndpointRef destination;
check_noerr(MIDIClientCreate(CFSTR("test"), ClientProc, NULL,
&clientRef));
check_noerr(MIDIOutputPortCreate(clientRef, CFSTR("outport"),
&outPort));
check_noerr(MIDIDestinationCreate(clientRef, CFSTR("virtual dest"),
VirtualReadProc, NULL, &destination));
Byte buffer[512];
MIDIPacketList *packetList = (MIDIPacketList *)buffer;
Byte sysExEvent[] = { 0xF0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12,
0xF7 };
MIDITimeStamp timeStamp = 0;
MIDIPacket *packet = MIDIPacketListInit(packetList);
check(packet != NULL);
packet = MIDIPacketListAdd(packetList, 512, packet, 0,
sizeof(sysExEvent), sysExEvent);
check_noerr(MIDISend(outPort, destination, packetList));
CFRunLoopRun();
return 0;
}
On Thursday, August 2, 2001, at 03:37 PM, Jason Bagley wrote:
Hi,
I've been having trouble sending anything but 3 byte messages through
MIDISend, and I can't seem to get anything to send through MIDISendSysex
at all. Both calls return noErr, and when using MIDISendSysex my
SysexComplete routine is called with bytesToSend == 0 and complete ==
TRUE.
Trying to send messages larger than 3 bytes through MIDISend often
freezes
my system! Cursor is active, but I can't do anything else. Unplugging
the
interface from the USB chain does not end the freeze.
I've isolated some of the MIDI code in a small test app. There I can
send
larger messages via MIDISend, but I have to send a 3 byte message first.
Otherwise, on subsequent invocations of the test app, no large data will
be sent.
I'm using OS X 10.0.4, and MIDISPORT 2x2 with the driver available from
MIDIMAN. I know others have said they have no trouble with this driver.
Thanks in advance for any help.
Here is a snippet of the test app:
const Byte kMIEXGGetKeyboardMode[] = { 0xf0, 0x43, 0x76, 0x65, 0x30,
0x7f, 0x00, 0x00, 0x02, 0xf7 };
Byte noteOn[] = { 0x90, 60, 4 };
Byte noteOff[] = { 0x80, 0, 0 };
...
const Byte *sysExEvent = kMIEXGGetKeyboardMode;
int sysExLength = CalcSysExLength(sysExEvent);
...
#if 0
// Send via MIDISendSysex
sysExRequest = malloc(sizeof(MIDISysexSendRequest) + sysExLength);
memcpy((unsigned char*)sysExRequest + sizeof(MIDISysexSendRequest),
sysExEvent, sysExLength);
sysExRequest->destination = destination;
sysExRequest->data = (unsigned char*)sysExRequest +
sizeof(MIDISysexSendRequest);
sysExRequest->bytesToSend = sysExLength;
sysExRequest->complete = false;
sysExRequest->completionProc = SysExCompletionProc;
sysExRequest->completionRefCon = (void *)sysExRequest;
result = MIDISendSysex(sysExRequest);
fprintf(stderr, "SendSysEx returned %ld.\n", result);
#else
// Send via MIDISend
packet = MIDIPacketListInit(packetList);
assert(NULL != packet);
// Workaround. Send a 3 byte message to "prime" driver?
packet = MIDIPacketListAdd(packetList, 512, packet, timeStamp, 3,
noteOff);
result = MIDISend(outputPort, destination, packetList);
fprintf(stderr, "MIDISend returned %ld.\n", result);
packet = MIDIPacketListInit(packetList);
packet = MIDIPacketListAdd(packetList, 512, packet, timeStamp +
100000,
sysExLength, sysExEvent);
result = MIDISend(outputPort, destination, packetList);
fprintf(stderr, "MIDISend returned %ld.\n", result);
#endif
fprintf(stderr, "Entering run loop.\n");
CFRunLoopRun();
Jason Bagley
Software Engineer
www.artlogic.com
_______________________________________________
coreaudio-api mailing list
email@hidden
http://www.lists.apple.com/mailman/listinfo/coreaudio-api
--
Doug Wyatt
work: email@hidden (CoreAudio)
personal: email@hidden
http://www.sonosphere.com
"He was the sort of person who stood on mountaintops during
thunderstorms in
wet copper armour shouting 'All the Gods are bastards.'"
-- Terry Pratchett