Changed the backend api somewhat. Added bpm==0 check.
[epichord.git] / src / jack.cpp
blobf9f8edc5de7bf0b744d6319a0e3e648b6ddac97a
1 /*
2 Epichord - a midi sequencer
3 Copyright (C) 2008 Evan Rinehart
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License
7 as published by the Free Software Foundation; either version 2
8 of the License, or (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to
18 The Free Software Foundation, Inc.
19 51 Franklin Street, Fifth Floor
20 Boston, MA 02110-1301, USA
23 #include <stdio.h>
24 #include <string.h>
26 #include <vector>
27 #include <string>
29 #include <pthread.h>
30 #include <jack/jack.h>
31 #include <jack/types.h>
32 #include <jack/ringbuffer.h>
33 #include <jack/midiport.h>
34 #include <jack/transport.h>
36 #define HAVE_LASH
38 #ifdef HAVE_LASH
39 #include <lash/lash.h>
40 lash_client_t* lash_client;
41 #endif
43 #include "seq.h"
44 #include "backend.h"
47 //#include "ui.h"
49 #define PORT_COUNT 8
51 //#define HAVE_LASH
53 extern std::vector<track*> tracks;
55 jack_client_t* client;
57 jack_port_t* outport[PORT_COUNT];
58 jack_port_t* inport;
59 void* pbo[PORT_COUNT];
60 void* pbi;
62 jack_ringbuffer_t* outbuf;
63 jack_ringbuffer_t* inbuf;
65 static int playing = 0;
66 static int looping = 0;
67 static int recording=0;
68 static int loop_start = 0;
69 static int loop_end = 512;
70 static int passthru = 1;
71 static int rec_port = 0;
73 static int init_chans = 1;
75 static uint64_t cur_frame = 0;
76 static uint64_t last_frame = 0;
77 static int frame_jump = 0;
78 static int cur_tick;
79 static int last_tick;
80 static int bpm = 120;
81 static int new_bpm = 120;
82 static int tpb = TICKS_PER_BEAT;
83 static int sample_rate = 0;
84 static int frame_count = 0;
86 #define t2f(X) ((uint64_t)X*60*sample_rate/(bpm*tpb))
87 #define f2t(X) ((uint64_t)X*bpm*tpb/(sample_rate*60))
91 //void (*update_display)() = NULL;
93 /* callback for seq.c and play.c */
94 /* THIS BARELY WORKS */
95 void dispatch_event(mevent* e, int track, int tick_base){
97 jack_midi_data_t* md;
99 int p = tracks[track]->port;
100 int c = tracks[track]->chan;
102 uint64_t base = t2f(tick_base);
103 uint64_t frame = t2f(e->tick) + base - last_frame + frame_jump;
105 if(e->type == -1){
106 return;
109 if(looping && e->tick+tick_base == loop_end && e->type != MIDI_NOTE_OFF){
110 //dispatch only note off events on a loop_end
111 return;
114 //printf("0x%x %d %llu %llu %llu %d %llu %d\n", e->type, e->tick, t2f(e->tick), base, last_frame, frame_jump, frame, bpm);
116 if(t2f(e->tick)+base < last_frame){
117 printf("playing a note in the past?? lucky it didnt segfault!\n");
118 return;
121 if(frame == frame_count){
122 frame--;
125 unsigned char buf[3];
126 size_t n;
127 if(midi_encode(e,c,buf,&n) < 0){
128 return;
131 md = jack_midi_event_reserve(pbo[p],frame,n);
132 if(md == NULL){
133 md = jack_midi_event_reserve(pbo[p],frame_count-1,n);
134 if(md == NULL){
135 printf("dispatch: can't reserve midi event\n");
136 return;
139 for(int i=0; i<n; i++){
140 md[i] = buf[i];
147 /* jack callbacks */
149 static int H = 1;
150 static int process(jack_nframes_t nframes, void* arg){
152 frame_count = nframes;
154 //handle incoming midi events
155 for(int i=0; i<PORT_COUNT; i++){
156 pbo[i] = jack_port_get_buffer(outport[i],nframes);
157 jack_midi_clear_buffer(pbo[i]);
159 pbi = jack_port_get_buffer(inport,nframes);
161 jack_midi_data_t* md1;
162 jack_midi_data_t* md2;
164 jack_midi_event_t me;
166 uint32_t rec_tick;
168 for(int i=0; i<jack_midi_get_event_count(pbi); i++){
169 jack_midi_event_get(&me,pbi,i);
170 md1 = me.buffer;
171 //printf("%d got midi event, type 0x%x, value 0x%x 0x%x\n",i,md1[0],md1[1],md1[2]);
172 if(passthru){
173 md2 = jack_midi_event_reserve(pbo[rec_port],0,me.size);
174 if(md2 == NULL){
175 printf("passthru: can't reserve midi event\n");
177 else{
178 memcpy(md2,md1,me.size);
181 rec_tick = last_tick + (me.time*bpm*tpb)/(sample_rate*60);
183 //if(playing && recording){
184 uint16_t size = me.size;
185 jack_ringbuffer_write(inbuf,(char*)&rec_tick,4);
186 jack_ringbuffer_write(inbuf,(char*)&size,2);
187 jack_ringbuffer_write(inbuf,(char*)md1,me.size);
188 // }
191 //init chans
192 if(init_chans && playing){
193 init_chans=0;
194 char buf[3];
195 for(int j=0; j<tracks.size(); j++){
196 int ch = tracks[j]->chan;
197 int pt = tracks[j]->port;
199 //bank select
200 buf[0] = 0xB0 | ch;
201 buf[1] = 0;
202 buf[2] = tracks[j]->bank;
203 send_midi(buf,3,pt);
205 //program change
206 buf[0] = 0xC0 | ch;
207 buf[1] = tracks[j]->prog;
208 send_midi(buf,2,pt);
210 //channel volume
211 buf[0] = 0xB0 | ch;
212 buf[1] = 7;
213 buf[2] = tracks[j]->vol;
214 send_midi(buf,3,pt);
216 //channel pan
217 buf[0] = 0xB0 | ch;
218 buf[1] = 10;
219 buf[2] = tracks[j]->pan;
220 send_midi(buf,3,pt);
225 //handle outgoing immediate midi events
226 uint16_t n;
227 char p;
228 char buf[1024];
229 while(jack_ringbuffer_read_space(outbuf) > 0){
230 jack_ringbuffer_read(outbuf,&p,1);
231 jack_ringbuffer_read(outbuf,(char*)&n,2);
232 jack_ringbuffer_read(outbuf,buf,n);
233 md1 = jack_midi_event_reserve(pbo[p],0,n);
234 if(md1 == NULL){
235 printf("gui: can't reserve midi event\n");
236 break;
238 for(int i=0; i<n; i++){
239 md1[i]=buf[i];
244 //play
245 if(playing){
246 if(bpm != new_bpm){
247 if(new_bpm != 0){
248 bpm = new_bpm;
250 else{
251 printf("process: someone set the bpm to zero!\n");
252 bpm = 120;
254 cur_frame = t2f(cur_tick);
255 last_frame = t2f(last_tick);
258 last_frame = cur_frame;
259 cur_frame += nframes;
260 last_tick = cur_tick;
261 cur_tick = f2t(cur_frame);
262 frame_jump = 0;
263 int le = loop_end;
264 int ls = loop_start;
265 int lf = looping;
268 /* this only handles the case where the nframes covers the
269 loop boundary once. a more robust way would split it into
270 before covering n loop boundaries, a loop for n looping regions,
271 and a final section covering part of the loop region. this
272 would only need to be used for insanely high bpm */
273 if(lf && last_tick < le && cur_tick > le ){
274 //printf("split l%d m%d r%d\n",last_tick,loop_end,cur_tick);
275 int split_frame = t2f(le) - last_frame + 1;
276 int left_over = nframes - split_frame;
277 int jump = split_frame;
278 cur_frame = last_frame + jump;
279 cur_tick = f2t(cur_frame);
280 //printf("cur tick %d\n",cur_tick);
281 play_seq(cur_tick);
283 reset_backend(ls);
284 //printf("cur tick %d\n",cur_tick);
285 frame_jump = jump;
286 last_frame = t2f(ls);
287 cur_frame = last_frame + left_over;
288 cur_tick = f2t(cur_frame);
290 play_seq(cur_tick);
292 else if(lf && cur_tick > le){
293 reset_backend(ls);
294 last_frame = t2f(ls);
295 cur_frame = last_frame + nframes;
296 cur_tick = f2t(cur_frame);
297 //printf("%llu %llu %d %d\n",last_frame,cur_frame,last_tick,cur_tick);
298 play_seq(cur_tick);
300 else{
301 //printf("%llu %llu %d %d\n",last_frame,cur_frame,last_tick,cur_tick);
302 play_seq(cur_tick);
306 return 0;
313 /* backend api wrapper */
315 int init_backend(int* argc, char*** argv){
317 client = jack_client_open("Epichord",(jack_options_t)0,NULL);
318 if(client == NULL){
319 printf("init_backend: failure to open jack client\n");
320 return -1;
323 jack_set_process_callback(client, process, 0);
325 char buf[64];
326 for(int i=0; i<PORT_COUNT; i++){
327 sprintf(buf,"midi out %d",i);
328 outport[i]=jack_port_register(client,buf,JACK_DEFAULT_MIDI_TYPE,JackPortIsOutput,0);
331 inport=jack_port_register(client, "midi in", JACK_DEFAULT_MIDI_TYPE, JackPortIsInput, 0);
333 outbuf = jack_ringbuffer_create(1024);
334 inbuf = jack_ringbuffer_create(1024);
336 sample_rate = jack_get_sample_rate(client);
338 jack_activate(client);
340 #ifdef HAVE_LASH
342 lash_client = lash_init(lash_extract_args(argc, argv), "Epichord",
343 LASH_Config_File, LASH_PROTOCOL( 2, 0 ));
344 if(!lash_client){
345 printf("init_backend: lash failed to initialize\n");
347 else{
348 lash_jack_client_name(lash_client, "Epichord");
351 #endif
353 return 0;
359 int shutdown_backend(){
360 pause_backend();
361 all_notes_off();
362 sleep(1);
363 jack_deactivate(client);
364 //sleep(1);
365 return 0;
369 int start_backend(){
370 playing = 1;
373 int pause_backend(){
374 playing = 0;
377 int reset_backend(int tick){
378 if(tick==0){
379 init_chans = 1;
381 cur_frame = t2f(tick);
382 last_frame = cur_frame;
383 last_tick = tick;
384 cur_tick = tick;
385 set_seq_pos(tick);
389 void toggle_backend_recording(){
390 if(recording){
391 recording = 0;
393 else{
394 recording = 1;
399 //send a midi event from the gui thread
400 void send_midi(char* raw, uint16_t n, uint8_t port){
401 if(n>1024){
402 printf("send_midi: cant send, immediate message too big\n");
403 return;
405 char buf[2048];
406 buf[0] = port;
407 memcpy(buf+1,&n,2);
408 memcpy(buf+3,raw,n);
409 //FIXME check return value
410 jack_ringbuffer_write(outbuf,buf,3+n);
413 void send_midi_local(char* raw, uint16_t n){
414 uint32_t tick = cur_tick;
415 uint16_t size = n;
416 //FIXME chec return value
417 jack_ringbuffer_write(inbuf,(char*)&tick,4);
418 jack_ringbuffer_write(inbuf,(char*)&size,2);
419 jack_ringbuffer_write(inbuf,raw,n);
424 std::string sysexbuf;
425 //get next incoming midi event for gui thread
426 int recv_midi(int* chan, int* tick, int* type, int* val1, int* val2){
427 uint16_t n;
428 uint32_t t;
429 unsigned char* buf;
430 if(jack_ringbuffer_read(inbuf,(char*)&t,4) == 0){
431 return 0;
433 jack_ringbuffer_read(inbuf,(char*)&n,2);
434 buf = (unsigned char*)malloc(n);
435 jack_ringbuffer_read(inbuf,(char*)buf,n);
437 *tick = t;
438 *chan = buf[0]&0x0f;
439 *type = buf[0]&0xf0;
440 *val1 = buf[1];
441 *val2 = buf[2];
443 char hbuf[8];
445 if (buf[0]==0xf0){
446 sysexbuf = "";
447 for(int i=2; i<n-1; i++){
448 snprintf(hbuf,8,"%02x ",buf[i]);
449 sysexbuf.append(hbuf);
453 free(buf);
454 return 1;
457 const char* getsysexbuf(){
458 return sysexbuf.c_str();
462 void all_notes_off(){
463 for(int i=0; i<tracks.size(); i++){
464 midi_track_off(i);
468 void program_change(int track, int prog){
469 int port = tracks[track]->port;
470 int chan = tracks[track]->chan;
472 char buf[2];
473 buf[0] = 0xC0 | chan;
474 buf[1] = prog;
475 send_midi(buf, 2, port);
478 void midi_bank_controller(int track, int bank){
479 int port = tracks[track]->port;
480 int chan = tracks[track]->chan;
482 char buf[3];
483 buf[0] = 0xB0 | chan;
484 buf[1] = 0;
485 buf[2] = bank;
486 send_midi(buf, 3, port);
489 void midi_volume_controller(int track, int vol){
490 int port = tracks[track]->port;
491 int chan = tracks[track]->chan;
493 char buf[3];
494 buf[0] = 0xB0 | chan;
495 buf[1] = 7;
496 buf[2] = vol;
497 send_midi(buf, 3, port);
500 void midi_pan_controller(int track, int pan){
501 int port = tracks[track]->port;
502 int chan = tracks[track]->chan;
504 char buf[3];
505 buf[0] = 0xB0 | chan;
506 buf[1] = 10;
507 buf[2] = pan;
508 send_midi(buf, 3, port);
511 void midi_expression_controller(int track, int expr){
512 int port = tracks[track]->port;
513 int chan = tracks[track]->chan;
515 char buf[3];
516 buf[0] = 0xB0 | chan;
517 buf[1] = 11;
518 buf[2] = expr;
519 send_midi(buf, 3, port);
523 void midi_note_off(int note, int chan, int port){
524 char buf[3];
525 buf[0] = 0x80 | chan;
526 buf[1] = note;
527 buf[2] = 0x00;
528 send_midi(buf,3,port);
531 void midi_track_off(int track){
532 int chan = tracks[track]->chan;
533 int port = tracks[track]->port;
535 midi_channel_off(chan,port);
538 void midi_channel_off(int chan, int port){
539 char buf[3] = {0xB0,123,0};
540 buf[0] = 0xB0 | chan;
541 send_midi(buf,3,port);
543 buf[0] = 0xB0 | chan;
544 buf[1] = 120;
545 send_midi(buf,3,port);
549 void backend_set_passthru(int v){
550 passthru = v;
553 void set_loop_start(int tick){
554 loop_start = tick;
557 void set_loop_end(int tick){
558 loop_end = tick;
561 int get_loop_start(){
562 return loop_start;
565 int get_loop_end(){
566 return loop_end;
569 int get_play_position(){
570 return cur_tick;
573 int solo;
574 void set_solo(int s){
575 solo = s;
578 int get_solo(){
579 return solo;
582 int is_backend_playing(){
583 return playing;
586 int is_backend_recording(){
587 return recording&&playing;
590 void toggle_loop(){
591 if(looping){
592 looping = 0;
594 else{
595 looping = 1;
600 void set_bpm(int n){
601 new_bpm = n;
605 char* session_string;
606 int backend_session_process(){
607 int ret = SESSION_NOMORE;
608 #ifdef HAVE_LASH
609 lash_event_t *e;
611 char *name;
613 e = lash_get_event(lash_client);
614 if(!e){
615 return SESSION_NOMORE;
618 asprintf(&session_string,"%s",lash_event_get_string(e));
619 const int t = lash_event_get_type (e);
621 switch(t)
623 case LASH_Save_File:
624 printf("session_process: LASH save\n");
625 lash_send_event(lash_client, lash_event_new_with_type(LASH_Save_File));
626 ret = SESSION_SAVE;
627 break;
628 case LASH_Restore_File:
629 printf("session_process: LASH load\n");
630 lash_send_event(lash_client, lash_event_new_with_type(LASH_Restore_File));
631 ret = SESSION_LOAD;
632 break;
633 case LASH_Quit:
634 printf("session_process: LASH quit\n");
635 ret = SESSION_QUIT;
636 break;
637 default:
638 printf("session_process: unhandled LASH event (%d)\n", t);
639 switch(t){
640 case LASH_Client_Name: printf("LASH_Client_Name\n"); break;
641 case LASH_Jack_Client_Name: printf("LASH_Jack_Client_Name\n"); break;
642 case LASH_Alsa_Client_ID: printf("LASH_Alsa_Client_ID\n"); break;
643 case LASH_Save_File: printf("LASH_Save_File\n"); break;
644 case LASH_Save_Data_Set: printf("LASH_Save_Data_Set\n"); break;
645 case LASH_Restore_Data_Set: printf("LASH_Restore_Data_Set\n"); break;
646 case LASH_Save: printf("LASH_Save\n"); break;
648 ret = SESSION_UNHANDLED;
649 break;
651 //lash_event_destroy(e);
652 #endif
653 return ret;
656 char* get_session_string(){
657 return session_string;