示例#1
0
文件: scope.c 项目: UIKit0/openlase-1
int main (int argc, char *argv[])
{
	jack_client_t *client;
	char jack_client_name[] = "scope";
	jack_status_t jack_status;
	jack_options_t  jack_options = JackNullOption;		

	if ((client = jack_client_open(jack_client_name, jack_options, &jack_status)) == 0) {
		fprintf (stderr, "jack server not running?\n");
		return 1;
	}

	jack_set_process_callback (client, process, 0);
	jack_set_buffer_size_callback (client, bufsize, 0);
	jack_set_sample_rate_callback (client, srate, 0);
	jack_on_shutdown (client, jack_shutdown, 0);

	in_l = jack_port_register (client, "in_l", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	in_r = jack_port_register (client, "in_r", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	out_x = jack_port_register (client, "out_x", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
	out_y = jack_port_register (client, "out_y", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
	out_w = jack_port_register (client, "out_w", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);

	if (jack_activate (client)) {
		fprintf (stderr, "cannot activate client");
		return 1;
	}

	while (1)
		sleep(1);
	jack_client_close (client);
	exit (0);
}
示例#2
0
    JackAudioProvider(Synth *synth, const std::string &name)
      : synth_(synth)
    {
      SampleBufferAllocator::reset();
      client_ = jack_client_open(name.c_str(), JackNoStartServer, 0);
      if (client_ == NULL) {
	throw JackClientOpenError();
      }
      std::cout << "connected to jackd as client `" << name << "`\n";
      sl::sampleRate(jack_get_sample_rate(client_));
      jack_set_sample_rate_callback(client_, jackSampleRateCallback, 0);
      sl::bufferSize(jack_get_buffer_size(client_));
      jack_set_buffer_size_callback(client_, jackBufferSizeCallback, 0);
      jack_set_process_callback(client_, jackProcessCallback, this);
      midiInPort_ = jack_port_register(client_, "midi_in", JACK_DEFAULT_MIDI_TYPE, JackPortIsInput, 0);
      std::cout << "registered midi port: midi_in\n";
      char portName[64];
      for (int i=0; i<Synth::InputBuffer::nChannels; i++) {
	snprintf(portName, sizeof(portName), "in_%u", i+1);
	inputPorts_[i] = jack_port_register(client_, portName, JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
        std::cout << "registered audio port: " << portName << "\n";
      }
      for (int i=0; i<Synth::OutputBuffer::nChannels; i++) {
	snprintf(portName, sizeof(portName), "out_%u", i+1);
	outputPorts_[i] = jack_port_register(client_, portName, JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
        std::cout << "registered audio port: " << portName << "\n";
      }
      for (int i=0; i<128; i++) {
        midiCtrlMap_[i] = i;
      }
      for (int i=11; i<=19; i++) {
        midiCtrlMap_[i] = i-10;
      }
      midiCtrlMap_[1] = 129; // modwheel
    }
示例#3
0
文件: pyjack.c 项目: egasimus/pyjack
// Attempt to connect to the Jack server
static PyObject* attach(PyObject* self, PyObject* args)
{
    char* cname;
    if (! PyArg_ParseTuple(args, "s", &cname))
        return NULL;

    pyjack_client_t * client = self_or_global_client(self);
    if(client->pjc != NULL) {
        PyErr_SetString(JackUsageError, "A connection is already established.");
        return NULL;
    }

    jack_status_t status;
    client->pjc = jack_client_open(cname, JackNoStartServer, &status);
    if(client->pjc == NULL) {
        //TODO check status
        PyErr_SetString(JackNotConnectedError, "Failed to connect to Jack audio server.");
        return NULL;
    }

    jack_on_shutdown(client->pjc, pyjack_shutdown, client);
    signal(SIGHUP, pyjack_hangup); // TODO: This just works with global clients

    if(jack_set_process_callback(client->pjc, pyjack_process, client) != 0) {
        PyErr_SetString(JackError, "Failed to set jack process callback.");
        return NULL;
    }

    if(jack_set_buffer_size_callback(client->pjc, pyjack_buffer_size_changed, client) != 0) {
        PyErr_SetString(JackError, "Failed to set jack buffer size callback.");
        return NULL;
    }

    if(jack_set_sample_rate_callback(client->pjc, pyjack_sample_rate_changed, client) != 0) {
        PyErr_SetString(JackError, "Failed to set jack sample rate callback.");
        return NULL;
    }

    if(jack_set_port_registration_callback(client->pjc, pyjack_port_registration, client) != 0) {
        PyErr_SetString(JackError, "Failed to set jack port registration callback.");
        return NULL;
    }

    if(jack_set_graph_order_callback(client->pjc, pyjack_graph_order, client) != 0) {
        PyErr_SetString(JackError, "Failed to set jack graph order callback.");
        return NULL;
    }

    if(jack_set_xrun_callback(client->pjc, pyjack_xrun, client) != 0) {
        PyErr_SetString(JackError, "Failed to set jack xrun callback.");
        return NULL;
    }

    // Get buffer size
    client->buffer_size = jack_get_buffer_size(client->pjc);

    // Success!
    Py_INCREF(Py_None);
    return Py_None;
}
bool Out_JACK::Go()
{
	SampleRate = 0;

	// Create a new JACK client.
	JackClient = jack_client_new("Sinospan");
	if(JackClient == NULL) { printf("FATAL: out_jack: Couldn't make JACK client\n"); return false; }

	// Associate our render function as the JACK process callback
	if(jack_set_process_callback(JackClient, R_pRender, (void*) this) != 0) { printf("ERROR: out_jack: Couldn't register processing callback\n"); }
	
	// Set our sample rate change handler
	if(jack_set_sample_rate_callback(JackClient, R_pNewSrate, (void*) this) != 0) { printf("WARNING: out_jack: Couldn't register sample rate callback.\n"); }

	// Make our output port
	JackOut1 = jack_port_register(JackClient, "Out", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
	if(JackOut1 == NULL) { printf("FATAL: out_jack: Couldn't register an output port.\n"); return false; }

	// Get the sample rate from the JACK server.
	R_pNewSrate(jack_get_sample_rate(JackClient), (void*) this);

	// It's go-time!
	if(jack_activate(JackClient) != 0) { printf("ERROR: out_jack: Couldn't activate JACK client.\n"); return false; }

	return true;
}
示例#5
0
jack_raw_output::jack_raw_output (const char* client,
                                  const char* server,
                                  int         rate,
                                  int         channels,
                                  callback_type cb)
    : detail::async_base_impl (cb)
    , _out_ports (channels)
    , _buffer_size (0)
{
    jack_set_error_function (log_jack_error);
    jack_set_info_function (log_jack_info);
    
    jack_options_t options = !server ? JackNullOption : JackServerName; 
    _client = jack_client_open (client, options, 0, server);
    if (!_client) throw jack_open_error ();

    auto grd_client = base::make_guard ([&] { jack_client_close (_client); });
    
    PSYNTH_JACK_CHECK (jack_set_process_callback (
                           _client, &jack_raw_output::_process_cb, this),
                       jack_param_error);
    PSYNTH_JACK_CHECK (jack_set_sample_rate_callback (
                           _client, &jack_raw_output::_sample_rate_cb, this),
                       jack_param_error);

    jack_on_shutdown (_client, &jack_raw_output::_shutdown_cb, this);
	
    _actual_rate = jack_get_sample_rate (_client);
    if (_actual_rate != rate)
        PSYNTH_LOG
            << base::log::warning
            << "Jackd sample rate and application sample rate mismatch."
            << "Better sound quality is achieved if both are the same.";


    _buffer_size = jack_get_buffer_size (_client);
    PSYNTH_LOG << base::log::info
               << "Jackd buffer size is: " << _buffer_size;
    
    for (size_t i = 0; i < _out_ports.size(); ++i)
    {
        std::string port_name = std::string ("out_") +
            boost::lexical_cast<std::string> (i);
        
        _out_ports [i] = jack_port_register (
            _client, port_name.c_str (), JACK_DEFAULT_AUDIO_TYPE,
            JackPortIsOutput, 0);
        
        if (_out_ports [i] == 0)
            throw jack_param_error ();
    }
    
    grd_client.dismiss ();
}
示例#6
0
bool JACKaudiooutputinit(Master *master_){
    jackmaster=master_;
    jackclient=0;
    char tmpstr[100];

    jackoutl=new REALTYPE [SOUND_BUFFER_SIZE];
    jackoutr=new REALTYPE [SOUND_BUFFER_SIZE];
    
    int rbbufsize=SOUND_BUFFER_SIZE*sizeof (REALTYPE)*2*2;
    printf("%d\n",rbbufsize);
    rb=jack_ringbuffer_create(rbbufsize);
    for (int i=0;i<rbbufsize;i++) rb->buf[i]=0.0;


    for (int i=0;i<15;i++){
	if (i!=0) snprintf(tmpstr,100,"ZynAddSubFX_%d",i);
	    else snprintf(tmpstr,100,"ZynAddSubFX");
	jackclient=jack_client_new(tmpstr);
	if (jackclient!=0) break;
    };

    if (jackclient==0) {
	fprintf(stderr,"\nERROR: Cannot make a jack client (possible reasons: JACK server is not running or jackd is launched by root and zynaddsubfx by another user.).\n\n\n");
	return(false);
    };

    fprintf(stderr,"Internal SampleRate   = %d\nJack Output SampleRate= %d\n",SAMPLE_RATE,jack_get_sample_rate(jackclient));
    if ((unsigned int)jack_get_sample_rate(jackclient)!=(unsigned int) SAMPLE_RATE) 
	fprintf(stderr,"It is recomanded that the both samplerates to be equal.\n");
    
    jack_set_process_callback(jackclient,jackprocess,0);    
    jack_set_sample_rate_callback(jackclient,jacksrate,0);    
    jack_on_shutdown(jackclient,jackshutdown,0);    
    
    outport_left=jack_port_register(jackclient,"out_1",
	JACK_DEFAULT_AUDIO_TYPE,JackPortIsOutput|JackPortIsTerminal,0);    
    outport_right=jack_port_register(jackclient,"out_2",
	JACK_DEFAULT_AUDIO_TYPE,JackPortIsOutput|JackPortIsTerminal,0);    

    if (jack_activate(jackclient)){
	fprintf(stderr,"Cannot activate jack client\n");
	return(false);
    };

    pthread_create(&bthr,NULL,thread_blocked,NULL);
    
    /*
    jack_connect(jackclient,jack_port_name(outport_left),"alsa_pcm:out_1");
    jack_connect(jackclient,jack_port_name(outport_right),"alsa_pcm:out_2");
     */
     
     return(true);
};
示例#7
0
static int
_jack_init(prog_t *handle, const char *id)
{
	jack_options_t opts = JackNullOption | JackNoStartServer;
	if(handle->server_name)
		opts |= JackServerName;
	if(handle->session_id)
		opts |= JackSessionID;

	jack_status_t status;
	if(!(handle->client = jack_client_open(id, opts, &status,
		handle->server_name ? handle->server_name : handle->session_id,
		handle->server_name ? handle->session_id : NULL)))
	{
		return -1;
	}

	//TODO check status

	// set client pretty name
#if defined(JACK_HAS_METADATA_API)
	jack_uuid_t uuid;
	const char *client_name = jack_get_client_name(handle->client);
	const char *uuid_str = jack_get_uuid_for_client_name(handle->client, client_name);
	if(uuid_str)
		jack_uuid_parse(uuid_str, &uuid);
	else
		jack_uuid_clear(&uuid);

	if(!jack_uuid_empty(uuid))
	{
		jack_set_property(handle->client, uuid,
			JACK_METADATA_PRETTY_NAME, "Synthpod", "text/plain");
	}
#endif

	// set client process callback
	if(jack_set_process_callback(handle->client, _process, handle))
		return -1;
	if(jack_set_session_callback(handle->client, _session, handle))
		return -1;
	if(jack_set_sample_rate_callback(handle->client, _sample_rate, handle))
		return -1;
	if(jack_set_buffer_size_callback(handle->client, _buffer_size, handle))
		return -1;
	jack_on_shutdown(handle->client, _shutdown, handle);
	jack_set_xrun_callback(handle->client, _xrun, handle);

	return 0;
}
示例#8
0
void gojack_generic_callback_sync_destroy(struct gojack_generic_callback_sync *sync) {
    jack_set_freewheel_callback(sync->client, NULL, NULL);
    jack_set_buffer_size_callback(sync->client, NULL, NULL);
    jack_set_sample_rate_callback(sync->client, NULL, NULL);
    jack_set_client_registration_callback(sync->client, NULL, NULL);
    jack_set_port_registration_callback(sync->client, NULL, NULL);
    jack_set_port_connect_callback(sync->client, NULL, NULL);
    jack_set_port_rename_callback(sync->client, NULL, NULL);
    jack_set_graph_order_callback(sync->client, NULL, NULL);
    jack_set_xrun_callback(sync->client, NULL, NULL);
    jack_set_latency_callback(sync->client, NULL, NULL);
    cgo_callback_sync_destroy(sync->base);
    pthread_mutex_destroy(&sync->lock);
    free(sync);
}
示例#9
0
bool SC_JackDriver::DriverSetup(int* outNumSamples, double* outSampleRate)
{
	char* clientName = 0;
	char* serverName = 0;

	if (mWorld->hw->mInDeviceName && (strlen(mWorld->hw->mInDeviceName) > 0)) {
		// parse string <serverName>:<clientName>
		SC_StringParser sp(mWorld->hw->mInDeviceName, ':');
		if (!sp.AtEnd()) serverName = strdup(sp.NextToken());
		if (!sp.AtEnd()) clientName = strdup(sp.NextToken());
		if (clientName == 0) {
			// no semicolon found
			clientName = serverName;
			serverName = 0;
		} else if (strlen(clientName) == 0) {
			free(clientName);
			clientName = 0;
		}
	}

	mClient = jack_client_open(
		clientName ? clientName : kJackDefaultClientName,
		serverName ? JackServerName : JackNullOption,
		NULL, serverName);
	if (serverName) free(serverName); if (clientName) free(clientName);
	if (mClient == 0) return false;

	scprintf("%s: client name is '%s'\n", kJackDriverIdent, jack_get_client_name(mClient));

	// create jack I/O ports
	mInputList = new SC_JackPortList(mClient, mWorld->mNumInputs, JackPortIsInput);
	mOutputList = new SC_JackPortList(mClient, mWorld->mNumOutputs, JackPortIsOutput);

	// register callbacks
	jack_set_process_callback(mClient, sc_jack_process_cb, this);
	jack_set_buffer_size_callback(mClient, sc_jack_bufsize_cb, this);
	jack_set_sample_rate_callback(mClient, sc_jack_srate_cb, this);
	jack_set_graph_order_callback(mClient, sc_jack_graph_order_cb, this);
	jack_set_xrun_callback(mClient, sc_jack_xrun_cb, this);
	jack_on_shutdown(mClient, sc_jack_shutdown_cb, mWorld);

	*outNumSamples = (int)jack_get_buffer_size(mClient);
	*outSampleRate = (double)jack_get_sample_rate(mClient);

	return true;
}
示例#10
0
文件: main.c 项目: shdawson/setBfree
int open_jack(void) {
  int i;
  j_client = jack_client_open (jack_client_name, JackNullOption, NULL);

  if (!j_client) {
    fprintf(stderr, "could not connect to jack.\n");
    return(1);
  }

  jack_on_shutdown (j_client, jack_shutdown_callback, NULL);
  jack_set_process_callback(j_client,jack_audio_callback, &inst);
  jack_set_sample_rate_callback (j_client, jack_srate_callback, NULL);

  j_output_port = (jack_port_t**) calloc(AUDIO_CHANNELS,sizeof(jack_port_t*));
  j_output_bufferptrs = (jack_default_audio_sample_t**) calloc(AUDIO_CHANNELS,sizeof(jack_default_audio_sample_t*));

  for (i=0;i<AUDIO_CHANNELS;i++) {
#if 0
    char channelid[16];
    snprintf(channelid,16,"output-%i",i);
#else
    const char *channelid = portnames[i];
#endif
    j_output_port[i] = jack_port_register (j_client, channelid, JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
    if (!j_output_port[i]) {
      fprintf(stderr, "no more jack ports available.\n");
      jack_client_close (j_client);
      return(1);
    }
  }

  if (use_jack_midi) { // use JACK-midi
    jack_midi_port = jack_port_register(j_client, midiport, JACK_DEFAULT_MIDI_TYPE, JackPortIsInput , 0);
    if (jack_midi_port == NULL) {
      fprintf(stderr, "can't register jack-midi-port\n");
	jack_client_close (j_client);
	return(1);
    }
  }


  jack_srate_callback(jack_get_sample_rate(j_client),NULL); // force geting samplerate

  return jack_activate(j_client);
}
示例#11
0
//--------------------------------------------------------------
void
ofxJackClient::setup(std::string _name)
{
	jack_status_t jack_status;

  if (!_name.empty())
      name = _name;
  
	if ((clientImpl = jack_client_open(name.c_str(), JackNullOption, &jack_status)) != NULL)
  {
    jack_set_process_callback(clientImpl, _onJackProcess, this);
    jack_set_buffer_size_callback(clientImpl, _onJackBufferSizeChanged, this);
    jack_set_sample_rate_callback(clientImpl, _onJackSampleRateChanged, this);
    jack_on_shutdown(clientImpl, _onJackShutdown, this);
  }
  else
    std::cerr << name << ":: jack server not running?" << std::endl;
}
示例#12
0
int main (int argc, char *argv[])
{
    static const char jack_client_name[] = "simulator";
    jack_status_t jack_status;


    glutInit(&argc, argv);

    glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_ALPHA | GLUT_DEPTH);
    glutInitWindowSize(640, 640);
    glutInitWindowPosition(0, 0);

    window = glutCreateWindow("OpenLase Simulator");

    glutDisplayFunc(&draw_gl);
    glutIdleFunc(&draw_gl);
    glutReshapeFunc(&resize_gl);
    glutKeyboardFunc(&key_gl);
    init_gl(640, 640);

    if ((client = jack_client_open(jack_client_name, JackNullOption, &jack_status)) == 0) {
        fprintf (stderr, "jack server not running?\n");
        return 1;
    }

    jack_set_process_callback (client, process, 0);
    jack_set_buffer_size_callback (client, bufsize, 0);
    jack_set_sample_rate_callback (client, srate, 0);
    jack_on_shutdown (client, jack_shutdown, 0);

    in_x = jack_port_register (client, "in_x", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
    in_y = jack_port_register (client, "in_y", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
    in_r = jack_port_register (client, "in_r", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
    in_g = jack_port_register (client, "in_g", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
    in_b = jack_port_register (client, "in_b", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);

    if (jack_activate (client)) {
        fprintf (stderr, "cannot activate client");
        return 1;
    }

    glutMainLoop();
    return 0;
}
示例#13
0
int main (int argc, char *argv[])
{
	int retval;
	jack_client_t *client;

	QApplication app(argc, argv);
	OutputSettings settings;
	
	cfg = &settings.cfg;

	if ((client = jack_client_new ("output")) == 0) {
		fprintf (stderr, "jack server not running?\n");
		return 1;
	}

	jack_set_process_callback (client, process, 0);
	jack_set_buffer_size_callback (client, bufsize, 0);
	jack_set_sample_rate_callback (client, srate, 0);
	jack_on_shutdown (client, jack_shutdown, 0);

	in_x = jack_port_register (client, "in_x", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	in_y = jack_port_register (client, "in_y", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	in_g = jack_port_register (client, "in_g", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	out_x = jack_port_register (client, "out_x", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
	out_y = jack_port_register (client, "out_y", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
	out_g = jack_port_register (client, "out_g", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
	out_e = jack_port_register (client, "out_e", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);

	if (jack_activate (client)) {
		fprintf (stderr, "cannot activate client");
		return 1;
	}

	settings.show();

	retval = app.exec();

	jack_client_close (client);
	return retval;
}
示例#14
0
文件: main.c 项目: dbkaplun/mictomidi
void jack_start() {
	jack_set_error_function(error);

	client = jack_client_open("MicToMIDI", JackNullOption, NULL);
	if (client == 0) {
		fprintf(stderr, "jack server not running?\n");
		exit(1);
	}

	jack_set_process_callback(client, process, 0);
	jack_set_sample_rate_callback(client, sample_rate, 0);
	jack_on_shutdown(client, jack_shutdown, 0);

	input_port = jack_port_register(client, "input", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	output_port = jack_port_register(client, "output", JACK_DEFAULT_MIDI_TYPE, JackPortIsOutput, 0);

	if(jack_activate(client)) {
		fprintf(stderr, "cannot activate client");
		exit(1);
	}
	atexit(jack_stop);

	const char **ports;
	if((ports = jack_get_ports(client, NULL, NULL, JackPortIsPhysical | JackPortIsOutput)) == NULL)
	{
		fprintf(stderr, "cannot find any physical capture ports\n");
		exit(1);
	}
	if(jack_connect(client, ports[0], jack_port_name(input_port)))
		fprintf(stderr, "cannot connect to physical capture port\n");

	jack_free(ports);
	if((ports = jack_get_ports(client, NULL, "midi", JackPortIsInput)) == NULL)
	{
		fprintf(stderr, "cannot find any MIDI playback ports\n");
		exit(1);
	}
	if(jack_connect(client, jack_port_name(output_port), ports[0]))
		fprintf(stderr, "cannot connect to MIDI playback port\n");
}
示例#15
0
文件: audio_jack.cpp 项目: K0F/FreeJ
bool JackClient::Attach(const std::string &ClientName) {
    if(m_Attached) return true;

    /* jack_client_new is now deprecated (Oct 2010)
       m_Client = jack_client_new(ClientName.c_str());

       if (!m_Client)
       {
       error("jack server not running? client_new returns %p", m_Client);
       return false;
       } */
    m_Client =
        jack_client_open(ClientName.c_str(),
                         (jack_options_t)(JackNullOption | JackNoStartServer), NULL);
    if(!m_Client) {
        error("jack server not running?", m_Client);
        return false;
    }

    jack_set_process_callback(m_Client, JackClient::Process, this);
    jack_set_sample_rate_callback(m_Client, JackClient::OnSRateChange, 0);
    jack_on_shutdown(m_Client, JackClient::OnJackShutdown, this);

    m_InputPortMap.clear();
    m_OutputPortMap.clear();

    // tell the JACK server that we are ready to roll
    if(jack_activate(m_Client)) {
        error("cannot activate client");
        return false;
    }

    m_Attached = true;

    audio_mix_ring = ringbuffer_create(4096 * 512 * 4);         //1024 not enought, must be the same size_t
    // as buf_fred set up in OggTheoraEncoder::init
    first = ringbuffer_create(4096 * 512 * 4);  //first jack Input ring buffer
    return true;
}
示例#16
0
int main(int narg, char **args)
{
	if ((client = jack_client_open("midisine", JackNullOption, NULL)) == 0)
	{
		fprintf(stderr, "JACK server not running?\n");
		return 1;
	}

	calc_note_frqs(jack_get_sample_rate (client));

	jack_set_process_callback (client, process, 0);

	jack_set_sample_rate_callback (client, srate, 0);

	jack_on_shutdown (client, jack_shutdown, 0);

	input_port = jack_port_register (client, "midi_in", JACK_DEFAULT_MIDI_TYPE, JackPortIsInput, 0);
	output_port = jack_port_register (client, "audio_out", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);

	if (jack_activate (client))
	{
		fprintf(stderr, "cannot activate client");
		return 1;
	}

    /* install a signal handler to properly quits jack client */
    signal(SIGQUIT, signal_handler);
	signal(SIGTERM, signal_handler);
	signal(SIGHUP, signal_handler);
	signal(SIGINT, signal_handler);

	/* run until interrupted */
	while(1) {
		sleep(1);
	}
	jack_client_close(client);
	exit (0);
}
示例#17
0
文件: Client.C 项目: 0mk/non
/** Connect to JACK using client name /client_name/. Return a static
 * pointer to actual name as reported by JACK */
    const char *
    Client::init ( const char *client_name, unsigned int opts )
    {
        if (( _client = jack_client_open ( client_name, (jack_options_t)0, NULL )) == 0 )
            return NULL;

#define set_callback( name ) jack_set_ ## name ## _callback( _client, &Client:: name , this )

        set_callback( thread_init );
        set_callback( process );
        set_callback( xrun );
        set_callback( freewheel );
        set_callback( buffer_size );
        set_callback( port_connect );

        jack_set_sample_rate_callback( _client, &Client::sample_rate_changed, this );
  
#ifdef HAVE_JACK_PORT_GET_LATENCY_RANGE
        set_callback( latency );
#endif

        /* FIXME: should we wait to register this until after the project
           has been loaded (and we have disk threads running)? */
        if ( opts & SLOW_SYNC )
            set_callback( sync );

        if ( opts & TIMEBASE_MASTER )
            jack_set_timebase_callback( _client, 0, &Client::timebase, this );

        jack_on_shutdown( _client, &Client::shutdown, this );

        activate();

//        _sample_rate = frame_rate();

        return jack_get_client_name( _client );
    }
int JackAudioDriver::init( unsigned bufferSize )
{
	// Destination ports the output of Hydrogen will be connected
	// to.
	Preferences* pPref = Preferences::get_instance();
	output_port_name_1 = pPref->m_sJackPortName1;
	output_port_name_2 = pPref->m_sJackPortName2;

	QString sClientName = "Hydrogen";

#ifdef H2CORE_HAVE_OSC
	QString sNsmClientId = pPref->getNsmClientId();

	if(!sNsmClientId.isEmpty()){
		sClientName = sNsmClientId;
	}
#endif

	// The address of the status object will be used by JACK to
	// return information from the open operation.
	jack_status_t status;
	// Sometimes jackd doesn't stop and start fast enough.
	int nTries = 2;
	while ( nTries > 0 ) {
		--nTries;

		// Open an external client session with the JACK
		// server.  The `jack_client_open' function is defined
		// in the jack/jack.h header. With it, clients may
		// choose which of several servers to connect, and
		// control whether and how to start the server
		// automatically, if it was not already running. Its
		// first argument _client_name_ of is at most
		// jack_client_name_size() characters. The name scope
		// is local to each server. Unless forbidden by the
		// JackUseExactName option, the server will modify
		// this name to create a unique variant, if
		// needed. The second argument _options_ is formed by
		// OR-ing together JackOptions bits. Only the
		// JackOpenOptions bits are allowed. _status_ (if
		// non-NULL) is an address for JACK to return
		// information from the open operation. This status
		// word is formed by OR-ing together the relevant
		// JackStatus bits.  Depending on the _status_, an
		// optional argument _server_name_ selects from among
		// several possible concurrent server
		// instances. Server names are unique to each user. It
		// returns an opaque client handle if successful. If
		// this is NULL, the open operation failed, *status
		// includes JackFailure and the caller is not a JACK
		// client.
#ifdef H2CORE_HAVE_JACKSESSION
		if (pPref->getJackSessionUUID().isEmpty()){
			m_pClient = jack_client_open( sClientName.toLocal8Bit(),
						      JackNullOption,
						      &status);
		} else {
			// Unique name of the JACK server used within
			// the JACK session.
			const QByteArray uuid = pPref->getJackSessionUUID().toLocal8Bit();
			// Using the JackSessionID option and the
			// supplied SessionID Token the sessionmanager
			// is able to identify the client again.
			m_pClient = jack_client_open( sClientName.toLocal8Bit(),
						      JackSessionID,
						      &status,
						      uuid.constData());
		}
#else
		m_pClient = jack_client_open( sClientName.toLocal8Bit(),
					      JackNullOption,
					      &status);
#endif
		// Check what did happen during the opening of the
		// client. CLIENT_SUCCESS sets the nTries variable
		// to 0 while CLIENT_FAILURE resets m_pClient to the
		// nullptr.
		switch(status) {
		case JackFailure:
			CLIENT_FAILURE("unknown error");
			break;
		case JackInvalidOption:
			CLIENT_FAILURE("invalid option");
			break;
		case JackNameNotUnique:
			if (m_pClient) {
				sClientName = jack_get_client_name(m_pClient);
				CLIENT_SUCCESS(QString("Jack assigned the client name '%1'").arg(sClientName));
			} else {
				CLIENT_FAILURE("name not unique");
			}
			break;
		case JackServerStarted:
			CLIENT_SUCCESS("JACK Server started for Hydrogen.");
			break;
		case JackServerFailed:
			CLIENT_FAILURE("unable to connect");
			break;
		case JackServerError:
			CLIENT_FAILURE("communication error");
			break;
		case JackNoSuchClient:
			CLIENT_FAILURE("unknown client type");
			break;
		case JackLoadFailure:
			CLIENT_FAILURE("can't load internal client");
			break;
		case JackInitFailure:
			CLIENT_FAILURE("can't initialize client");
			break;
		case JackShmFailure:
			CLIENT_FAILURE("unable to access shared memory");
			break;
		case JackVersionError:
			CLIENT_FAILURE("client/server protocol version mismatch");
			break;
		default:
			if (status) {
				ERRORLOG("Unknown status with JACK server.");
				if (m_pClient) {
					CLIENT_SUCCESS("Client pointer is *not* null..."
						       " assuming we're OK");
				}
			} else {
				CLIENT_SUCCESS("Connected to JACK server");
			}
		}
	}

	if (m_pClient == 0) return -1;

	// Here, client should either be valid, or NULL.
	jack_server_sampleRate = jack_get_sample_rate( m_pClient );
	jack_server_bufferSize = jack_get_buffer_size( m_pClient );

	pPref->m_nSampleRate = jack_server_sampleRate;
	pPref->m_nBufferSize = jack_server_bufferSize;

	/* tell the JACK server to call `process()' whenever
	   there is work to be done.
	*/
	jack_set_process_callback( m_pClient, this->processCallback, 0 );

	/* tell the JACK server to call `srate()' whenever
	   the sample rate of the system changes.
	*/
	jack_set_sample_rate_callback( m_pClient, jackDriverSampleRate, this );

	/* tell JACK server to update us if the buffer size
	   (frames per process cycle) changes.
	*/
	jack_set_buffer_size_callback( m_pClient, jackDriverBufferSize, 0 );

	/* tell the JACK server to call `jack_shutdown()' if
	   it ever shuts down, either entirely, or if it
	   just decides to stop calling us.
	*/
	jack_on_shutdown( m_pClient, jackDriverShutdown, 0 );

	// Create two new ports for Hydrogen's client. These are
	// objects used for moving data of any type in or out of the
	// client. Ports may be connected in various ways. The
	// function `jack_port_register' (jack/jack.h) is called like
	// jack_port_register( jack_client_t *client, 
	//                     const char *port_name,
        //                     const char *port_type,
        //                     unsigned long flags,
        //                     unsigned long buffer_size)
	//
	// All ports have a type, which may be any non-NULL and non-zero
	// length string, passed as an argument. Some port types are built
	// into the JACK API, currently only JACK_DEFAULT_AUDIO_TYPE.
	// It returns a _jack_port_t_ pointer on success, otherwise NULL.
	output_port_1 = jack_port_register( m_pClient, "out_L", JACK_DEFAULT_AUDIO_TYPE,
					    JackPortIsOutput, 0 );
	output_port_2 = jack_port_register( m_pClient, "out_R", JACK_DEFAULT_AUDIO_TYPE,
					    JackPortIsOutput, 0 );

	Hydrogen *pEngine = Hydrogen::get_instance();
	if ( ( output_port_1 == NULL ) || ( output_port_2 == NULL ) ) {
		pEngine->raiseError( Hydrogen::JACK_ERROR_IN_PORT_REGISTER );
		return 4;
	}

#ifdef H2CORE_HAVE_LASH
	if ( pPref->useLash() ){
		LashClient* lashClient = LashClient::get_instance();
		if (lashClient->isConnected()) {
			lashClient->setJackClientName(sClientName.toLocal8Bit().constData());
		}
	}
#endif

#ifdef H2CORE_HAVE_JACKSESSION
	jack_set_session_callback(m_pClient, jack_session_callback, (void*)this);
#endif

	if ( pPref->m_bJackMasterMode == Preferences::USE_JACK_TIME_MASTER ){
		// Make Hydrogen the timebase master, regardless if there
		// is already a timebase master present.
		m_nJackConditionalTakeOver = 0;
		// Make Hydrogen the JACK timebase master.
		initTimeMaster();
	}
	
	return 0;
}
/* make a connection with @id and @server. Returns NULL on failure with the
 * status set. */
static GstJackAudioConnection *
gst_jack_audio_make_connection (const gchar * id, const gchar * server,
    jack_client_t * jclient, jack_status_t * status)
{
  GstJackAudioConnection *conn;
  jack_options_t options;
  gint res;

  *status = 0;

  GST_DEBUG ("new client %s, connecting to server %s", id,
      GST_STR_NULL (server));

  /* never start a server */
  options = JackNoStartServer;
  /* if we have a servername, use it */
  if (server != NULL)
    options |= JackServerName;
  /* open the client */
  if (jclient == NULL)
    jclient = jack_client_open (id, options, status, server);
  if (jclient == NULL)
    goto could_not_open;

  /* now create object */
  conn = g_new (GstJackAudioConnection, 1);
  conn->refcount = 1;
  g_mutex_init (&conn->lock);
  g_cond_init (&conn->flush_cond);
  conn->id = g_strdup (id);
  conn->server = g_strdup (server);
  conn->client = jclient;
  conn->n_clients = 0;
  conn->src_clients = NULL;
  conn->sink_clients = NULL;
  conn->cur_ts = -1;
  conn->transport_state = GST_STATE_VOID_PENDING;

  /* set our callbacks  */
  jack_set_process_callback (jclient, jack_process_cb, conn);
  /* these callbacks cause us to error */
  jack_set_buffer_size_callback (jclient, jack_buffer_size_cb, conn);
  jack_set_sample_rate_callback (jclient, jack_sample_rate_cb, conn);
  jack_on_shutdown (jclient, jack_shutdown_cb, conn);

  /* all callbacks are set, activate the client */
  GST_INFO ("activate jack_client %p", jclient);
  if ((res = jack_activate (jclient)))
    goto could_not_activate;

  GST_DEBUG ("opened connection %p", conn);

  return conn;

  /* ERRORS */
could_not_open:
  {
    GST_DEBUG ("failed to open jack client, %d", *status);
    return NULL;
  }
could_not_activate:
  {
    GST_ERROR ("Could not activate client (%d)", res);
    *status = JackFailure;
    g_mutex_clear (&conn->lock);
    g_free (conn->id);
    g_free (conn->server);
    g_free (conn);
    return NULL;
  }
}
示例#20
0
    /*
        JackProxyDriver is wrapped in a JackWaitCallbackDriver decorator that behaves
        as a "dummy driver, until Initialize method returns.
    */
    bool JackProxyDriver::Initialize()
    {
        jack_log("JackProxyDriver::Initialize");

        // save existing local connections if needed
        if (fAutoSave) {
            SaveConnections(0);
        }

        // new loading, but existing client, restart the driver
        if (fClient) {
            jack_info("JackProxyDriver restarting...");
            jack_client_close(fClient);
        }
        FreePorts();

        // display some additional infos
        jack_info("JackProxyDriver started in %s mode.",
                    (fEngineControl->fSyncMode) ? "sync" : "async");

        do {
            jack_status_t status;
            char *old = NULL;

            if (fPromiscuous) {
                // as we are fiddling with the environment variable content, save it
                const char* tmp = getenv("JACK_PROMISCUOUS_SERVER");
                if (tmp) {
                    old = strdup(tmp);
                }
                // temporary enable promiscuous mode
                if (setenv("JACK_PROMISCUOUS_SERVER", fPromiscuous, 1) < 0) {
                    free(old);
                    jack_error("Error allocating memory.");
                    return false;
                }
            }

            jack_info("JackProxyDriver connecting to %s", fUpstream);
            fClient = jack_client_open(fClientName, static_cast<jack_options_t>(JackNoStartServer|JackServerName), &status, fUpstream);

            if (fPromiscuous) {
                // restore previous environment variable content
                if (old) {
                    if (setenv("JACK_PROMISCUOUS_SERVER", old, 1) < 0) {
                        free(old);
                        jack_error("Error allocating memory.");
                        return false;
                    }
                    free(old);
                } else {
                    unsetenv("JACK_PROMISCUOUS_SERVER");
                }
            }

            // the connection failed, try again later
            if (!fClient) {
                JackSleep(1000000);
            }

        } while (!fClient);
        jack_info("JackProxyDriver connected to %s", fUpstream);

        // we are connected, let's register some callbacks

        jack_on_shutdown(fClient, shutdown_callback, this);

        if (jack_set_process_callback(fClient, process_callback, this) != 0) {
            jack_error("Cannot set process callback.");
            return false;
        }

        if (jack_set_buffer_size_callback(fClient, bufsize_callback, this) != 0) {
            jack_error("Cannot set buffer size callback.");
            return false;
        }

        if (jack_set_sample_rate_callback(fClient, srate_callback, this) != 0) {
            jack_error("Cannot set sample rate callback.");
            return false;
        }

        if (jack_set_port_connect_callback(fClient, connect_callback, this) != 0) {
            jack_error("Cannot set port connect callback.");
            return false;
        }

        // detect upstream physical playback ports if needed
        if (fDetectPlaybackChannels) {
            fPlaybackChannels = CountIO(JACK_DEFAULT_AUDIO_TYPE, JackPortIsPhysical | JackPortIsOutput);
        }

        // detect upstream physical capture ports if needed
        if (fDetectCaptureChannels) {
            fCaptureChannels = CountIO(JACK_DEFAULT_AUDIO_TYPE, JackPortIsPhysical | JackPortIsInput);
        }

        if (AllocPorts() != 0) {
            jack_error("Can't allocate ports.");
            return false;
        }

        bufsize_callback(jack_get_buffer_size(fClient));
        srate_callback(jack_get_sample_rate(fClient));

        // restore local connections if needed
        if (fAutoSave) {
            LoadConnections(0);
        }

        // everything is ready, start upstream processing
        if (jack_activate(fClient) != 0) {
            jack_error("Cannot activate jack client.");
            return false;
        }

        // connect upstream ports if needed
        if (fAutoConnect) {
            ConnectPorts();
        }

        return true;
    }
示例#21
0
JackAudioSystem::JackAudioSystem()
	: bActive(false)
	, client(NULL)
	, in_port(NULL)
	, output_buffer(NULL)
	, iBufferSize(0)
	, bJackIsGood(false)
	, bInputIsGood(false)
	, bOutputIsGood(false)
	, iSampleRate(0)
{
	if (g.s.qsJackAudioOutput.isEmpty()) {
		iOutPorts = 1;
	} else {
		iOutPorts = g.s.qsJackAudioOutput.toInt();
	}
	memset(reinterpret_cast<void *>(&out_ports), 0, sizeof(out_ports));

	qhInput.insert(QString(), tr("Hardware Ports"));
	qhOutput.insert(QString::number(1), tr("Mono"));
	qhOutput.insert(QString::number(2), tr("Stereo"));

	jack_status_t status = static_cast<jack_status_t>(0);
	int err = 0;

	jack_options_t jack_option = g.s.bJackStartServer ? JackNullOption : JackNoStartServer;
	client = jack_client_open(g.s.qsJackClientName.toStdString().c_str(), jack_option, &status);

	if (!client) {
		QStringList errors = jackStatusToStringList(status);
		qWarning("JackAudioSystem: unable to open client due to %i errors:", errors.count());
		for (int i = 0; i < errors.count(); ++i) {
			qWarning("JackAudioSystem: %s", qPrintable(errors.at(i)));
		}

		return;
	}

	qWarning("JackAudioSystem: client \"%s\" opened successfully", jack_get_client_name(client));
	iBufferSize = jack_get_buffer_size(client);
	iSampleRate = jack_get_sample_rate(client);

	err = jack_set_process_callback(client, process_callback, this);
	if (err != 0) {
		qWarning("JackAudioSystem: unable to set process callback - jack_set_process_callback() returned %i", err);
		return;
	}

	err = jack_set_sample_rate_callback(client, srate_callback, this);
	if (err != 0) {
		qWarning("JackAudioSystem: unable to set sample rate callback - jack_set_sample_rate_callback() returned %i", err);
		return;
	}

	err = jack_set_buffer_size_callback(client, buffer_size_callback, this);
	if (err != 0) {
		qWarning("JackAudioSystem: unable to set buffer size callback - jack_set_buffer_size_callback() returned %i", err);
		return;
	}

	jack_on_shutdown(client, shutdown_callback, this);

	// If we made it this far, then everything is okay
	bJackIsGood = true;
}
示例#22
0
static int instream_open_jack(struct SoundIoPrivate *si, struct SoundIoInStreamPrivate *is) {
    SoundIoInStream *instream = &is->pub;
    SoundIoInStreamJack *isj = &is->backend_data.jack;
    SoundIoJack *sij = &si->backend_data.jack;
    SoundIoDevice *device = instream->device;
    SoundIoDevicePrivate *dev = (SoundIoDevicePrivate *)device;
    SoundIoDeviceJack *dj = &dev->backend_data.jack;

    if (sij->is_shutdown)
        return SoundIoErrorBackendDisconnected;

    if (!instream->name)
        instream->name = "SoundIoInStream";

    instream->software_latency = device->software_latency_current;
    isj->period_size = sij->period_size;

    jack_status_t status;
    isj->client = jack_client_open(instream->name, JackNoStartServer, &status);
    if (!isj->client) {
        instream_destroy_jack(si, is);
        assert(!(status & JackInvalidOption));
        if (status & JackShmFailure)
            return SoundIoErrorSystemResources;
        if (status & JackNoSuchClient)
            return SoundIoErrorNoSuchClient;
        return SoundIoErrorOpeningDevice;
    }

    int err;
    if ((err = jack_set_process_callback(isj->client, instream_process_callback, is))) {
        instream_destroy_jack(si, is);
        return SoundIoErrorOpeningDevice;
    }
    if ((err = jack_set_buffer_size_callback(isj->client, instream_buffer_size_callback, is))) {
        instream_destroy_jack(si, is);
        return SoundIoErrorOpeningDevice;
    }
    if ((err = jack_set_sample_rate_callback(isj->client, instream_sample_rate_callback, is))) {
        instream_destroy_jack(si, is);
        return SoundIoErrorOpeningDevice;
    }
    if ((err = jack_set_xrun_callback(isj->client, instream_xrun_callback, is))) {
        instream_destroy_jack(si, is);
        return SoundIoErrorOpeningDevice;
    }
    jack_on_shutdown(isj->client, instream_shutdown_callback, is);

    jack_nframes_t max_port_latency = 0;

    // register ports and map channels
    int connected_count = 0;
    for (int ch = 0; ch < instream->layout.channel_count; ch += 1) {
        SoundIoChannelId my_channel_id = instream->layout.channels[ch];
        const char *channel_name = soundio_get_channel_name(my_channel_id);
        unsigned long flags = JackPortIsInput;
        if (!instream->non_terminal_hint)
            flags |= JackPortIsTerminal;
        jack_port_t *jport = jack_port_register(isj->client, channel_name, JACK_DEFAULT_AUDIO_TYPE, flags, 0);
        if (!jport) {
            instream_destroy_jack(si, is);
            return SoundIoErrorOpeningDevice;
        }
        SoundIoInStreamJackPort *isjp = &isj->ports[ch];
        isjp->dest_port = jport;
        // figure out which source port this connects to
        SoundIoDeviceJackPort *djp = find_port_matching_channel(device, my_channel_id);
        if (djp) {
            isjp->source_port_name = djp->full_name;
            isjp->source_port_name_len = djp->full_name_len;
            connected_count += 1;
            max_port_latency = max(max_port_latency, djp->latency_range.max);
        }
    }
    // If nothing got connected, channel layouts aren't working. Just send the
    // data in the order of the ports.
    if (connected_count == 0) {
        max_port_latency = 0;
        instream->layout_error = SoundIoErrorIncompatibleDevice;

        int ch_count = min(instream->layout.channel_count, dj->port_count);
        for (int ch = 0; ch < ch_count; ch += 1) {
            SoundIoInStreamJackPort *isjp = &isj->ports[ch];
            SoundIoDeviceJackPort *djp = &dj->ports[ch];
            isjp->source_port_name = djp->full_name;
            isjp->source_port_name_len = djp->full_name_len;
            max_port_latency = max(max_port_latency, djp->latency_range.max);
        }
    }

    isj->hardware_latency = max_port_latency / (double)instream->sample_rate;

    return 0;
}
示例#23
0
int soundio_jack_init(struct SoundIoPrivate *si) {
    SoundIoJack *sij = &si->backend_data.jack;
    SoundIo *soundio = &si->pub;

    if (!global_msg_callback_flag.test_and_set()) {
        if (soundio->jack_error_callback)
            jack_set_error_function(soundio->jack_error_callback);
        if (soundio->jack_info_callback)
            jack_set_info_function(soundio->jack_info_callback);
        global_msg_callback_flag.clear();
    }

    sij->mutex = soundio_os_mutex_create();
    if (!sij->mutex) {
        destroy_jack(si);
        return SoundIoErrorNoMem;
    }

    sij->cond = soundio_os_cond_create();
    if (!sij->cond) {
        destroy_jack(si);
        return SoundIoErrorNoMem;
    }

    // We pass JackNoStartServer due to
    // https://github.com/jackaudio/jack2/issues/138
    jack_status_t status;
    sij->client = jack_client_open(soundio->app_name, JackNoStartServer, &status);
    if (!sij->client) {
        destroy_jack(si);
        assert(!(status & JackInvalidOption));
        if (status & JackShmFailure)
            return SoundIoErrorSystemResources;
        if (status & JackNoSuchClient)
            return SoundIoErrorNoSuchClient;

        return SoundIoErrorInitAudioBackend;
    }

    int err;
    if ((err = jack_set_buffer_size_callback(sij->client, buffer_size_callback, si))) {
        destroy_jack(si);
        return SoundIoErrorInitAudioBackend;
    }
    if ((err = jack_set_sample_rate_callback(sij->client, sample_rate_callback, si))) {
        destroy_jack(si);
        return SoundIoErrorInitAudioBackend;
    }
    if ((err = jack_set_port_registration_callback(sij->client, port_registration_callback, si))) {
        destroy_jack(si);
        return SoundIoErrorInitAudioBackend;
    }
    if ((err = jack_set_port_rename_callback(sij->client, port_rename_calllback, si))) {
        destroy_jack(si);
        return SoundIoErrorInitAudioBackend;
    }
    jack_on_shutdown(sij->client, shutdown_callback, si);

    sij->refresh_devices_flag.clear();
    sij->period_size = jack_get_buffer_size(sij->client);
    sij->sample_rate = jack_get_sample_rate(sij->client);

    if ((err = jack_activate(sij->client))) {
        destroy_jack(si);
        return SoundIoErrorInitAudioBackend;
    }

    if ((err = refresh_devices(si))) {
        destroy_jack(si);
        return err;
    }

    si->destroy = destroy_jack;
    si->flush_events = flush_events_jack;
    si->wait_events = wait_events_jack;
    si->wakeup = wakeup_jack;
    si->force_device_scan = force_device_scan_jack;

    si->outstream_open = outstream_open_jack;
    si->outstream_destroy = outstream_destroy_jack;
    si->outstream_start = outstream_start_jack;
    si->outstream_begin_write = outstream_begin_write_jack;
    si->outstream_end_write = outstream_end_write_jack;
    si->outstream_clear_buffer = outstream_clear_buffer_jack;
    si->outstream_pause = outstream_pause_jack;
    si->outstream_get_latency = outstream_get_latency_jack;

    si->instream_open = instream_open_jack;
    si->instream_destroy = instream_destroy_jack;
    si->instream_start = instream_start_jack;
    si->instream_begin_read = instream_begin_read_jack;
    si->instream_end_read = instream_end_read_jack;
    si->instream_pause = instream_pause_jack;
    si->instream_get_latency = instream_get_latency_jack;

    return 0;
}
示例#24
0
void JACKInput::Init() {

	m_message_queue.Reset(RING_BUFFER_SIZE * m_channels * sizeof(float));

	m_jack_client = jack_client_open("SimpleScreenRecorder", JackNoStartServer, NULL);
	if(m_jack_client == NULL) {
		Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not connect to JACK!"));
		throw JACKException();
	}

	m_jack_ports.resize(m_channels, NULL);
	for(unsigned int i = 0; i < m_channels; ++i) {
		std::string port_name = "in_" + NumToString(i + 1);
		m_jack_ports[i] = jack_port_register(m_jack_client, port_name.c_str(), JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
		if(m_jack_ports[i] == NULL) {
			Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not create JACK port!"));
			throw JACKException();
		}
	}

	if(jack_set_process_callback(m_jack_client, ProcessCallback, this) != 0) {
		Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not set JACK process callback!"));
		throw JACKException();
	}
	if(jack_set_sample_rate_callback(m_jack_client, SampleRateCallback, this) != 0) {
		Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not set JACK sample rate callback!"));
		throw JACKException();
	}
	if(jack_set_xrun_callback(m_jack_client, XRunCallback, this) != 0) {
		Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not set JACK xrun callback!"));
		throw JACKException();
	}
	if(jack_set_port_connect_callback(m_jack_client, PortConnectCallback, this) != 0) {
		Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not set JACK port connect callback!"));
		throw JACKException();
	}

	if(jack_activate(m_jack_client) != 0) {
		Logger::LogError("[JACKInput::Init] " + Logger::tr("Error: Could not activate JACK client!"));
		throw JACKException();
	}

	for(unsigned int i = 0; i < m_channels; ++i) {
		std::string port_name_full = std::string(jack_get_client_name(m_jack_client)) + ":in_" + NumToString(i + 1);
		if(m_connect_system_capture) {
			std::string capture_name = "system:capture_" + NumToString(i + 1);
			Logger::LogInfo("[JACKInput::Init] " + Logger::tr("Connecting port %1 to %2.")
							.arg(QString::fromStdString(capture_name)).arg(QString::fromStdString(port_name_full)));
			jack_connect(m_jack_client, capture_name.c_str(), port_name_full.c_str());
		}
		if(m_connect_system_playback) {
			std::string playback_name = "system:playback_" + NumToString(i + 1);
			jack_port_t *port = jack_port_by_name(m_jack_client, playback_name.c_str());
			if(port != NULL) {
				const char **connected_ports = jack_port_get_all_connections(m_jack_client, port);
				if(connected_ports != NULL) {
					for(const char **p = connected_ports; *p != NULL; ++p) {
						Logger::LogInfo("[JACKInput::Init] " + Logger::tr("Connecting port %1 to %2.")
										.arg(*p).arg(QString::fromStdString(port_name_full)));
						jack_connect(m_jack_client, *p, port_name_full.c_str());
					}
					jack_free(connected_ports);
				}
			}
		}

	}

	// start input thread
	m_should_stop = false;
	m_error_occurred = false;
	m_thread = std::thread(&JACKInput::InputThread, this);

}
示例#25
0
文件: jack.c 项目: k4rtik/ultragrid
static void * audio_play_jack_init(const char *cfg)
{
        struct state_jack_playback *s;
        const char **ports;
        jack_status_t status;

        if(!cfg || strcmp(cfg, "help") == 0) {
                audio_play_jack_help("jack");
                return &audio_init_state_ok;
        }

        s = calloc(1, sizeof(struct state_jack_playback));
        if(!s) {
                fprintf(stderr, "[JACK playback] Unable to allocate memory.\n");
                goto error;
        }

        s->jack_ports_pattern = strdup(cfg);

        s->client = jack_client_open(PACKAGE_STRING, JackNullOption, &status);
        if(status & JackFailure) {
                fprintf(stderr, "[JACK playback] Opening JACK client failed.\n");
                goto error;
        }

        if(jack_set_sample_rate_callback(s->client, jack_samplerate_changed_callback, (void *) s)) {
                fprintf(stderr, "[JACK capture] Registering callback problem.\n");
                goto release_client;
        }


        if(jack_set_process_callback(s->client, jack_process_callback, (void *) s) != 0) {
                fprintf(stderr, "[JACK capture] Process callback registration problem.\n");
                goto release_client;
        }

        s->jack_sample_rate = jack_get_sample_rate (s->client);
	fprintf(stderr, "JACK sample rate: %d\n", (int) s->jack_sample_rate);


        ports = jack_get_ports(s->client, cfg, NULL, JackPortIsInput);
        if(ports == NULL) {
                fprintf(stderr, "[JACK playback] Unable to input ports matching %s.\n", cfg);
                goto release_client;
        }

        s->jack_ports_count = 0;
        while(ports[s->jack_ports_count]) s->jack_ports_count++;
        free(ports);

        {
                char name[30];
                int i;
                
                for(i = 0; i < MAX_PORTS; ++i) {
                        snprintf(name, 30, "playback_%02u", i);
                        s->output_port[i] = jack_port_register (s->client, name, JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
                }
        }
                

        return s;

release_client:
        jack_client_close(s->client);
error:
        free(s);
        return NULL;
}
示例#26
0
// Main
int main(int argc, char * argv[]) {
	// User supplied correct vals? Otherwise show usage...
	// TODO: Allow a minimum of <image path> to be provided and default
	// 	 the rest.
	if (argc < 8) {
		fprintf(stderr, "usage: sonify <client name> <image path> <freq scale> <lowest freq> <sin | sq | tri | saw> <window scale>\ni.e. sonify sfy img.png 10000 1000 1 sin\n");
		exit(1);
	}
	jack_client_t * client;
	const char ** ports;
	char file_name[100];
	int window_scale;
	init_vars(argv, file_name, &window_scale);

	// Init Jack Client
	if ((client = jack_client_open(argv[1], JackNullOption, NULL)) == 0) {
		fprintf (stderr, "Jack server not running?\n");
		return 1;
	}
	jack_set_process_callback(client, process, 0);
	jack_set_sample_rate_callback(client, srate, 0);
	input_port = jack_port_register(client, "input", JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
	output_port = jack_port_register(client, "output", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);

	// Get Sample Rate & Init Aubio
	sample_rate = jack_get_sample_rate(client);
	init_aubio(sample_rate);
	
	// Init SDL Surfaces
	source_image = IMG_Load(file_name);
	if (source_image == NULL) {
		fprintf(stderr, "Load failes: %s\n", IMG_GetError());
		exit(1);
	}
	//   Generate Tones From Pixels
	generate_tone_array(source_image);
	dest_image = SDL_CreateRGBSurface (SDL_SWSURFACE, source_image->w, source_image->h, 32, 0, 0, 0, 0);
	if(dest_image == NULL) {
		fprintf(stderr, "CreateRGBSurface failed: %s\n", SDL_GetError());
		exit(1);
    	}
	SDL_FreeSurface(source_image);

	// Build Tone
	build_tone(image_tones[image_tones_index], image_tones_amp[image_tones_index], waveform_type);

	// Activate Jack Client
	if (jack_activate(client)) {
		fprintf(stderr, "cannot activate client\n");
		return 1;
	}

	// Init SDL Window
	if (SDL_Init(SDL_INIT_VIDEO) != 0) {
		fprintf(stderr, "Init failed: %s\n", SDL_GetError());
		exit(1);
	}
	SDL_Surface * display;
	display = SDL_SetVideoMode(dest_image->w * window_scale, dest_image->h * window_scale, 32, SDL_HWSURFACE | SDL_DOUBLEBUF);
	if (display == NULL) { 
		fprintf(stderr, "SetVideoMode failed: %s\n", SDL_GetError()); 
		exit(1);
	}
	SDL_WM_SetCaption("Sonify", "Sonify");
	SDL_Event event;

	// GUI Loop
	// TODO: Implement a fullscreen mode that can be toggled with a keypress.
	// TODO: The larger the window_scale, the slower SDL_ResizeFactor runs.
	//       Consider writing a function that only redraws a particular portion
	//       of dub_image instead. This will improve performance in fullscreen
	//       mode down the line. 
	// TODO: Can we introduce some simple menu items for changing the transcoding
	//       algorithm on the fly?
	while(1) {
		if (SDL_PollEvent(&event)) {
			if (event.type == SDL_QUIT) {
				break;
			}
		}
		// TODO: Optimize this...
		dub_image = SDL_DisplayFormat(dest_image);
		if (SDL_BlitSurface(SDL_ResizeFactor(dub_image, window_scale, 1), NULL, display, NULL) != 0) {
			fprintf(stderr, "SDL_BlitSurface() Failed.");
			exit(1);
		}
		SDL_Flip(display);
	}

	// Cleanup
	jack_client_close(client);
	del_aubio_pitchdetection(aubio);
	SDL_FreeSurface(display);
	SDL_FreeSurface(dub_image);
	SDL_FreeSurface(dest_image);
	SDL_Quit();
	free(cycle);
	free(image_tones);
	free(image_tones_amp);
	exit(0);
}
示例#27
0
void * audio_cap_jack_init(char *cfg)
{
        struct state_jack_capture *s;
        jack_status_t status;
        const char **ports;
        int i;



        if(!cfg || strcmp(cfg, "help") == 0) {
                audio_cap_jack_help("jack");
                return NULL;
        }


        s = (struct state_jack_capture *) calloc(1, sizeof(struct state_jack_capture));
        if(!s) {
                fprintf(stderr, "[JACK capture] Unable to allocate memory.\n");
                goto error;
        }

        s->client = jack_client_open(PACKAGE_STRING, JackNullOption, &status);
        if(status == JackFailure) {
                fprintf(stderr, "[JACK capture] Opening JACK client failed.\n");
                goto error;
        }

        ports = jack_get_ports(s->client, cfg, NULL, JackPortIsOutput);
        if(ports == NULL) {
                fprintf(stderr, "[JACK capture] Unable to output ports matching %s.\n", cfg);
                goto release_client;
        }

        i = 0;
        while(ports[i]) i++;

        s->frame.ch_count = i;
        s->frame.bps = 4;
        s->frame.sample_rate = jack_get_sample_rate (s->client);
        s->frame.max_size = s->frame.ch_count * s->frame.bps * s->frame.sample_rate;
        s->frame.data = malloc(s->frame.max_size);

        s->tmp = malloc(s->frame.max_size);

        s->data = ring_buffer_init(s->frame.max_size);
        
        free(ports);

        if(jack_set_sample_rate_callback(s->client, jack_samplerate_changed_callback, (void *) s)) {
                fprintf(stderr, "[JACK capture] Registring callback problem.\n");
                goto release_client;
        }

        if(jack_set_process_callback(s->client, jack_process_callback, (void *) s) != 0) {
                fprintf(stderr, "[JACK capture] Process callback registration problem.\n");
                goto release_client;
        }

        if(jack_activate(s->client)) {
                fprintf(stderr, "[JACK capture] Cannot activate client.\n");
                goto release_client;
        }

        {
                int port;
                char name[32];

                for(port = 0; port < i; port++) {
                        snprintf(name, 32, "capture_%02u", port);
                        s->input_ports[port] = jack_port_register(s->client, name, JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
                        /* attach ports */
                        if(jack_connect(s->client, ports[port], jack_port_name(s->input_ports[port]))) {
                                fprintf(stderr, "[JACK capture] Cannot connect input ports.\n");
                        }
                }
        }

        return s;

release_client:
        jack_client_close(s->client);   
error:
        free(s);
        return NULL;
}
示例#28
0
int jack_open_audio(int inchans, int outchans, int rate)
{
    int j;
    char port_name[80] = "";
    int client_iterator = 0;
    int new_jack = 0;
    int srate;
    jack_status_t status;

    jack_dio_error = 0;
    
    if ((inchans == 0) && (outchans == 0)) return 0;

    if (outchans > NUM_JACK_PORTS)
    {
        error("JACK: %d output ports not supported, setting to %d",
            outchans, NUM_JACK_PORTS);
        outchans = NUM_JACK_PORTS;
    }

    if (inchans > NUM_JACK_PORTS)
    {
        error("JACK: %d input ports not supported, setting to %d",
            inchans, NUM_JACK_PORTS);
        inchans = NUM_JACK_PORTS;
    }

    /* try to become a client of the JACK server */
    /* if no JACK server exists, start a default one
       (jack_client_open() does that for us... */
    if (!jack_client)
    {
        do {
            sprintf(port_name,"pure_data_%d",client_iterator);
            client_iterator++;
            /* do not try to start the jack-server...
               seems to make problems... */
            jack_client = jack_client_open(port_name,
                JackNoStartServer, &status, NULL);
            if (status & JackServerFailed)
            {
                error("JACK: unable to connect to JACK server");
                jack_client=NULL;
                break;
            }
        } while (status & JackNameNotUnique);

        if(status)
        {
            if (status & JackServerStarted)
            {
                post("JACK: started JACK server?");
            }
            else
            {
                post("JACK: jack returned status %d", status);
            }
        }
      
        if (!jack_client)
        { // jack spits out enough messages already, do not warn
            sys_inchannels = sys_outchannels = 0;
            return 1;
        }
      
        jack_get_clients();

        /* tell the JACK server to call `process()' whenever
           there is work to be done.
        */
      
        jack_set_process_callback (jack_client, process, 0);
      
        // jack_set_error_function (jack_error);
      
#ifdef JACK_XRUN
        jack_set_xrun_callback (jack_client, jack_xrun, NULL);
#endif
      
        /* tell the JACK server to call `srate()' whenever
           the sample rate of the system changes.
        */
      
        jack_set_sample_rate_callback (jack_client, jack_srate, 0);
      
      
        /* tell the JACK server to call `jack_shutdown()' if
           it ever shuts down, either entirely, or if it
           just decides to stop calling us.
        */
      
        jack_on_shutdown (jack_client, jack_shutdown, 0);
      
        for (j = 0; j < NUM_JACK_PORTS; j++)
        {
             input_port[j]=NULL;
             output_port[j] = NULL;
        }

        new_jack = 1;
    }

    /* display the current sample rate. once the client is activated
       (see below), you should rely on your own sample rate
       callback (see above) for this value.
    */
    
    srate = jack_get_sample_rate (jack_client);
    sys_dacsr = srate;
            
    /* create the ports */
    
    for (j = 0; j < inchans; j++)
    {
        sprintf(port_name, "input%d", j);
        if (!input_port[j])
            input_port[j] = jack_port_register(jack_client, port_name,
                JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0);
        if (!input_port[j])
        {
            error("JACK: can only register %d input ports "
                  "(instead of requested %d)",
                j, inchans);
            sys_inchannels = inchans = j;
            break;
        }
    }

    for (j = 0; j < outchans; j++)
    {
        sprintf(port_name, "output%d", j);
        if (!output_port[j])
            output_port[j] = jack_port_register(jack_client, port_name,
                JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0);
        if (!output_port[j])
        {
            error("JACK: can only register %d output ports "
                  "(instead of requested %d)",
                j, outchans);
            sys_outchannels = outchans = j;
            break;
        }
    } 
    outport_count = outchans;

    /* tell the JACK server that we are ready to roll */

    if (new_jack)
    {
        if (jack_activate (jack_client))
        {
            error("JACK: cannot activate client");
            sys_inchannels = sys_outchannels = 0;
            return 1;
        }
        
        memset(jack_outbuf,0,sizeof(jack_outbuf));
        
        if (jack_client_names[0])
            jack_connect_ports(jack_client_names[0]);

        pthread_mutex_init(&jack_mutex,NULL);
        pthread_cond_init(&jack_sem,NULL);
    }
    return 0;
}
示例#29
0
int JackOutput::init( unsigned /*nBufferSize*/ )
{
	Preferences* pref = Preferences::get_instance();
	output_port_name_1 = pref->m_sJackPortName1;
	output_port_name_2 = pref->m_sJackPortName2;

	QString sClientName = "Hydrogen";

#ifdef H2CORE_HAVE_NSMSESSION
	QString nsmClientId = pref->getNsmClientId();

	if(!nsmClientId.isEmpty()){
		sClientName = nsmClientId;
	}
#endif


	jack_status_t status;
	int tries = 2;  // Sometimes jackd doesn't stop and start fast enough.
	while ( tries > 0 ) {
		--tries;

#ifdef H2CORE_HAVE_JACKSESSION
		if (pref->getJackSessionUUID().isEmpty()){
			client = jack_client_open(
						 sClientName.toLocal8Bit(),
						 JackNullOption,
						 &status);
		} else {
			const QByteArray uuid = pref->getJackSessionUUID().toLocal8Bit();
			client = jack_client_open(
						 sClientName.toLocal8Bit(),
						 JackSessionID,
						 &status,
						 uuid.constData());
		}
#else
		client = jack_client_open(
					 sClientName.toLocal8Bit(),
					 JackNullOption,
					 &status);
#endif
		switch(status) {
			case JackFailure:
				CLIENT_FAILURE("unknown error");
				break;
			case JackInvalidOption:
				CLIENT_FAILURE("invalid option");
				break;
			case JackNameNotUnique:
				if (client) {
					sClientName = jack_get_client_name(client);
					CLIENT_SUCCESS(QString("Jack assigned the client name '%1'").arg(sClientName));
				} else {
					CLIENT_FAILURE("name not unique");
				}
				break;
			case JackServerStarted:
				CLIENT_SUCCESS("JACK Server started for Hydrogen.");
				break;
			case JackServerFailed:
				CLIENT_FAILURE("unable to connect");
				break;
			case JackServerError:
				CLIENT_FAILURE("communication error");
				break;
			case JackNoSuchClient:
				CLIENT_FAILURE("unknown client type");
				break;
			case JackLoadFailure:
				CLIENT_FAILURE("can't load internal client");
				break;
			case JackInitFailure:
				CLIENT_FAILURE("can't initialize client");
				break;
			case JackShmFailure:
				CLIENT_FAILURE("unable to access shared memory");
				break;
			case JackVersionError:
				CLIENT_FAILURE("client/server protocol version mismatch");
			default:
				if (status) {
					ERRORLOG("Unknown status with JACK server.");
					if (client) {
						CLIENT_SUCCESS("Client pointer is *not* null..."
									   " assuming we're OK");
					}
				} else {
					CLIENT_SUCCESS("Connected to JACK server");
				}
		}
	}

	if (client == 0) return -1;

	// Here, client should either be valid, or NULL.
	jack_server_sampleRate = jack_get_sample_rate ( client );
	jack_server_bufferSize = jack_get_buffer_size ( client );

	pref->m_nSampleRate = jack_server_sampleRate;
	pref->m_nBufferSize = jack_server_bufferSize;

	/* tell the JACK server to call `process()' whenever
	   there is work to be done.
	*/
	jack_set_process_callback ( client, this->processCallback, 0 );

	/* tell the JACK server to call `srate()' whenever
	   the sample rate of the system changes.
	*/
	jack_set_sample_rate_callback ( client, jackDriverSampleRate, this );

	/* tell JACK server to update us if the buffer size
	   (frames per process cycle) changes.
	*/
	jack_set_buffer_size_callback ( client, jackDriverBufferSize, 0 );

	/* tell the JACK server to call `jack_shutdown()' if
	   it ever shuts down, either entirely, or if it
	   just decides to stop calling us.
	*/
	jack_on_shutdown ( client, jackDriverShutdown, 0 );

	/* create two ports */
	output_port_1 = jack_port_register ( client, "out_L", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0 );
	output_port_2 = jack_port_register ( client, "out_R", JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0 );

	Hydrogen *H = Hydrogen::get_instance();
	if ( ( output_port_1 == NULL ) || ( output_port_2 == NULL ) ) {
		H->raiseError( Hydrogen::JACK_ERROR_IN_PORT_REGISTER );
		return 4;
	}

	// clear buffers
	//	jack_default_audio_sample_t *out_L = (jack_default_audio_sample_t *) jack_port_get_buffer (output_port_1, jack_server_bufferSize);
	//	jack_default_audio_sample_t *out_R = (jack_default_audio_sample_t *) jack_port_get_buffer (output_port_2, jack_server_bufferSize);
	//	memset( out_L, 0, nBufferSize * sizeof( float ) );
	//	memset( out_R, 0, nBufferSize * sizeof( float ) );

#ifdef H2CORE_HAVE_LASH
	if ( pref->useLash() ){
		LashClient* lashClient = LashClient::get_instance();
		if (lashClient->isConnected()) {
			lashClient->setJackClientName(sClientName.toLocal8Bit().constData());
		}
	}
#endif

#ifdef H2CORE_HAVE_JACKSESSION
	jack_set_session_callback (client, jack_session_callback, (void*)this);
#endif

	if ( pref->m_bJackMasterMode == Preferences::USE_JACK_TIME_MASTER )
		initTimeMaster();

	return 0;
}
示例#30
0
/*****************************************************************************
 *
 * JACK_INIT()
 *
 * Setup the jack client.
 *
 *****************************************************************************/
int
jack_init(void) {
    const char		*server_name = NULL;
    static char		client_name[32];
    jack_options_t	options = JackNoStartServer | JackUseExactName;
    jack_status_t	status = 0;

    if (debug) {
	fprintf (stderr, "Initializing JACK client from thread 0x%lx\n", pthread_self());
    }

    if (client != NULL) {
	if (debug) {
	    fprintf (stderr, "Warning: closing stale JACK client...\n");
	}
	jack_client_close (client);
	client = NULL;
    }

    /* open a client connection to the JACK server */
    for( phasex_instance = 0; phasex_instance != 16; phasex_instance++)
    {
    if(!phasex_instance) {
        snprintf (client_name, 32, "%s", phasex_title);
    }
    else {
        snprintf (client_name, 32, "%s-%02d", phasex_title, phasex_instance);
    }
    printf("Using client name %s\n", client_name);
    if (client = jack_client_open ((const char *)client_name, options, &status, server_name))
        break;
    }
    
    /* deal with non-unique client name */
    if (status & JackNameNotUnique) {
	fprintf (stderr, "Unable to start JACK client '%s'!\n", client_name);
	return 1;
    }

    /* deal with jack server problems */
    if (status & (JackServerFailed | JackServerError)) {
	if (debug) {
	    fprintf (stderr, "Unable to connect to JACK server.  Status = 0x%2.0x\n", status);
	}
	return 1;
    }

    /* deal with missing client */
    if (client == NULL) {
	if (debug) {
	    fprintf (stderr, "Unable to open JACK client.  Status = 0x%2.0x\n", status);
	}
	return 1;
    }

    /* callback for when jack shuts down (needs to be set as early as possible) */
    jack_on_shutdown (client, jack_shutdown_handler, 0);

    if (debug) {
	fprintf (stderr, "Unique JACK client name '%s' assigned.\n", client_name);
    }

    /* notify if we started jack server */
    if (status & JackServerStarted) {
	fprintf (stderr, "JACK server started.\n");
    }

    /* report realtime scheduling in JACK */
    if (debug) {
	if (jack_is_realtime (client)) {
	    fprintf (stderr, "JACK is running with realtime scheduling.\n");
	}
	else {
	    fprintf (stderr, "JACK is running without realtime scheduling.\n");
	}
    }

    /* get sample rate early and notify other threads */
    sample_rate = jack_get_sample_rate (client);

    if (debug) {
	fprintf (stderr, "JACK sample rate:  %d\n", sample_rate);
    }

    /* scale sample rate depending on mode */
    switch (sample_rate_mode) {
    case SAMPLE_RATE_UNDERSAMPLE:
	sample_rate /= 2;
	break;
    case SAMPLE_RATE_OVERSAMPLE:
	sample_rate *= 2;
	break;
    }

    /* set samplerate related vars */
    f_sample_rate = (sample_t)sample_rate;
    nyquist_freq  = (sample_t)(sample_rate / 2);
    wave_period   = (sample_t)(F_WAVEFORM_SIZE / (double)sample_rate);

    if (debug) {
	fprintf (stderr, "Internal sample rate:  %d\n", sample_rate);
    }

    /* callback for setting our sample rate when jack tells us to */
    jack_set_sample_rate_callback (client, jack_samplerate_handler, 0);

    /* now that we have the sample rate, signal anyone else who needs to know */
    pthread_mutex_lock (&sample_rate_mutex);
    pthread_cond_broadcast (&sample_rate_cond);
    pthread_mutex_unlock (&sample_rate_mutex);

    /* get buffer size */
    buffer_size = jack_get_buffer_size (client) * 2;
    if (buffer_size > (PHASEX_MAX_BUFSIZE / 2)) {
    	fprintf (stderr, "JACK requested buffer size:  %d.  Max is:  %d.\n",
		 buffer_size, (PHASEX_MAX_BUFSIZE / 2));
    	fprintf (stderr, "JACK buffer size exceeded.  Closing client...\n");
	jack_client_close (client);
	client = NULL;
	jack_running = 0;
	return 1;
    }
    buffer_full = buffer_size;
    if (debug) {
	fprintf (stderr, "JACK output buffer size:  %d.\n", buffer_size);
    }

    /* callback for setting our buffer size when jack tells us to */
    jack_set_buffer_size_callback (client, jack_bufsize_handler, 0);

    /* callback for dealing with xruns */
    jack_set_xrun_callback (client, jack_xrun_handler, 0);

    /* create ports */
    input_port1 = jack_port_register (client, "in_1",
				      JACK_DEFAULT_AUDIO_TYPE,
				      JackPortIsInput, 0);
    input_port2 = jack_port_register (client, "in_2",
				      JACK_DEFAULT_AUDIO_TYPE,
				      JackPortIsInput, 0);

    output_port1 = jack_port_register (client, "out_1",
				       JACK_DEFAULT_AUDIO_TYPE,
				       JackPortIsOutput, 0);
    output_port2 = jack_port_register (client, "out_2",
				       JACK_DEFAULT_AUDIO_TYPE,
				       JackPortIsOutput, 0);

    if ( (output_port1 == NULL) || (output_port2 == NULL) ||
	 (input_port1 == NULL) || (input_port2 == NULL) )
    {
	fprintf (stderr, "JACK has no output ports available.\n");
	jack_client_close (client);
	client = NULL;
	jack_running = 0;
	return 0;
    }

    /* set callback for jack to grab audio data */
    jack_set_process_callback (client, process_buffer, 0);

    return 0;
}