ResidualVM logo ResidualVM website - Forums - Contact us BuildBot - Doxygen - Wiki curved edge

dmedia.cpp

Go to the documentation of this file.
00001 /* ScummVM - Graphic Adventure Engine
00002  *
00003  * ScummVM is the legal property of its developers, whose names
00004  * are too numerous to list here. Please refer to the COPYRIGHT
00005  * file distributed with this source distribution.
00006  *
00007  * This program is free software; you can redistribute it and/or
00008  * modify it under the terms of the GNU General Public License
00009  * as published by the Free Software Foundation; either version 2
00010  * of the License, or (at your option) any later version.
00011  *
00012  * This program is distributed in the hope that it will be useful,
00013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015  * GNU General Public License for more details.
00016  *
00017  * You should have received a copy of the GNU General Public License
00018  * along with this program; if not, write to the Free Software
00019  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00020  *
00021  */
00022 
00023 /*
00024  * IRIX dmedia support by Rainer Canavan <scumm@canavan.de>
00025  *    some code liberated from seq.cpp and coremidi.cpp
00026  */
00027 
00028 // Disable symbol overrides so that we can use system headers.
00029 #define FORBIDDEN_SYMBOL_ALLOW_ALL
00030 
00031 #include "common/scummsys.h"
00032 
00033 #if defined(IRIX)
00034 
00035 #include "common/config-manager.h"
00036 #include "common/error.h"
00037 #include "common/textconsole.h"
00038 #include "common/util.h"
00039 #include "audio/musicplugin.h"
00040 #include "audio/mpu401.h"
00041 
00042 #include <dmedia/midi.h>
00043 #include <sys/types.h>
00044 #include <bstring.h>
00045 #include <unistd.h>
00046 
00048 //
00049 // IRIX dmedia midi driver
00050 //
00052 
00053 #define SEQ_MIDIPUTC 5
00054 
00055 class MidiDriver_DMEDIA : public MidiDriver_MPU401 {
00056 public:
00057     MidiDriver_DMEDIA();
00058     int open();
00059     bool isOpen() const { return _isOpen; }
00060     void close();
00061     void send(uint32 b);
00062     void sysEx(const byte *msg, uint16 length);
00063 
00064 private:
00065     bool _isOpen;
00066     int _deviceNum;
00067     char *_midiportName;
00068     MDport _midiPort;
00069     int _fd;
00070 };
00071 
00072 MidiDriver_DMEDIA::MidiDriver_DMEDIA() {
00073     _isOpen = false;
00074     _deviceNum = 0;
00075     _midiportName = NULL;
00076 }
00077 
00078 int MidiDriver_DMEDIA::open() {
00079     int numinterfaces;
00080     int i;
00081     const char *var;
00082     char *portName;
00083 
00084     if (_isOpen)
00085         return MERR_ALREADY_OPEN;
00086     _isOpen = true;
00087 
00088     numinterfaces = mdInit();
00089     if (numinterfaces <= 0) {
00090         fprintf(stderr, "No MIDI interfaces configured.\n");
00091         perror("Cannot initialize libmd for sound output");
00092         return -1;
00093     }
00094 
00095     if (getenv("RESIDUALVM_MIDIPORT")) {
00096         _deviceNum = atoi(getenv("RESIDUALVM_MIDIPORT"));
00097         _midiportName = mdGetName(_deviceNum);
00098     } else {
00099         var = ConfMan.get("dmedia_port").c_str();
00100         if (strlen(var) > 0) {
00101             for (i = 0; i < numinterfaces; i++) {
00102                 portName = mdGetName(i);
00103                 if (strcmp(var, portName) == 0) {
00104                     _deviceNum = i;
00105                     _midiportName = portName;
00106                 }
00107             }
00108 
00109         }
00110     }
00111 
00112     _midiPort = mdOpenOutPort(_midiportName);
00113     if (!_midiPort) {
00114         warning("Failed to open MIDI interface %s", _midiportName);
00115         return -1;
00116     }
00117 
00118     _fd = mdGetFd(_midiPort);
00119     if (!_fd) {
00120         warning("Failed to aquire filehandle for MIDI port %s", _midiportName);
00121         mdClosePort(_midiPort);
00122         return -1;
00123     }
00124 
00125     mdSetStampMode(_midiPort, MD_NOSTAMP);  /* don't use Timestamps */
00126 
00127     return 0;
00128 }
00129 
00130 void MidiDriver_DMEDIA::close() {
00131     mdClosePort(_midiPort);
00132     _isOpen = false;
00133     _deviceNum = 0;
00134     _midiportName = NULL;
00135 }
00136 
00137 void MidiDriver_DMEDIA::send(uint32 b) {
00138     MDevent event;
00139     byte status_byte = (b & 0x000000FF);
00140     byte first_byte = (b & 0x0000FF00) >> 8;
00141     byte second_byte = (b & 0x00FF0000) >> 16;
00142 
00143 
00144     event.sysexmsg = NULL;
00145     event.msg[0] = status_byte;
00146     event.msg[1] = first_byte;
00147     event.msg[2] = second_byte;
00148 
00149     switch (status_byte & 0xF0) {
00150     case 0x80:      // Note Off
00151     case 0x90:      // Note On
00152     case 0xA0:      // Polyphonic Aftertouch
00153     case 0xB0:      // Controller Change
00154     case 0xE0:      // Pitch Bending
00155         event.msglen = 3;
00156         break;
00157     case 0xC0:      // Programm Change
00158     case 0xD0:      // Monophonic Aftertouch
00159         event.msglen = 2;
00160         break;
00161     default:
00162         warning("DMediaMIDI driver encountered unsupported status byte: 0x%02x", status_byte);
00163         event.msglen = 3;
00164         break;
00165     }
00166     if (mdSend(_midiPort, &event, 1) != 1) {
00167         warning("failed sending MIDI event (dump follows...)");
00168         warning("MIDI Event (len=%u):", event.msglen);
00169         for (int i = 0; i < event.msglen; i++)
00170             warning("%02x ", (int)event.msg[i]);
00171     }
00172 }
00173 
00174 void MidiDriver_DMEDIA::sysEx (const byte *msg, uint16 length) {
00175     MDevent event;
00176     char buf [1024];
00177 
00178     assert(length + 2 <= 256);
00179 
00180     memcpy(buf, msg, length);
00181     buf[length] = MD_EOX;
00182     event.sysexmsg = buf;
00183     event.msglen = length;
00184     event.msg[0] = MD_SYSEX;
00185     event.msg[1] = 0;
00186     event.msg[2] = 0;
00187 
00188     if (mdSend(_midiPort, &event, 1) != 1) {
00189         fprintf(stderr, "failed sending MIDI SYSEX event (dump follows...)\n");
00190         for (int i = 0; i < event.msglen; i++)
00191             warning("%02x ", (int)event.msg[i]);
00192     }
00193 }
00194 
00195 
00196 // Plugin interface
00197 
00198 class DMediaMusicPlugin : public MusicPluginObject {
00199 public:
00200     const char *getName() const {
00201         return "DMedia";
00202     }
00203 
00204     const char *getId() const {
00205         return "dmedia";
00206     }
00207 
00208     MusicDevices getDevices() const;
00209     Common::Error createInstance(MidiDriver **mididriver, MidiDriver::DeviceHandle = 0) const;
00210 };
00211 
00212 MusicDevices DMediaMusicPlugin::getDevices() const {
00213     int numinterfaces;
00214     int i;
00215     char *portName;
00216     MusicDevices devices;
00217 
00218     // TODO: Return a different music type depending on the configuration
00219 
00220     numinterfaces = mdInit();
00221     if (numinterfaces <= 0) {
00222         fprintf(stderr, "No MIDI interfaces configured.\n");
00223     }
00224 
00225     for (i=0; i<numinterfaces; i++) {
00226         portName = mdGetName(0);
00227         fprintf(stderr, "device %i %s\n", i, portName);
00228         devices.push_back(MusicDevice(this, portName, MT_GM));
00229     }
00230 
00231     return devices;
00232 }
00233 
00234 Common::Error DMediaMusicPlugin::createInstance(MidiDriver **mididriver, MidiDriver::DeviceHandle) const {
00235     *mididriver = new MidiDriver_DMEDIA();
00236 
00237     return Common::kNoError;
00238 }
00239 
00240 //#if PLUGIN_ENABLED_DYNAMIC(DMEDIA)
00241     //REGISTER_PLUGIN_DYNAMIC(DMEDIA, PLUGIN_TYPE_MUSIC, DMediaMusicPlugin);
00242 //#else
00243     REGISTER_PLUGIN_STATIC(DMEDIA, PLUGIN_TYPE_MUSIC, DMediaMusicPlugin);
00244 //#endif
00245 
00246 #endif


Generated on Sat Feb 16 2019 05:00:49 for ResidualVM by doxygen 1.7.1
curved edge   curved edge