/[svn]/liblscp/trunk/examples/example_server.c
ViewVC logotype

Annotation of /liblscp/trunk/examples/example_server.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 963 - (hide annotations) (download)
Sun Dec 3 18:30:04 2006 UTC (17 years, 4 months ago) by capela
File MIME type: text/plain
File size: 24490 byte(s)
* MIDI instrument mapping fixed, previously missing
  the regular ON_DEMAND load mode.

* Server error reporting is now effective; all server
  numerical error and warning codes are added to 100,
  thus giving a proper non-zero lscp_client_get_errno()
  return value.

1 capela 105 // example_server.c
2     //
3     /****************************************************************************
4 capela 921 liblscp - LinuxSampler Control Protocol API
5 capela 869 Copyright (C) 2004-2006, rncbc aka Rui Nuno Capela. All rights reserved.
6 capela 105
7     This program is free software; you can redistribute it and/or
8     modify it under the terms of the GNU General Public License
9     as published by the Free Software Foundation; either version 2
10     of the License, or (at your option) any later version.
11    
12     This program is distributed in the hope that it will be useful,
13     but WITHOUT ANY WARRANTY; without even the implied warranty of
14     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15     GNU General Public License for more details.
16    
17 capela 921 You should have received a copy of the GNU General Public License along
18     with this program; if not, write to the Free Software Foundation, Inc.,
19     51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20 capela 105
21     *****************************************************************************/
22    
23     #include "server.h"
24     #include "parser.h"
25    
26     #include <time.h>
27    
28     #define SERVER_PORT 8888
29    
30     #if defined(WIN32)
31     static WSADATA _wsaData;
32     #endif
33    
34     ////////////////////////////////////////////////////////////////////////
35    
36     lscp_status_t server_callback ( lscp_connect_t *pConnect, const char *pchBuffer, int cchBuffer, void *pvData )
37     {
38 capela 963 lscp_status_t ret = LSCP_OK;
39     lscp_parser_t tok;
40     const char *pszResult = NULL;
41     char szTemp[4096];
42     int i;
43     static int iSamplerChannel = 0;
44     static int iAudioDevice = 0;
45     static int iMidiDevice = 0;
46     static int iMidiInstruments = 0;
47 capela 105
48 capela 963 if (pchBuffer == NULL) {
49     fprintf(stderr, "server_callback: addr=%s port=%d: ",
50     inet_ntoa(pConnect->client.addr.sin_addr),
51     htons(pConnect->client.addr.sin_port));
52     switch (cchBuffer) {
53     case LSCP_CONNECT_OPEN:
54     fprintf(stderr, "New client connection.\n");
55     break;
56     case LSCP_CONNECT_CLOSE:
57     fprintf(stderr, "Connection closed.\n");
58     break;
59     }
60     return ret;
61     }
62 capela 105
63 capela 963 lscp_socket_trace("server_callback", &(pConnect->client.addr), pchBuffer, cchBuffer);
64 capela 105
65 capela 963 lscp_parser_init(&tok, pchBuffer, cchBuffer);
66 capela 105
67 capela 963 if (lscp_parser_test(&tok, "GET")) {
68     if (lscp_parser_test(&tok, "CHANNEL")) {
69     if (lscp_parser_test(&tok, "INFO")) {
70     // Getting sampler channel informations:
71     // GET CHANNEL INFO <sampler-channel>
72     pszResult = "ENGINE_NAME: DummyEngine\r\n"
73     "INSTRUMENT_FILE: DummyInstrument.gig\r\n"
74     "INSTRUMENT_NR: 0\r\n"
75     "INSTRUMENT_NAME: Dummy Instrument\r\n"
76     "INSTRUMENT_STATUS: 100\r\n"
77     "AUDIO_OUTPUT_DEVICE: 0\r\n"
78     "AUDIO_OUTPUT_CHANNELS: 2\r\n"
79     "AUDIO_OUTPUT_ROUTING: 0,1\r\n"
80     "MIDI_INPUT_DEVICE: 0\r\n"
81     "MIDI_INPUT_PORT: 0\r\n"
82     "MIDI_INPUT_CHANNEL: ALL\r\n"
83     "VOLUME: 0.5\r\n"
84     "MUTE: FALSE\r\n"
85     "SOLO: TRUE\r\n"
86 capela 948 ".\r\n";
87 capela 963 }
88     else if (lscp_parser_test(&tok, "VOICE_COUNT")) {
89     // Current number of active voices:
90     // GET CHANNEL VOICE_COUNT <sampler-channel>
91     sprintf(szTemp, "%d\r\n", rand() % 100);
92     pszResult = szTemp;
93     }
94     else if (lscp_parser_test(&tok, "STREAM_COUNT")) {
95     // Current number of active disk streams:
96     // GET CHANNEL STREAM_COUNT <sampler-channel>
97     pszResult = "3\r\n";
98     }
99     else if (lscp_parser_test(&tok, "BUFFER_FILL")) {
100     if (lscp_parser_test(&tok, "BYTES")) {
101     // Current fill state of disk stream buffers:
102     // GET CHANNEL BUFFER_FILL BYTES <sampler-channel>
103     sprintf(szTemp, "[1]%d,[2]%d,[3]%d\r\n", rand(), rand(), rand());
104     pszResult = szTemp;
105     }
106     else if (lscp_parser_test(&tok, "PERCENTAGE")) {
107     // Current fill state of disk stream buffers:
108     // GET CHANNEL BUFFER_FILL PERCENTAGE <sampler-channel>
109     sprintf(szTemp, "[1]%d%%,[2]%d%%,[3]%d%%\r\n", rand() % 100, rand() % 100, rand() % 100);
110     pszResult = szTemp;
111     }
112     else ret = LSCP_FAILED;
113     }
114     else ret = LSCP_FAILED;
115     }
116     else if (lscp_parser_test(&tok, "CHANNELS")) {
117     // Current number of sampler channels:
118     // GET CHANNELS
119     sprintf(szTemp, "%d\r\n", iSamplerChannel);
120     pszResult = szTemp;
121     }
122     else if (lscp_parser_test(&tok, "AVAILABLE_AUDIO_OUTPUT_DRIVERS")) {
123     // Getting all available audio output driver count.
124     // GET AVAILABLE_AUDIO_OUTPUT_DRIVERS
125     pszResult = "2\r\n";
126     }
127     else if (lscp_parser_test(&tok, "AVAILABLE_MIDI_INPUT_DRIVERS")) {
128     // Getting all available MIDI input driver count.
129     // GET AVAILABLE_MIDI_INPUT_DRIVERS
130     pszResult = "1\r\n";
131     }
132     else if (lscp_parser_test2(&tok, "AUDIO_OUTPUT_DRIVER", "INFO")) {
133     // Getting informations about a specific audio output driver.
134     // GET AUDIO_OUTPUT_DRIVER INFO <audio-output-type>
135     if (lscp_parser_test(&tok, "Alsa")) {
136     pszResult = "DESCRIPTION: 'ALSA PCM'\r\n"
137     "VERSION: '1.0'\r\n"
138     "PARAMETERS: channels,samplerate,active\r\n"
139     ".\r\n";
140     }
141     else if (lscp_parser_test(&tok, "Jack")) {
142     pszResult = "DESCRIPTION: JACK Audio Connection Kit\r\n"
143     "VERSION: 0.98.1\r\n"
144     "PARAMETERS: channels,samplerate,active\r\n"
145     ".\r\n";
146     }
147     else ret = LSCP_FAILED;
148     }
149     else if (lscp_parser_test2(&tok, "MIDI_INPUT_DRIVER", "INFO")) {
150     // Getting informations about a specific MIDI input driver.
151     // GET MIDI_INPUT_DRIVER INFO <midi-input-type>
152     if (lscp_parser_test(&tok, "Alsa")) {
153     pszResult = "DESCRIPTION: ALSA Sequencer\r\n"
154     "VERSION: 1.0\r\n"
155     "PARAMETERS: ports,active\r\n"
156     ".\r\n";
157     }
158     else ret = LSCP_FAILED;
159     }
160     else if (lscp_parser_test2(&tok, "AUDIO_OUTPUT_DRIVER_PARAMETER", "INFO")) {
161     // Getting informations about a specific audio output driver parameter.
162     // GET AUDIO_OUTPUT_DRIVER_PARAMETER INFO <audio-output-type> <param>
163     if (lscp_parser_test(&tok, "Alsa")) {
164     if (lscp_parser_test(&tok, "active")) {
165     pszResult = "DESCRIPTION: 'ALSA PCM active state'\r\n"
166     "TYPE: BOOL\r\n"
167     "MANDATORY: TRUE\r\n"
168     "FIX: TRUE\r\n"
169     "MULTIPLICITY: FALSE\r\n"
170     "DEPENDS: channels,samplerate,card\r\n"
171     "DEFAULT: TRUE\r\n"
172     "RANGE_MIN: FALSE\r\n"
173     "RANGE_MAX: TRUE\r\n"
174     "POSSIBILITIES: FALSE,TRUE\r\n"
175     ".\r\n";
176     }
177     else if (lscp_parser_test(&tok, "channels")) {
178     pszResult = "DESCRIPTION: 'Number of ALSA PCM channels'\r\n"
179     "TYPE: INT\r\n"
180     "MANDATORY: TRUE\r\n"
181     "FIX: TRUE\r\n"
182     "MULTIPLICITY: FALSE\r\n"
183     "DEFAULT: 2\r\n"
184     ".\r\n";
185     }
186     else if (lscp_parser_test(&tok, "samplerate")) {
187     pszResult = "DESCRIPTION: 'ALSA PCM sample rate'\r\n"
188     "TYPE: INT\r\n"
189     "MANDATORY: TRUE\r\n"
190     "FIX: TRUE\r\n"
191     "MULTIPLICITY: TRUE\r\n"
192     "DEFAULT: 44100\r\n"
193     "POSSIBILITIES: 44100,48000,96000\r\n"
194     ".\r\n";
195     }
196     else ret = LSCP_FAILED;
197     }
198     else if (lscp_parser_test(&tok, "Jack")) {
199     if (lscp_parser_test(&tok, "active")) {
200     pszResult = "DESCRIPTION: 'JACK active state'\r\n"
201     "TYPE: BOOL\r\n"
202     "MANDATORY: TRUE\r\n"
203     "FIX: TRUE\r\n"
204     "MULTIPLICITY: FALSE\r\n"
205     "DEPENDS: channels,samplerate\r\n"
206     "DEFAULT: TRUE\r\n"
207     "RANGE_MIN: FALSE\r\n"
208     "RANGE_MAX: TRUE\r\n"
209     "POSSIBILITIES: FALSE,TRUE\r\n"
210     ".\r\n";
211     }
212     else if (lscp_parser_test(&tok, "channels")) {
213     pszResult = "DESCRIPTION: 'Number of JACK audio channels'\r\n"
214     "TYPE: INT\r\n"
215     "MANDATORY: TRUE\r\n"
216     "FIX: TRUE\r\n"
217     "MULTIPLICITY: FALSE\r\n"
218     "DEFAULT: 2\r\n"
219     ".\r\n";
220     }
221     else if (lscp_parser_test(&tok, "samplerate")) {
222     pszResult = "DESCRIPTION: 'JACK sample rate'\r\n"
223     "TYPE: INT\r\n"
224     "MANDATORY: TRUE\r\n"
225     "FIX: TRUE\r\n"
226     "MULTIPLICITY: TRUE\r\n"
227     "DEFAULT: 44100\r\n"
228     "POSSIBILITIES: 44100,48000,96000\r\n"
229     ".\r\n";
230     }
231     else ret = LSCP_FAILED;
232     }
233     else ret = LSCP_FAILED;
234     }
235     else if (lscp_parser_test2(&tok, "MIDI_INPUT_DRIVER_PARAMETER", "INFO")) {
236     // Getting informations about a specific MIDI input driver parameter.
237     // GET MIDI_INPUT_DRIVER_PARAMETER INFO <midi-input-type> <param>
238     if (lscp_parser_test(&tok, "Alsa")) {
239     if (lscp_parser_test(&tok, "active")) {
240     pszResult = "DESCRIPTION: 'ALSA Sequencer device active state'\r\n"
241     "TYPE: BOOL\r\n"
242     "MANDATORY: TRUE\r\n"
243     "FIX: TRUE\r\n"
244     "MULTIPLICITY: FALSE\r\n"
245     "DEPENDS: channels,ports\r\n"
246     "DEFAULT: TRUE\r\n"
247     "RANGE_MIN: FALSE\r\n"
248     "RANGE_MAX: TRUE\r\n"
249     "POSSIBILITIES: FALSE,TRUE\r\n"
250     ".\r\n";
251     }
252     else if (lscp_parser_test(&tok, "ports")) {
253     pszResult = "DESCRIPTION: 'Number of ALSA Sequencer ports'\r\n"
254     "TYPE: INT\r\n"
255     "MANDATORY: FALSE\r\n"
256     "FIX: FALSE\r\n"
257     "MULTIPLICITY: FALSE\r\n"
258     "DEFAULT: 1\r\n"
259     "RANGE_MIN: 1\r\n"
260     "RANGE_MAX: 4\r\n"
261     ".\r\n";
262     }
263     else ret = LSCP_FAILED;
264     }
265     else ret = LSCP_FAILED;
266     }
267     else if (lscp_parser_test2(&tok, "AUDIO_OUTPUT_DEVICE", "INFO")) {
268     // Getting informations about a specific audio output device.
269     // GET AUDIO_OUTPUT_DEVICE INFO <audio-device-id>
270     if (lscp_parser_nextint(&tok) < iAudioDevice) {
271     pszResult = "driver: Alsa\r\n"
272     "active: TRUE\r\n"
273     "channels: 2\r\n"
274     "samplerate: 44100\r\n"
275     ".\r\n";
276     }
277     else ret = LSCP_FAILED;
278     }
279     else if (lscp_parser_test2(&tok, "MIDI_INPUT_DEVICE", "INFO")) {
280     // Getting informations about a specific MIDI input device.
281     // GET MIDI_INPUT_DEVICE INFO <midi-device-id>
282     if (lscp_parser_nextint(&tok) < iMidiDevice) {
283     pszResult = "driver: Alsa\r\n"
284     "active: TRUE\r\n"
285     "channels: 16\r\n"
286     "ports: 1\r\n"
287     ".\r\n";
288     }
289     else ret = LSCP_FAILED;
290     }
291     else if (lscp_parser_test2(&tok, "AUDIO_OUTPUT_CHANNEL", "INFO")) {
292     // Getting informations about an audio channel.
293     // GET AUDIO_OUTPUT_CHANNEL INFO <audio-device-id> <audio-channel>
294     if (lscp_parser_nextint(&tok) < iAudioDevice) {
295     pszResult = "name: DummyMonitor\r\n"
296     "is_mix_channel: FALSE\r\n"
297     "mix_channel_destination: 0\r\n"
298     ".\r\n";
299     }
300     else ret = LSCP_FAILED;
301     }
302     else if (lscp_parser_test2(&tok, "MIDI_INPUT_PORT", "INFO")) {
303     // Getting informations about a MIDI port.
304     // GET MIDI_INPUT_PORT INFO <midi-device-id> <midi-port>
305     if (lscp_parser_nextint(&tok) < iMidiDevice) {
306     pszResult = "name: DummyKeyboard\r\n"
307     "alsa_seq_bindings: '64:0'\r\n"
308     ".\r\n";
309     }
310     else ret = LSCP_FAILED;
311     }
312     else if (lscp_parser_test2(&tok, "AUDIO_OUTPUT_CHANNEL_PARAMETER", "INFO")) {
313     // Getting informations about specific audio channel parameter.
314     // GET AUDIO_OUTPUT_CHANNEL_PARAMETER INFO <audio-device-id> <audio-channel> <param>
315     if (lscp_parser_nextint(&tok) < iAudioDevice) {
316     lscp_parser_nextint(&tok);
317     if (lscp_parser_test(&tok, "is_mix_channel")) {
318     pszResult = "DESCRIPTION: 'Whether this is an audio mix channel'\r\n"
319     "TYPE: BOOL\r\n"
320     "MANDATORY: TRUE\r\n"
321     "FIX: FALSE\r\n"
322     "MULTIPLICITY: FALSE\r\n"
323     "POSSIBILITIES: FALSE,TRUE\r\n"
324     ".\r\n";
325     }
326     else if (lscp_parser_test(&tok, "mix_channel_destination")) {
327     pszResult = "DESCRIPTION: 'Audio mix channel destination'\r\n"
328     "TYPE: INT\r\n"
329     "MANDATORY: TRUE\r\n"
330     "FIX: FALSE\r\n"
331     "MULTIPLICITY: TRUE\r\n"
332     "POSSIBILITIES: 0,1\r\n"
333     ".\r\n";
334     }
335     else ret = LSCP_FAILED;
336     }
337     else ret = LSCP_FAILED;
338     }
339     else if (lscp_parser_test2(&tok, "MIDI_INPUT_PORT_PARAMETER", "INFO")) {
340     // Getting informations about specific MIDI port parameter.
341     // GET MIDI_INPUT_PORT_PARAMETER INFO <midi-device-id> <midi-port> <param>
342     if (lscp_parser_nextint(&tok) < iMidiDevice) {
343     lscp_parser_nextint(&tok);
344     if (lscp_parser_test(&tok, "alsa_seq_bindings")) {
345     pszResult = "DESCRIPTION: 'Alsa sequencer port bindings'\r\n"
346     "TYPE: STRING\r\n"
347     "MANDATORY: TRUE\r\n"
348     "FIX: FALSE\r\n"
349     "MULTIPLICITY: TRUE\r\n"
350     "POSSIBILITIES: '64:0','68:0','68:1'\r\n"
351     ".\r\n";
352     }
353     else ret = LSCP_FAILED;
354     }
355     else ret = LSCP_FAILED;
356     }
357     else if (lscp_parser_test(&tok, "AUDIO_OUTPUT_DEVICES")) {
358     // Getting all created audio output device count.
359     // GET AUDIO_OUTPUT_DEVICES
360     sprintf(szTemp, "%d\r\n", iAudioDevice);
361     pszResult = szTemp;
362     }
363     else if (lscp_parser_test(&tok, "MIDI_INPUT_DEVICES")) {
364     // Getting all created MID input device count.
365     // GET MIDI_INPUT_DEVICES
366     sprintf(szTemp, "%d\r\n", iMidiDevice);
367     pszResult = szTemp;
368     }
369     else if (lscp_parser_test(&tok, "AVAILABLE_ENGINES")) {
370     // Getting all available engine count:
371     // GET AVAILABLE_ENGINES
372     pszResult = "3\r\n";
373     }
374     else if (lscp_parser_test2(&tok, "SERVER", "INFO")) {
375     // Getting information about the server.
376     // GET SERVER INFO
377     sprintf(szTemp, "DESCRIPTION: example_server (%s) %s\r\n"
378     "VERSION: %s\r\n.\r\n", lscp_server_package(),
379     lscp_server_build(), lscp_server_version());
380     pszResult = szTemp;
381     }
382     else if (lscp_parser_test2(&tok, "ENGINE", "INFO")) {
383     // Getting information about an engine.
384     // GET ENGINE INFO <engine-name>
385     if (lscp_parser_test(&tok, "GigEngine")) {
386     pszResult = "DESCRIPTION: GigaSampler Engine\r\n"
387     "VERSION: 0.3\r\n"
388     ".\r\n";
389     }
390     else if (lscp_parser_test(&tok, "DLSEngine")) {
391     pszResult = "DESCRIPTION: 'DLS Generic Engine'\r\n"
392     "VERSION: 0.2\r\n"
393     ".\r\n";
394     }
395     else if (lscp_parser_test(&tok, "AkaiEngine")) {
396     pszResult = "DESCRIPTION: Akai Sampler Engine\r\n"
397     "VERSION: 0.1\r\n"
398     ".\r\n";
399     }
400     else ret = LSCP_FAILED;
401     }
402     else if (lscp_parser_test(&tok, "TOTAL_VOICE_COUNT")) {
403     // Current number of active voices:
404     // GET TOTAL_VOICE_COUNT
405     sprintf(szTemp, "%d\r\n", rand() % 100);
406     pszResult = szTemp;
407     }
408     else if (lscp_parser_test(&tok, "TOTAL_VOICE_COUNT_MAX")) {
409     // Maximum amount of active voices:
410     // GET TOTAL_VOICE_COUNT_MAX
411     sprintf(szTemp, "%d\r\n", rand() % 100);
412     pszResult = szTemp;
413     }
414     else if (lscp_parser_test(&tok, "MIDI_INSTRUMENTS")) {
415     // Get the total count of MIDI instrument map entries:
416     // GET MIDI_INSTRUMENTS
417     sprintf(szTemp, "%d\r\n", iMidiInstruments);
418     pszResult = szTemp;
419     }
420     if (lscp_parser_test2(&tok, "MIDI_INSTRUMENT", "INFO")) {
421     // Getting information about a MIDI instrument map entry:
422     // GET MIDI_INSTRUMENT INFO <midi-bank-msb> <midi-bank-lsb> <midi-prog>
423     pszResult = "NAME: DummyName\r\n"
424     "ENGINE_NAME: DummyEngine\r\n"
425     "INSTRUMENT_FILE: DummyInstrument.gig\r\n"
426     "INSTRUMENT_NR: 0\r\n"
427     "INSTRUMENT_NAME: Dummy Instrument\r\n"
428     "LOAD_MODE: ON_DEMAND\r\n"
429     "VOLUME: 0.5\r\n"
430     ".\r\n";
431     }
432     else ret = LSCP_FAILED;
433     }
434     else if (lscp_parser_test(&tok, "LIST")) {
435     if (lscp_parser_test(&tok, "CHANNELS")) {
436     // Getting all created sampler channel list.
437     // LIST CHANNELS
438     for (i = 0; i < iSamplerChannel && strlen(szTemp) < sizeof(szTemp) - 8; i++) {
439     if (i > 0)
440     strcat(szTemp, ",");
441     sprintf(szTemp + strlen(szTemp), "%d", i);
442     }
443     strcat(szTemp, "\r\n");
444     pszResult = szTemp;
445     }
446     else if (lscp_parser_test(&tok, "AVAILABLE_ENGINES")) {
447     // Getting all available engines:
448     // LIST AVAILABLE_ENGINES
449     pszResult = "GigEngine,DLSEngine,AkaiEngine\r\n";
450     }
451     else if (lscp_parser_test(&tok, "AVAILABLE_AUDIO_OUTPUT_DRIVERS")) {
452     // Getting all available audio output drivers.
453     // LIST AVAILABLE_AUDIO_OUTPUT_DRIVERS
454     pszResult = "ALSA,JACK\r\n";
455     }
456     else if (lscp_parser_test(&tok, "AVAILABLE_MIDI_INPUT_DRIVERS")) {
457     // Getting all available MIDI input drivers.
458     // LIST AVAILABLE_MIDI_INPUT_DRIVERS
459     pszResult = "ALSA\r\n";
460     }
461     else if (lscp_parser_test(&tok, "AUDIO_OUTPUT_DEVICES")) {
462     // Getting all created audio output device list.
463     // LIST AUDIO_OUTPUT_DEVICES
464     for (i = 0; i < iAudioDevice && strlen(szTemp) < sizeof(szTemp) - 8; i++) {
465     if (i > 0)
466     strcat(szTemp, ",");
467     sprintf(szTemp + strlen(szTemp), "%d", i);
468     }
469     strcat(szTemp, "\r\n");
470     pszResult = szTemp;
471     }
472     else if (lscp_parser_test(&tok, "MIDI_INPUT_DEVICES")) {
473     // Getting all created MID input device list.
474     // LIST MIDI_INPUT_DEVICES
475     for (i = 0; i < iMidiDevice && strlen(szTemp) < sizeof(szTemp) - 8; i++) {
476     if (i > 0)
477     strcat(szTemp, ",");
478     sprintf(szTemp + strlen(szTemp), "%d", i);
479     }
480     strcat(szTemp, "\r\n");
481     pszResult = szTemp;
482     }
483     else if (lscp_parser_test(&tok, "MIDI_INSTRUMENTS")) {
484     // Getting indeces of all MIDI instrument map entries:
485     // LIST MIDI_INSTRUMENTS
486     for (i = 0; i < iMidiInstruments && strlen(szTemp) < sizeof(szTemp) - 16; i++) {
487     if (i > 0)
488     strcat(szTemp, ",");
489     sprintf(szTemp + strlen(szTemp), "{0,%d,%d}", i / 128, i % 128);
490     }
491     strcat(szTemp, "\r\n");
492     pszResult = szTemp;
493     }
494     else ret = LSCP_FAILED;
495     }
496     else if (lscp_parser_test(&tok, "SET")) {
497     if (lscp_parser_test(&tok, "CHANNEL")) {
498     if (lscp_parser_test(&tok, "VOLUME")) {
499     // Setting channel volume:
500     // SET CHANNEL VOLUME <sampler-channel> <volume>
501     }
502     else if (lscp_parser_test(&tok, "MUTE")) {
503     // Muting a sampler channel:
504     // SET CHANNEL MUTE <sampler-channel> <mute>
505     }
506     else if (lscp_parser_test(&tok, "SOLO")) {
507     // Soloing a sampler channel:
508     // SET CHANNEL SOLO <sampler-channel> <solo>
509     }
510     else if (lscp_parser_test(&tok, "AUDIO_OUTPUT_TYPE")) {
511     // Setting audio output type:
512     // SET CHANNEL AUDIO_OUTPUT_TYPE <sampler-channel> <audio-output-type>
513     }
514     else if (lscp_parser_test(&tok, "AUDIO_OUTPUT_DEVICE")) {
515     // Setting audio output device:
516     // SET CHANNEL AUDIO_OUTPUT_DEVICE <sampler-channel> <device-id>
517     }
518     else if (lscp_parser_test(&tok, "AUDIO_OUTPUT_CHANNEL")) {
519     // Setting audio output channel:
520     // SET CHANNEL AUDIO_OUTPUT_CHANNEL <sampler-channel> <audio-in> <audio-out>
521     }
522     else if (lscp_parser_test(&tok, "MIDI_INPUT_TYPE")) {
523     // Setting MIDI input type:
524     // SET CHANNEL MIDI_INPUT_TYPE <sampler-channel> <midi-input-type>
525     }
526     else if (lscp_parser_test(&tok, "MIDI_INPUT_DEVICE")) {
527     // Setting MIDI input device:
528     // SET CHANNEL MIDI_INPUT_DEVICE <sampler-channel> <device-id>
529     }
530     else if (lscp_parser_test(&tok, "MIDI_INPUT_PORT")) {
531     // Setting MIDI input port:
532     // SET CHANNEL MIDI_INPUT_PORT <sampler-channel> <midi-input-port>
533     }
534     else if (lscp_parser_test(&tok, "MIDI_INPUT_CHANNEL")) {
535     // Setting MIDI input channel:
536     // SET CHANNEL MIDI_INPUT_CHANNEL <sampler-channel> <midi-input-chan>
537     }
538     else ret = LSCP_FAILED;
539     }
540     else ret = LSCP_FAILED;
541     }
542     else if (lscp_parser_test(&tok, "LOAD")) {
543     if (lscp_parser_test(&tok, "ENGINE")) {
544     // Loading a sampler engine:
545     // LOAD ENGINE <engine-name> <sampler-channel>
546     }
547     else if (lscp_parser_test(&tok, "INSTRUMENT")) {
548     // Loading an instrument:
549     // LOAD INSTRUMENT [NON_MODAL] <filename> <instr-index> <sampler-channel>
550     }
551     else ret = LSCP_FAILED;
552     }
553     else if (lscp_parser_test2(&tok, "ADD", "CHANNEL")) {
554     // Adding a new sampler channel:
555     // ADD CHANNEL
556     if (iSamplerChannel < 16) {
557     sprintf(szTemp, "OK[%d]\r\n", iSamplerChannel++);
558     pszResult = szTemp;
559     } else {
560     iSamplerChannel = 0;
561     ret = LSCP_FAILED;
562     }
563     }
564     else if (lscp_parser_test2(&tok, "REMOVE", "CHANNEL")) {
565     // Removing a sampler channel:
566     // REMOVE CHANNEL <sampler-channel>
567     if (lscp_parser_nextint(&tok) < iSamplerChannel)
568     iSamplerChannel--;
569     else
570     ret = LSCP_FAILED;
571     }
572     else if (lscp_parser_test(&tok, "RESET")) {
573     if (lscp_parser_test(&tok, "CHANNEL")) {
574     // Resetting a sampler channel:
575     // RESET CHANNEL <sampler-channel>
576     if (lscp_parser_nextint(&tok) > iSamplerChannel)
577     ret = LSCP_FAILED;
578     } else {
579     // Reset sampler:
580     // RESET
581     iSamplerChannel = 0;
582     iAudioDevice = 0;
583     iMidiDevice = 0;
584     }
585     }
586     else if (lscp_parser_test(&tok, "CREATE")) {
587     if (lscp_parser_test(&tok, "AUDIO_OUTPUT_DEVICE")) {
588     // Creating an audio output device.
589     // CREATE AUDIO_OUTPUT_DEVICE <audio-output-driver> [<params>]
590     if (iAudioDevice < 8) {
591     sprintf(szTemp, "OK[%d]\r\n", iAudioDevice++);
592     pszResult = szTemp;
593     } else {
594     iAudioDevice = 0;
595     ret = LSCP_FAILED;
596     }
597     }
598     else if (lscp_parser_test(&tok, "MIDI_INPUT_DEVICE")) {
599     // Creating an MIDI input device.
600     // CREATE MIDI_INPUT_DEVICE <midi-input-driver> [<params>]
601     if (iMidiDevice < 8) {
602     sprintf(szTemp, "OK[%d]\r\n", iMidiDevice++);
603     pszResult = szTemp;
604     } else {
605     iMidiDevice = 0;
606     ret = LSCP_FAILED;
607     }
608     }
609     else ret = LSCP_FAILED;
610     }
611     else if (lscp_parser_test(&tok, "DESTROY")) {
612     if (lscp_parser_test(&tok, "AUDIO_OUTPUT_DEVICE")) {
613     // Destroying an audio output device.
614     // DESTROY AUDIO_OUTPUT_DEVICE <audio-device-id>
615     if (lscp_parser_nextint(&tok) < iAudioDevice)
616     iAudioDevice--;
617     else
618     ret = LSCP_FAILED;
619     }
620     else if (lscp_parser_test(&tok, "MIDI_INPUT_DEVICE")) {
621     // Destroying an MIDI intput device.
622     // DESTROY MIDI_INPUT_DEVICE <midi-device-id>
623     if (lscp_parser_nextint(&tok) < iMidiDevice)
624     iMidiDevice--;
625     else
626     ret = LSCP_FAILED;
627     }
628     else ret = LSCP_FAILED;
629     }
630     else if (lscp_parser_test2(&tok, "MAP", "MIDI_INSTRUMENT")) {
631     // Create or replace a MIDI instrumnet map entry:
632     // MAP MIDI_INSTRUMENT <midi-bank-msb> <midi-bank-lsb> <midi-prog>
633     // <engine-name> <filename> <instr-index> <volume> <load-mode> [<name>]
634     iMidiInstruments++;
635     }
636     else if (lscp_parser_test2(&tok, "UNMAP", "MIDI_INSTRUMENT")) {
637     // Remove an entry from the MIDI instrument map:
638     // UNMAP MIDI_INSTRUMENT <midi-bank-msb> <midi-bank-lsb> <midi-prog>
639     if (iMidiInstruments > 0)
640     iMidiInstruments--;
641     else
642     ret = LSCP_FAILED;
643     }
644     else if (lscp_parser_test2(&tok, "CLEAR", "MIDI_INSTRUMENTS")) {
645     // Clear the MIDI instrumnet map:
646     // CLEAR MIDI_INSTRUMENTS
647     }
648     else if (lscp_parser_test(&tok, "SUBSCRIBE")) {
649     // Register frontend for receiving event notification messages:
650     // SUBSCRIBE <event>
651     ret = lscp_server_subscribe(pConnect, lscp_event_from_text(lscp_parser_next(&tok)));
652     }
653     else if (lscp_parser_test(&tok, "UNSUBSCRIBE")) {
654     // Deregister frontend for not receiving event notification messages anymore:
655     // UNSUBSCRIBE <event>
656     ret = lscp_server_unsubscribe(pConnect, lscp_event_from_text(lscp_parser_next(&tok)));
657     }
658     else if (lscp_parser_test(&tok, "QUIT")) {
659     // Close client connection:
660     // QUIT
661     lscp_parser_free(&tok);
662     return LSCP_FAILED; // Disconnect.
663     }
664     else ret = LSCP_FAILED;
665 capela 105
666 capela 963 lscp_parser_free(&tok);
667 capela 105
668 capela 963 if (pszResult == NULL)
669     pszResult = (ret == LSCP_OK ? "OK\r\n" : "ERR:1:Failed\r\n");
670 capela 105
671 capela 963 fprintf(stderr, "> %s", pszResult);
672 capela 105
673 capela 963 return lscp_server_result(pConnect, pszResult, strlen(pszResult));
674 capela 105 }
675    
676     ////////////////////////////////////////////////////////////////////////
677    
678 capela 189
679 capela 105 void server_usage (void)
680     {
681 capela 963 printf("\n %s %s (Build: %s)\n", lscp_server_package(), lscp_server_version(), lscp_server_build());
682 capela 105
683 capela 963 fputs("\n Available server commands: help, exit, quit, list", stdout);
684     fputs("\n (all else are broadcast verbatim to subscribers)\n\n", stdout);
685 capela 105 }
686    
687     void server_prompt (void)
688     {
689 capela 963 fputs("lscp_server> ", stdout);
690 capela 105 }
691    
692     int main (int argc, char *argv[] )
693     {
694 capela 963 lscp_server_t *pServer;
695     char szLine[200];
696     int cchLine;
697     lscp_connect_t *p;
698 capela 105
699     #if defined(WIN32)
700 capela 963 if (WSAStartup(MAKEWORD(1, 1), &_wsaData) != 0) {
701     fprintf(stderr, "lscp_server: WSAStartup failed.\n");
702     return -1;
703     }
704 capela 105 #endif
705    
706 capela 963 srand(time(NULL));
707 capela 105
708 capela 963 pServer = lscp_server_create(SERVER_PORT, server_callback, NULL);
709     if (pServer == NULL)
710     return -1;
711 capela 105
712 capela 963 server_usage();
713     server_prompt();
714 capela 105
715 capela 963 while (fgets(szLine, sizeof(szLine), stdin)) {
716 capela 105
717 capela 963 cchLine = strlen(szLine);
718     while (cchLine > 0 && (szLine[cchLine - 1] == '\n' || szLine[cchLine - 1] == '\r'))
719     cchLine--;
720     szLine[cchLine] = '\0';
721 capela 105
722 capela 963 if (strcmp(szLine, "exit") == 0 || strcmp(szLine, "quit") == 0)
723     break;
724     else
725     if (strcmp(szLine, "list") == 0) {
726     for (p = pServer->connects.first; p; p = p->next) {
727     printf("client: sock=%d addr=%s port=%d events=0x%04x.\n",
728     p->client.sock,
729     inet_ntoa(p->client.addr.sin_addr),
730     ntohs(p->client.addr.sin_port),
731     (int) p->events
732     );
733     }
734     }
735     else
736     if (cchLine > 0 && strcmp(szLine, "help") != 0)
737     lscp_server_broadcast(pServer, LSCP_EVENT_MISCELLANEOUS, szLine, strlen(szLine));
738     else
739     server_usage();
740 capela 105
741 capela 963 server_prompt();
742     }
743 capela 105
744 capela 963 lscp_server_destroy(pServer);
745 capela 105
746     #if defined(WIN32)
747 capela 963 WSACleanup();
748 capela 105 #endif
749    
750 capela 963 return 0;
751 capela 105 }
752    
753     // end of example_server.c

  ViewVC Help
Powered by ViewVC