/** * @brief Respond to a given AppleMIDI command. * Use the command as response and - if neccessary - send it back to the peer. * @private @memberof MIDIDriverAppleMIDI * @param driver The driver. * @param fd The file descriptor to be used for communication. * @param command The command. * @retval 0 On success. * @retval >0 If the packet could not be sent. */ static int _applemidi_respond(struct MIDIDriverAppleMIDI *driver, struct sock *sk, struct AppleMIDICommand *command) { struct RTPPeer *peer = NULL; switch (command->type) { case APPLEMIDI_COMMAND_INVITATION: if (sk == driver->control_socket->sk) { // event = MIDIEventCreate( // MIDI_APPLEMIDI_PEER_DID_SEND_INVITATION, NULL, "%s", // &(command->data.session.name[0]) ); // MIDIDriverTriggerEvent( &(driver->base), event ); // MIDIEventRelease( event ); } if (driver->accept) { command->type = APPLEMIDI_COMMAND_INVITATION_ACCEPTED; if (sk == driver->rtp_socket->sk) { peer = RTPPeerCreate( command->data.session.ssrc, command->size, (struct sockaddr_in *)&(command->addr)); RTPSessionAddPeer(driver->rtp_session, peer); RTPPeerRelease(peer); } } else { command->type = APPLEMIDI_COMMAND_INVITATION_REJECTED; } RTPSessionGetSSRC(driver->rtp_session, &(command->data.session.ssrc)); pr_debug("processed invitation should now answer\n"); return _applemidi_send_command(driver, sk, command); case APPLEMIDI_COMMAND_INVITATION_ACCEPTED: // TODO for receive break; case APPLEMIDI_COMMAND_INVITATION_REJECTED: // TODO for receive break; case APPLEMIDI_COMMAND_ENDSESSION: RTPSessionFindPeerBySSRC(driver->rtp_session, &peer, command->data.session.ssrc); // event = MIDIEventCreate( MIDI_APPLEMIDI_PEER_DID_END_SESSION, // NULL, "%s", &(command->data.session.name[0]) ); // MIDIDriverTriggerEvent( &(driver->base), event ); // MIDIEventRelease( event ); if (peer != NULL) { RTPSessionRemovePeer(driver->rtp_session, peer); } break; case APPLEMIDI_COMMAND_SYNCHRONIZATION: return _applemidi_sync(driver, sk, command); case APPLEMIDI_COMMAND_RECEIVER_FEEDBACK: // RTPSessionFindPeerBySSRC( driver->rtp_session, &peer, // command->data.feedback.ssrc ); // RTPMIDISessionJournalTrunkate( driver->rtpmidi_session, peer, // command->data.feedback.seqnum ); break; default: return 1; } return 0; }
/** * @brief Respond to a given AppleMIDI command. * Use the command as response and - if neccessary - send it back to the peer. * @private @memberof MIDIDriverAppleMIDI * @param driver The driver. * @param fd The file descriptor to be used for communication. * @param command The command. * @retval 0 On success. * @retval >0 If the packet could not be sent. */ static int _applemidi_respond( struct MIDIDriverAppleMIDI * driver, int fd, struct AppleMIDICommand * command ) { struct RTPPeer * peer = NULL; struct MIDIEvent * event = NULL; switch( command->type ) { case APPLEMIDI_COMMAND_INVITATION: if( fd == driver->control_socket ) { event = MIDIEventCreate( MIDI_APPLEMIDI_PEER_DID_SEND_INVITATION, NULL, "%s", &(command->data.session.name[0]) ); MIDIDriverTriggerEvent( &(driver->base), event ); MIDIEventRelease( event ); } if( driver->accept ) { command->type = APPLEMIDI_COMMAND_INVITATION_ACCEPTED; if( fd == driver->rtp_socket ) { peer = RTPPeerCreate( command->data.session.ssrc, command->size, (struct sockaddr *) &(command->addr) ); RTPSessionAddPeer( driver->rtp_session, peer ); RTPPeerRelease( peer ); } } else { command->type = APPLEMIDI_COMMAND_INVITATION_REJECTED; } RTPSessionGetSSRC( driver->rtp_session, &(command->data.session.ssrc) ); return _applemidi_send_command( driver, fd, command ); case APPLEMIDI_COMMAND_INVITATION_ACCEPTED: if( command->data.session.token == driver->token ) { if( fd == driver->control_socket ) { _applemidi_rtp_addr( command->size, (struct sockaddr *) &command->addr, (struct sockaddr *) &command->addr ); return _applemidi_invite( driver, driver->rtp_socket, command->size, (struct sockaddr *) &(command->addr) ); } else { peer = RTPPeerCreate( command->data.session.ssrc, command->size, (struct sockaddr *) &(command->addr) ); RTPSessionAddPeer( driver->rtp_session, peer ); event = MIDIEventCreate( MIDI_APPLEMIDI_PEER_DID_ACCEPT_INVITATION, NULL, "%s", &(command->data.session.name[0]) ); MIDIDriverTriggerEvent( &(driver->base), event ); MIDIEventRelease( event ); RTPPeerRelease( peer ); return _applemidi_start_sync( driver, driver->rtp_socket, command->size, (struct sockaddr *) &(command->addr) ); } } break; case APPLEMIDI_COMMAND_INVITATION_REJECTED: event = MIDIEventCreate( MIDI_APPLEMIDI_PEER_DID_REJECT_INVITATION, NULL, "%s", &(command->data.session.name[0]) ); MIDIDriverTriggerEvent( &(driver->base), event ); MIDIEventRelease( event ); break; case APPLEMIDI_COMMAND_ENDSESSION: RTPSessionFindPeerBySSRC( driver->rtp_session, &peer, command->data.session.ssrc ); event = MIDIEventCreate( MIDI_APPLEMIDI_PEER_DID_END_SESSION, NULL, "%s", &(command->data.session.name[0]) ); MIDIDriverTriggerEvent( &(driver->base), event ); MIDIEventRelease( event ); if( peer != NULL ) { RTPSessionRemovePeer( driver->rtp_session, peer ); } break; case APPLEMIDI_COMMAND_SYNCHRONIZATION: return _applemidi_sync( driver, fd, command ); case APPLEMIDI_COMMAND_RECEIVER_FEEDBACK: RTPSessionFindPeerBySSRC( driver->rtp_session, &peer, command->data.feedback.ssrc ); RTPMIDISessionJournalTrunkate( driver->rtpmidi_session, peer, command->data.feedback.seqnum ); break; default: return 1; } return 0; }