コード例 #1
0
int dns_service_publisher_start( dns_service_desc_t *service_desc )
{
	int ret = 0;
	int error;

	if( ! service_desc ) return 1;

	if( ! (threaded_poll = avahi_threaded_poll_new() ) ) {
		logging_printf(LOGGING_ERROR, "Unable to create publisher thread\n");
		return 1;
	}

	sd_name_copy = avahi_strdup( service_desc->name );
	sd_service_copy = avahi_strdup( service_desc->service );
	sd_port = service_desc->port;

	use_ipv4 = service_desc->publish_ipv4;
	use_ipv6 = service_desc->publish_ipv6;

	client = avahi_client_new(avahi_threaded_poll_get(threaded_poll), 0, client_callback, NULL, &error);

	if (! client) {
		logging_printf(LOGGING_ERROR, "Failed to create client: %s\n", avahi_strerror(error));
		return 1;
	}

	avahi_threaded_poll_start( threaded_poll );

	return ret;
}
コード例 #2
0
ファイル: midi_journal.c プロジェクト: ravelox/pimidi
void journal_header_dump( journal_header_t *header )
{
	DEBUG_ONLY;
	if( ! header ) return;

	logging_printf( LOGGING_DEBUG, "Journal (Header: bitfield=%02x totchan=%d seq=%04x)\n", header->bitfield, header->totchan, header->seq);
	logging_printf( LOGGING_DEBUG, "Header Size = %u\n", sizeof( journal_header_t ) );
}
コード例 #3
0
ファイル: midi_program.c プロジェクト: ravelox/pimidi
int midi_program_unpack( midi_program_t **midi_program, unsigned char *buffer, size_t buffer_len )
{
	int ret = 0;


	*midi_program = NULL;

	if( ! buffer ) return -1;

	if( buffer_len != sizeof( PACKED_MIDI_PROGRAM_SIZE ))
	{
		logging_printf( LOGGING_DEBUG, "midi_program_unpack: Expecting %d, got %zd\n", PACKED_MIDI_PROGRAM_SIZE, buffer_len );
		return -1;
	}

	*midi_program = midi_program_create();
	
	if( ! *midi_program ) return -1;

	(*midi_program)->command = (buffer[0] & 0xf0) >> 4 ;
	(*midi_program)->channel = (buffer[0] & 0x0f);
	(*midi_program)->B = (buffer[1] & 0x80 ) >> 7;
	(*midi_program)->bank_msb = ( buffer[1] & 0x7f );
	(*midi_program)->X = (buffer[2] & 0x80 ) >> 7;
	(*midi_program)->bank_lsb = ( buffer[2] & 0x7f );

	return ret;
}
コード例 #4
0
ファイル: midi_journal.c プロジェクト: ravelox/pimidi
void channel_header_dump( channel_header_t *header )
{
	DEBUG_ONLY;
	if( ! header ) return;

	logging_printf( LOGGING_DEBUG, "Channel #%d (Header: S=%d,H=%d,len=%u,bitfield=%02x)\n", header->chan, header->S, header->H, header->len, header->bitfield);
}
コード例 #5
0
ファイル: midi_program.c プロジェクト: ravelox/pimidi
void midi_program_dump( midi_program_t *midi_program )
{
	DEBUG_ONLY;
	if(! midi_program ) return;

	logging_printf( LOGGING_DEBUG, "MIDI Program Change: command=0x%02x, channel=0x%02x, S=%d program=%d B=%d, bank_msb=0x%02x, X=%d, bank_lsb=0x%02x\n",
		midi_program->command, midi_program->channel, midi_program->S, midi_program->program, midi_program->B, midi_program->bank_msb, midi_program->X, midi_program->bank_lsb );
}
コード例 #6
0
ファイル: net_connection.c プロジェクト: alepom/pimidi
void net_ctx_send( uint8_t ctx_id, unsigned char *buffer, size_t buffer_len )
{
	net_ctx_t *ctx = NULL;
	struct sockaddr_in send_address;
	ssize_t bytes_sent = 0;
	uint16_t port;
	int send_socket;

	if( ! buffer ) return;
	if( buffer_len <= 0 ) return;

	ctx = net_ctx_find_by_id( ctx_id );

	if( ! ctx ) return;

	debug_net_ctx_dump( ctx );
	debug_ctx_journal_dump( ctx_id );

	send_socket = socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP );

	if( send_socket < 0 )
	{
		logging_printf( LOGGING_ERROR, "Unable to create sending socket to %s:%u\n%s\n", ctx->ip_address, port, strerror( errno ) );
		return;
	}

	memset((char *)&send_address, 0, sizeof( send_address));
	send_address.sin_family = AF_INET;
	port = ctx->port + 1;
	send_address.sin_port = htons( port ) ;
	inet_aton( ctx->ip_address, &send_address.sin_addr );

	bytes_sent = sendto( send_socket, buffer, buffer_len , 0 , (struct sockaddr *)&send_address, sizeof( send_address ) );

	close( send_socket );
	
	if( bytes_sent < 0 )
	{
		logging_printf( LOGGING_ERROR, "Failed to send %u bytes to %s:%u\n%s\n", buffer_len, ctx->ip_address, port , strerror( errno ));
	} else {
		logging_printf( LOGGING_DEBUG, "Sent %u bytes to %s:%u\n", bytes_sent, ctx->ip_address, port );
	}
}
コード例 #7
0
ファイル: midi_journal.c プロジェクト: ravelox/pimidi
void journal_pack( journal_t *journal, char **packed, size_t *size )
{
	char *packed_journal_header = NULL;
	size_t packed_journal_header_size = 0;
	char *packed_channel = NULL;
	size_t packed_channel_size = 0;
	char *packed_channel_buffer = NULL;	
	size_t packed_channel_buffer_size = 0;
	char *p = NULL;
	int i = 0;

	*packed = NULL;
	*size = 0;

	if( ! journal ) return;

	logging_printf( LOGGING_DEBUG, "journal_pack: journal_has_data = %s header->totchan=%u\n", ( journal_has_data( journal )  ? "YES" : "NO" ) , journal->header->totchan);
	if(  ! journal_has_data( journal ) ) return;

	journal_header_pack( journal->header, &packed_journal_header, &packed_journal_header_size );

	for( i = 0 ; i < MAX_MIDI_CHANNELS ; i++ )
	{
		if( ! journal->channels[i] ) continue;

		channel_pack( journal->channels[i], &packed_channel, &packed_channel_size );

		packed_channel_buffer = ( char * )realloc( packed_channel_buffer, packed_channel_buffer_size + packed_channel_size );
		if( ! packed_channel_buffer ) goto journal_pack_cleanup;

		p = packed_channel_buffer + packed_channel_buffer_size;
		memset( p, 0, packed_channel_size );

		packed_channel_buffer_size += packed_channel_size;
		memcpy( p, packed_channel, packed_channel_size );

		FREENULL( "packed_channel", (void **)&packed_channel );
	}

	// Join it all together

	*packed = ( char * )malloc( packed_journal_header_size + packed_channel_buffer_size );
	p = *packed;
	memcpy( p, packed_journal_header, packed_journal_header_size );
	*size += packed_journal_header_size;
	p += packed_journal_header_size;

	memcpy( p, packed_channel_buffer, packed_channel_buffer_size );
	*size += packed_channel_buffer_size;
	
journal_pack_cleanup:
	FREENULL( "packed_channel", (void **)&packed_channel );
	FREENULL( "packed_channel_buffer", (void **)&packed_channel_buffer );
	FREENULL( "packed_journal_header", (void **)&packed_journal_header );
}
コード例 #8
0
ファイル: remote_connection.c プロジェクト: ravelox/pimidi
static void *remote_connect_sync_thread( void *data )
{
	net_response_t *response;
	net_ctx_t *ctx = NULL;
	char *remote_service_name = NULL;
	int shutdown_fd = 0;
	fd_set read_fds;
	struct timeval tv;
	int sync_interval = 0;

	logging_printf( LOGGING_DEBUG, "remote_connect_sync_thread: start\n");
	logging_printf( LOGGING_DEBUG, "rmeote_connect_sync_thread: sync.interval=%s\n", config_string_get("sync.interval"));

	shutdown_fd = net_socket_get_shutdown_fd();
	logging_printf( LOGGING_DEBUG, "remote_connect_sync_thread: shutdown_fd=%u\n", shutdown_fd );

	remote_service_name = config_string_get("remote.connect");
	sync_interval = config_int_get("sync.interval");

	do
	{
		ctx = net_ctx_find_by_name( remote_service_name );
		if( ! ctx )
		{
			logging_printf( LOGGING_DEBUG, "remote_connect_sync_thread: No remote connection context\n");
			break;
		}
		FD_ZERO( &read_fds );
		FD_SET( shutdown_fd, &read_fds );
		memset( &tv, 0, sizeof( struct timeval ) );
		tv.tv_sec = sync_interval;
		select( shutdown_fd + 1, &read_fds, NULL , NULL, &tv );
		logging_printf( LOGGING_DEBUG, "remote_connect_sync_thread: select()=\"%s\"\n", strerror( errno ) );
		if( net_socket_get_shutdown_lock() == 1 )
		{
			logging_printf(LOGGING_DEBUG, "remote_connect_sync_thread: shutdown received during poll\n");
			break;
		}
		response = net_response_sync( ctx->send_ssrc , ctx->start );
		net_ctx_send( ctx, response->buffer, response->len, USE_CONTROL_PORT );
		hex_dump( response->buffer, response->len );
		net_response_destroy( &response );
	} while( 1 );

	if( net_socket_get_shutdown_lock() == 1 )
	{
		logging_printf(LOGGING_DEBUG, "remote_connect_sync_thread: shutdown received\n");
	}
	logging_printf( LOGGING_DEBUG, "remote_connect_sync_thread: stop\n");

	return NULL;
}
コード例 #9
0
ファイル: logging.c プロジェクト: lshain/enviroment
/**
 * logging_arguments: print arguments into the logging file.
 *
 *	@param[in]	argc
 *	@param[in]	argv
 *
 *	@par Uses:
 *		logging_printf()
 */
void
logging_arguments(int argc, char **argv)
{
	int i;

	for (i = 0; i < argc; i++) {
		if (ignore)
			break;
		logging_printf("%d: |%s|\n", i, argv[i]);
	}
}
コード例 #10
0
static void entry_group_callback(AvahiEntryGroup *g, AvahiEntryGroupState state, AVAHI_GCC_UNUSED void *userdata) {
    assert(g == group || group == NULL);
    group = g;

    /* Called whenever the entry group state changes */

    switch (state) {
        case AVAHI_ENTRY_GROUP_ESTABLISHED :
            /* The entry group has been established successfully */
            logging_printf(LOGGING_INFO, "Service '%s' successfully established.\n", sd_name_copy);
            break;

        case AVAHI_ENTRY_GROUP_COLLISION : {
            char *n;

            /* A service name collision with a remote service
             * happened. Let's pick a new name */
            n = avahi_alternative_service_name( sd_name_copy );
            avahi_free(sd_name_copy);
            sd_name_copy = n;

            logging_printf(LOGGING_WARN, "Service name collision, renaming service to '%s'\n", sd_name_copy);

            /* And recreate the services */
            create_services( avahi_entry_group_get_client(g) );
            break;
        }

        case AVAHI_ENTRY_GROUP_FAILURE :

            logging_printf(LOGGING_WARN, "Entry group failure: %s\n", avahi_strerror(avahi_client_errno(avahi_entry_group_get_client(g))));

            /* Some kind of failure happened while we were registering our services */
            avahi_threaded_poll_quit(threaded_poll);
            break;

        case AVAHI_ENTRY_GROUP_UNCOMMITED:
        case AVAHI_ENTRY_GROUP_REGISTERING:
            ;
    }
}
コード例 #11
0
ファイル: midi_journal.c プロジェクト: ravelox/pimidi
void channel_journal_reset( channel_t *channel )
{
	if( ! channel ) return;

	if( channel->header )
	{
		logging_printf(LOGGING_DEBUG, "channel_journal_reset( %u )\n", channel->header->chan);
	}
	chapter_n_reset( channel->chapter_n );
	chapter_c_reset( channel->chapter_c );
	channel_header_reset( channel->header );
}
コード例 #12
0
ファイル: cmd_end_handler.c プロジェクト: ViktorNova/pimidi
net_response_t * cmd_end_handler( void *data )
{
	net_applemidi_inv *inv = NULL;
	net_ctx_t *ctx = NULL;

	if( ! data ) return NULL;

	inv = ( net_applemidi_inv *) data;

	logging_printf( LOGGING_DEBUG, "BYE( \n");
	logging_printf( LOGGING_DEBUG, "\tname=<<%s>>\n", inv->name);
	logging_printf( LOGGING_DEBUG, "\tssrc=0x%08x\n", inv->ssrc);
	logging_printf( LOGGING_DEBUG, "\tversion = 0x%08x\n", inv->version);
	logging_printf( LOGGING_DEBUG, "\tinitiator=0x%08x )\n", inv->initiator);

	ctx = net_ctx_find_by_ssrc( inv->ssrc );

	if( ! ctx )
	{
		logging_printf( LOGGING_WARN, "cmd_end_handler:No existing connection found\n");
		return NULL;
	}

	net_ctx_reset( ctx );

	return NULL;
}
コード例 #13
0
ファイル: net_connection.c プロジェクト: alepom/pimidi
void debug_net_ctx_dump( net_ctx_t *ctx )
{
	if( ! ctx ) return;
	
	logging_printf( LOGGING_DEBUG, "CTX(\n");
	logging_printf( LOGGING_DEBUG, "\tUsed=%d\n", ctx->used);
	logging_printf( LOGGING_DEBUG, "\tssrc=%08x\n", ctx->ssrc);
	logging_printf( LOGGING_DEBUG, "\tsend_ssrc=%08x\n", ctx->send_ssrc);
	logging_printf( LOGGING_DEBUG, "\tinitiator=%08x\n", ctx->initiator);
	logging_printf( LOGGING_DEBUG, "\tseq=%08x (%08d)\n", ctx->seq, ctx->seq);
	logging_printf( LOGGING_DEBUG, "\thost=%s:%u )\n", ctx->ip_address, ctx->port);
}
コード例 #14
0
ファイル: midi_program.c プロジェクト: ravelox/pimidi
midi_program_t * midi_program_create( void )
{
	midi_program_t *new_program = NULL;

	new_program = (midi_program_t *) malloc( sizeof( midi_program_t ) );

	if( ! new_program )
	{
		logging_printf(LOGGING_ERROR,"midi_program_create: Unable to allocate memory for new midi_program_t\n");
		return NULL;
	}

	memset( new_program, 0, sizeof( midi_program_t ) );
	return new_program;
}
コード例 #15
0
ファイル: net_connection.c プロジェクト: alepom/pimidi
void debug_ctx_journal_dump( uint8_t ctx_id )
{
	net_ctx_t *ctx = NULL;

	if( ctx_id > _max_ctx - 1 ) return;

	ctx = net_ctx_find_by_id( ctx_id );

	if( ! ctx) return;

	logging_printf( LOGGING_DEBUG, "Journal has data: %s\n", ( journal_has_data( ctx->journal ) ? "YES" : "NO" ) );

	if( ! journal_has_data( ctx->journal ) ) return;

	journal_dump( ctx->journal );
}
コード例 #16
0
ファイル: midi_payload.c プロジェクト: ViktorNova/pimidi
void payload_dump( midi_payload_t *payload )
{
	if( ! payload ) return;
	if( ! payload->header ) return;

	logging_printf( LOGGING_DEBUG, "MIDI Payload(\n");
	logging_printf( LOGGING_DEBUG, "\tB=%d\n", payload->header->B);
	logging_printf( LOGGING_DEBUG, "\tJ=%d\n", payload->header->J);
	logging_printf( LOGGING_DEBUG, "\tZ=%d\n", payload->header->Z);
	logging_printf( LOGGING_DEBUG, "\tP=%d\n", payload->header->P);
	logging_printf( LOGGING_DEBUG, "\tpayloadlength=%u )\n", payload->header->len);
}
コード例 #17
0
static void client_callback(AvahiClient *c, AvahiClientState state, AVAHI_GCC_UNUSED void * userdata) {
    assert(c);

    /* Called whenever the client or server state changes */

    switch (state) {
        case AVAHI_CLIENT_S_RUNNING:

            /* The server has startup successfully and registered its host
             * name on the network, so it's time to create our services */
            create_services(c);
            break;

        case AVAHI_CLIENT_FAILURE:

            logging_printf(LOGGING_ERROR, "Client failure: %s\n", avahi_strerror(avahi_client_errno(c)));
            avahi_threaded_poll_quit(threaded_poll);

            break;

        case AVAHI_CLIENT_S_COLLISION:

            /* Let's drop our registered services. When the server is back
             * in AVAHI_SERVER_RUNNING state we will register them
             * again with the new host name. */

        case AVAHI_CLIENT_S_REGISTERING:

            /* The server records are now being established. This
             * might be caused by a host name change. We need to wait
             * for our own records to register until the host name is
             * properly esatblished. */

            if (group)
                avahi_entry_group_reset(group);

            break;

        case AVAHI_CLIENT_CONNECTING:
            ;
    }
}
コード例 #18
0
ファイル: midi_journal.c プロジェクト: ravelox/pimidi
void channel_journal_dump( channel_t *channel )
{
	DEBUG_ONLY;
	if( ! channel ) return;

	logging_printf(LOGGING_DEBUG,"channel_journal_dump\n");
	channel_header_dump( channel->header );

	if( channel->header->bitfield & CHAPTER_P )
	{
		chapter_p_dump( channel->chapter_p );
	}
	if( channel->header->bitfield & CHAPTER_C )
	{
		chapter_c_dump( channel->chapter_c );
	}
	if( channel->header->bitfield & CHAPTER_N )
	{
		chapter_n_dump( channel->chapter_n );
	}
}
コード例 #19
0
ファイル: net_connection.c プロジェクト: alepom/pimidi
net_ctx_t * net_ctx_register( uint32_t ssrc, uint32_t initiator, char *ip_address, uint16_t port )
{
	uint8_t i;

	for( i = 0 ; i < _max_ctx ; i++ )
	{
		if( ctx[i] )
		{
			if( ctx[i]->used == 0 )
			{
				time_t now = time( NULL );
				unsigned int send_ssrc = rand_r( (unsigned int *)&now );

				net_ctx_set( ctx[i], ssrc, initiator, send_ssrc, 0x638F, port, ip_address );
				return ctx[i];
			}
		}
	}
	
	logging_printf( LOGGING_WARN, "No free connection slots available\n");
	return NULL;
}
コード例 #20
0
ファイル: cmd_inv_handler.c プロジェクト: alepom/pimidi
net_response_t * cmd_inv_handler( char *ip_address, uint16_t port, void *data )
{
	net_applemidi_command *cmd = NULL;
	net_applemidi_inv *inv = NULL;
	net_applemidi_inv *accept_inv = NULL;
	net_ctx_t *ctx = NULL;
	net_response_t *response;
	char *service_name = NULL;

	if( ! data ) return NULL;

	inv = ( net_applemidi_inv *) data;

	logging_printf( LOGGING_DEBUG, "INV(%s:%u\n ", ip_address, port );

	logging_printf( LOGGING_DEBUG, "\tname=%s\n", inv->name);
	logging_printf( LOGGING_DEBUG, "\tssrc=0x%08x\n", inv->ssrc);
	logging_printf( LOGGING_DEBUG, "\tversion=0x%08x\n", inv->version);
	logging_printf( LOGGING_DEBUG, "\tinitiator=0x%08x )\n", inv->initiator);

	ctx = net_ctx_find_by_ssrc( inv->ssrc );

	if( ! ctx )
	{
		logging_printf( LOGGING_DEBUG, "cmd_inv_hander: Registering new connection\n");
		ctx = net_ctx_register( inv->ssrc, inv->initiator, ip_address, port );

		if( ! ctx ) 
		{
			logging_printf( LOGGING_ERROR, "cmd_inv_handler: Error registering connection\n");
		}
	}

	cmd = new_net_applemidi_command( NET_APPLEMIDI_CMD_ACCEPT );

	if( ! cmd )
	{
		logging_printf( LOGGING_ERROR, "Unable to allocate memory for accept_inv command\n");
		net_ctx_reset( ctx );
		return NULL;
	}

	accept_inv = new_net_applemidi_inv();
	
	if( ! accept_inv ) {
		logging_printf( LOGGING_ERROR, "Unabled to allocate memory for accept_inv command data\n");
		free( cmd );
		net_ctx_reset( ctx );
		return NULL;
	}

	accept_inv->ssrc = ctx->send_ssrc;
	accept_inv->version = 2;
	accept_inv->initiator = ctx->initiator;
	service_name = config_get("service.name");
	if( service_name )
	{
		accept_inv->name = (char *)strdup( service_name );
	} else {
		accept_inv->name = (char *)strdup( "RaveloxMIDI" );
	}

	cmd->data = accept_inv;

	response = new_net_response();

	if( response )
	{
		int ret = 0;
		ret = net_applemidi_pack( cmd , &(response->buffer), &(response->len) );
		if( ret != 0 )
		{
			logging_printf( LOGGING_ERROR, "Unable to pack response to inv command\n");
			net_response_destroy( &response );
		}
	}

	net_applemidi_cmd_destroy( &cmd );

	return response;
}
コード例 #21
0
ファイル: remote_connection.c プロジェクト: ravelox/pimidi
void remote_connect_teardown( void )
{
	net_applemidi_inv *by = NULL;
	net_response_t *response = NULL;
	net_applemidi_command *cmd = NULL;
	char *remote_service_name = NULL;
	net_ctx_t *ctx;

	remote_service_name = config_string_get("remote.connect");

	logging_printf( LOGGING_DEBUG, "remote_connect_teardown: Disconnecting from [%s]\n", remote_service_name);

	remote_connect_wait_for_thread();

	ctx = net_ctx_find_by_name( remote_service_name );
	
	if( ! ctx )
	{
		logging_printf( LOGGING_ERROR, "remote_connect_teardown: Unable to find connection for [%s]\n", remote_service_name);
		return;
	};

	// Build the BY packet
	by = net_applemidi_inv_create();
	
	if( ! by )
	{
		logging_printf( LOGGING_ERROR, "remote_connect_teardown: Unable to allocate memory for by packet\n");
		return;
	}

	by->ssrc = ctx->send_ssrc;
	by->version = 2;
	by->initiator = ctx->initiator;

	cmd = net_applemidi_cmd_create( NET_APPLEMIDI_CMD_END );
	
	if( ! cmd ) 
	{
		logging_printf( LOGGING_ERROR, "remote_connect_teardown: Unable to create AppleMIDI command\n");
		net_applemidi_inv_destroy( &by );
		goto remote_teardown_fail;
	}

	cmd->data = by;

	response = net_response_create();

	if( response )
	{
		int ret = 0;
		ret = net_applemidi_pack( cmd , &(response->buffer), &(response->len) );
		if( ret != 0 )
		{
			logging_printf( LOGGING_ERROR, "remote_connect_teardown: Unable to pack response to by command\n");
		} else {
			net_ctx_send( ctx, response->buffer, response->len , USE_CONTROL_PORT);
			hex_dump( response->buffer, response->len );
		}
	} else {
		logging_printf( LOGGING_ERROR, "remote_connect_teardown: Unable to create response packet\n");
	}

remote_teardown_fail:
	net_response_destroy( &response );
	net_applemidi_cmd_destroy( &cmd );
}
コード例 #22
0
static void create_services(AvahiClient *c) {
    char *n, r[128];
    int ret;
    AvahiProtocol protocol;
    assert(c);

    /* If this is the first time we're called, let's create a new
     * entry group if necessary */

    if (!group)
        if (!(group = avahi_entry_group_new(c, entry_group_callback, NULL))) {
            logging_printf( LOGGING_ERROR, "avahi_entry_group_new() failed: %s\n", avahi_strerror(avahi_client_errno(c)));
            goto fail;
        }

    /* If the group is empty (either because it was just created, or
     * because it was reset previously, add our entries.  */

    if (avahi_entry_group_is_empty(group)) {
        logging_printf(LOGGING_INFO, "Adding service '%s.%s'\n", sd_name_copy, sd_service_copy );

        /* Create some random TXT data */
        snprintf(r, sizeof(r), "random=%i", rand());

	if( use_ipv4 && use_ipv6 )
	{
		protocol = AVAHI_PROTO_UNSPEC;
	} else if( use_ipv4 ) {
		protocol = AVAHI_PROTO_INET;
	} else {
		protocol = AVAHI_PROTO_INET6;
	}

        if ((ret = avahi_entry_group_add_service(group, AVAHI_IF_UNSPEC, protocol, 0,  sd_name_copy , sd_service_copy , NULL, NULL,  sd_port, "test=blah", r, NULL)) < 0) {

            if (ret == AVAHI_ERR_COLLISION)
                goto collision;

            logging_printf(LOGGING_ERROR, "Failed to add %s service: %s\n", sd_service_copy,avahi_strerror(ret));
            goto fail;
        }

        /* Tell the server to register the service */
        if ((ret = avahi_entry_group_commit(group)) < 0) {
            logging_printf(LOGGING_ERROR, "Failed to commit entry group: %s\n", avahi_strerror(ret));
            goto fail;
        }
    }

    return;

collision:

    /* A service name collision with a local service happened. Let's
     * pick a new name */
    n = avahi_alternative_service_name( sd_name_copy );
    avahi_free(sd_name_copy);
    sd_name_copy = n;

    logging_printf(LOGGING_WARN, "Service name collision, renaming service to '%s'\n", sd_name_copy );

    avahi_entry_group_reset(group);

    create_services(c);
    return;

fail:
    avahi_threaded_poll_quit(threaded_poll);
}
コード例 #23
0
ファイル: remote_connection.c プロジェクト: ravelox/pimidi
void remote_connect_sync_start( void )
{
	logging_printf( LOGGING_DEBUG, "remote_connect_sync_start: Starting sync thread\n");
	pthread_create( &sync_thread, NULL, remote_connect_sync_thread, NULL );
}
コード例 #24
0
ファイル: remote_connection.c プロジェクト: ravelox/pimidi
void remote_connect_wait_for_thread( void )
{
	logging_printf( LOGGING_DEBUG, "remote_connect_wait_for_thread: Waiting\n");
	pthread_join( sync_thread, NULL );
	logging_printf( LOGGING_DEBUG, "remote_connect_wait_for_thread: Done\n");
}
コード例 #25
0
ファイル: remote_connection.c プロジェクト: ravelox/pimidi
void remote_connect_init( void )
{
	dns_service_t *found_service = NULL;
	char *remote_service_name = NULL;
	char *client_name = NULL;
	net_response_t *response = NULL;
	net_ctx_t *ctx;
	int use_ipv4, use_ipv6;
	uint32_t initiator = 0, ssrc = 0;
	char *p1 = NULL;
	char *p2 = NULL;
	int remote_port_number = 0;


	if( ! config_is_set( "remote.connect" ) )
	{
		logging_printf(LOGGING_WARN, "remote_connect_init: Called with no remote.connect value\n");
		return;
	}

	remote_service_name = (char *) strdup( config_string_get("remote.connect") );

	logging_printf(LOGGING_DEBUG, "remote_connect_init: Looking for [%s]\n", remote_service_name);

	p1 = remote_service_name;
	p2 = p1 + strlen( remote_service_name );

	/* Work backwards to find a colon ':' */
	/* If a ']' character is found first, we'll assume this is going to be an direct connect address */

	while( p2 > p1 )
	{
		if( *p2 == ']' ) break;
		if( *p2 == ':' ) break;
		p2--;
	}



	/* If no colon ':' or ']' was found, we'll assume this is a service name to be located */
	if( p2 == p1 )
	{
		use_ipv4 = is_yes( config_string_get("service.ipv4") ) ;
		use_ipv6 = is_yes( config_string_get("service.ipv6") ) ;

		if( dns_discover_services( use_ipv4, use_ipv6 ) <= 0 )
		{
			logging_printf(LOGGING_WARN, "remote_connect_init: No services available\n");
			free( remote_service_name );
			return;
		}

		found_service = dns_discover_by_name( remote_service_name );
		goto make_remote_connection;
	}  else {
		/* If there is a colon ':', split the string to determine the port number */
		if( *p2 == ':' )
		{
			*p2='\0';
			p2++;
			remote_port_number = atoi( p2 );
			p2 = remote_service_name + strlen( remote_service_name ) - 1;
		}

		/* If there is a ']', work forwards from the start of the string to remove the '[' */
		if ( *p2 == ']' )
		{
			*p2='\0';
			while( p1 < p2 )
			{
				if( *p1 == '[' ) break;
				p1++;
			}

		}
		if( p1 == p2 )
		{
			p1 = remote_service_name;
		} else {
			*p1='\0';
			p1++;
		}

		if( remote_port_number == 0 )
		{
			logging_printf( LOGGING_ERROR, "remote_connect_init: No port number specified\n");
			free( remote_service_name );
			return;
		}

		logging_printf( LOGGING_DEBUG, "remote_connect_init: connect_string=>%s<\n", config_string_get("remote.connect") );
		logging_printf( LOGGING_DEBUG, "remote_connect_init: connect_address=>%s<, connect_port=%d\n", p1, remote_port_number );

		dns_discover_add( config_string_get("remote.connect"), p1, remote_port_number );
		found_service = dns_discover_by_name( config_string_get("remote.connect") );
	}
	

make_remote_connection:
	free( remote_service_name );

	if( ! found_service )
	{
		logging_printf(LOGGING_WARN, "remote_connect_init: No service found: %s\n", remote_service_name );
		return;
	}

	logging_printf( LOGGING_DEBUG, "remote_connect_init: Found name=\"%s\" address=[%s]:%d\n", found_service->name, found_service->ip_address, found_service->port);
	ssrc = random_number();
	initiator = random_number();

	client_name = config_string_get("service.name");

	if( !client_name )
	{
		client_name = "RaveloxMIDIClient";
	}

	response = net_response_inv( ssrc, initiator, client_name );

	if( response )
	{
		ctx = net_ctx_register( ssrc, initiator, found_service->ip_address, found_service->port, found_service->name );

		if( ! ctx )
		{
			logging_printf( LOGGING_ERROR, "remote_connect_init: Unable to create socket context\n");
		} else {
			ctx->send_ssrc = ssrc;
			ctx->status = NET_CTX_STATUS_FIRST_INV;
			logging_printf( LOGGING_DEBUG, "remote_connect_init: Sending INV request to [%s]:%d\n", ctx->ip_address, ctx->control_port );
			net_ctx_send( ctx, response->buffer, response->len , USE_CONTROL_PORT );
		}
	}

	net_response_destroy( &response );
}
コード例 #26
0
ファイル: midi_journal.c プロジェクト: ravelox/pimidi
void channel_pack( channel_t *channel, char **packed, size_t *size )
{
	unsigned char *packed_channel_header = NULL;
	unsigned char *packed_chapter_n = NULL;
	unsigned char *packed_chapter_c = NULL;
	unsigned char *packed_chapter_p = NULL;
	
	size_t packed_channel_header_size = 0;
	size_t packed_chapter_n_size = 0;
	size_t packed_chapter_c_size = 0;
	size_t packed_chapter_p_size = 0;

	char *p = NULL;

	*packed = NULL;
	*size = 0;

	if( ! channel ) return;

	channel->header->len = CHANNEL_HEADER_PACKED_SIZE;
	logging_printf(LOGGING_DEBUG, "channel_pack: channel->header->len=%u\n", channel->header->len);

// The order of chapters is: PCMWNETA
	if( channel->chapter_p )
	{
		chapter_p_pack( channel->chapter_p, &packed_chapter_p, &packed_chapter_p_size );
		channel->header->len += packed_chapter_p_size;
		logging_printf(LOGGING_DEBUG, "channel_pack: packed_chapter_p_size=%u channel->header->len=%u\n", packed_chapter_p_size,channel->header->len);
	}

	if( channel->chapter_c )
	{
		chapter_c_pack( channel->chapter_c, &packed_chapter_c, &packed_chapter_c_size );
		channel->header->len += packed_chapter_c_size;
		logging_printf(LOGGING_DEBUG, "channel_pack: packed_chapter_c_size=%u channel->header->len=%u\n", packed_chapter_c_size,channel->header->len);
	}

	if( channel->chapter_n )
	{
		chapter_n_pack( channel->chapter_n, &packed_chapter_n, &packed_chapter_n_size );
		channel->header->len += packed_chapter_n_size;
		logging_printf(LOGGING_DEBUG, "channel_pack: packed_chapter_n_size=%u channel->header->len=%u\n", packed_chapter_n_size,channel->header->len);
	}


	channel_header_dump( channel->header );
	channel_header_pack( channel->header, &packed_channel_header, &packed_channel_header_size );
	logging_printf(LOGGING_DEBUG, "channel_pack: packed_channel_header_size=%u channel->header->len=%u\n", packed_channel_header_size,channel->header->len);

	*packed = ( char * ) malloc( packed_channel_header_size + packed_chapter_n_size + packed_chapter_c_size + packed_chapter_p_size );

	if( ! packed ) goto channel_pack_cleanup;

	p = *packed;

	memcpy( p, packed_channel_header, packed_channel_header_size );
	*size += packed_channel_header_size;
	p += packed_channel_header_size;
	
// The order of chapters is: PCMWNETA
	if( packed_chapter_p_size > 0 )
	{
		memcpy( p, packed_chapter_p, packed_chapter_p_size );
		*size += packed_chapter_p_size;
		p += packed_chapter_p_size;
	}

	if( packed_chapter_c_size > 0 )
	{
		memcpy( p, packed_chapter_c, packed_chapter_c_size );
		*size += packed_chapter_c_size;
		p += packed_chapter_c_size;
	}

	if( packed_chapter_n_size > 0 )
	{
		memcpy( p, packed_chapter_n, packed_chapter_n_size );
		*size += packed_chapter_n_size;
		p += packed_chapter_n_size;
	}

channel_pack_cleanup:
	FREENULL( "packed_channel_header", (void **)&packed_channel_header );
	FREENULL( "packed_chapter_n", (void **)&packed_chapter_n );
	FREENULL( "packed_chapter_c", (void **)&packed_chapter_c );
	FREENULL( "packed_chapter_p", (void **)&packed_chapter_p );
}