void destroy_test_slave(LINX * linx, LINX_SPID ts)
{
	union LINX_SIGNAL *sig;
	LINX_SIGSELECT any_sig[] = { 0 };

	sig = linx_alloc(linx, sizeof(LINX_SIGSELECT), ATTACH_SLAVE_SIG);
	linx_attach(linx, &sig, ts);

	sig = linx_alloc(linx, sizeof(LINX_SIGSELECT), TERMINATE_REQ);
	TRACE(1, "Terminate request");
	linx_send(linx, &sig, ts);

	linx_receive(linx, &sig, any_sig);

	if (sig->sigNo != ATTACH_SLAVE_SIG) {
		ERR("Wrong signal received while waiting for attach signal"
		    " from test slave. %d", sig->sigNo);
	}
	linx_free_buf(linx, &sig);
}
int OseGW_PLT_AttachReply_cbk(int skt, int len, char *payload,
                              struct ClientInfo *cinfo)
{
	OseGW_UL payload_len = sizeof(struct OseGW_AttachReply);
	struct OseGW_TransportData *reply = NULL;
	struct OseGW_AttachRequest *attach_request = NULL;
	int status = 0;
	PROCESS pid;
	union LINX_SIGNAL *signal;
	LINX_OSATTREF attref;
	int size = 0;

	size = sizeof(struct OseGW_TransportHdr) + payload_len;
	reply = (struct OseGW_TransportData *)malloc(size);
	if (reply == NULL) {
		syslog(LOG_ERR, "Malloc failure in Attach reply ");
		return -1;
	}

	attach_request = (struct OseGW_AttachRequest *)payload;
	pid = ntohl(attach_request->pid);
	attach_request->sig_len = ntohl(attach_request->sig_len);
	LOG(LOG_INFO, "Gateway Client: attaching to %#x", pid);
	if (attach_request->sig_len) {
		signal = linx_alloc(cinfo->linx, attach_request->sig_len,
				    ntohl(attach_request->sig_no));
		if (signal == LINX_NIL) {
			syslog(LOG_ERR, "Linx alloc failed in Attach "
                               "reply");
			free(reply);
			return -1;
		}
		memcpy(&((char *) signal)[sizeof(SIGSELECT)],
		       attach_request->sig_data,
		       attach_request->sig_len - sizeof(SIGSELECT));
		attref = linx_attach(cinfo->linx, &signal, pid);
	} else {
		attref = linx_attach(cinfo->linx, NULL, pid);
	}

	if (attref == LINX_ILLEGAL_ATTREF) {
	        free(reply);
		return -1;
	}
	/* Fill the header */
	reply->hdr.payload_type = htonl(OseGW_PLT_AttachReply);
	reply->hdr.payload_len = htonl(sizeof(struct OseGW_AttachReply));
	/* Fill the payload */
	reply->payload.attach_reply.status = htonl(cinfo->status);
	reply->payload.attach_reply.attref = htonl(attref);
	/*Send */
	size = sizeof(struct OseGW_TransportHdr) + payload_len;
	status = send(skt, (void *) reply, size, 0);
	if (status == size) {
		LOG(LOG_INFO, "Gateway Client: replying AttachReply "
                    "on socket %d", skt);
	} else {
		syslog(LOG_INFO, "Gateway Client: failed replying "
		       "AttachReply on socket %d",  skt);
		status = -1;
	}
	free(reply);
	return status;
}
int main(int argc, char *argv[])
{
	LINX *linx;
	LINX_SPID server_spid;
	union LINX_SIGNAL *sig;
	pthread_t server_th;
	int c;
	int loop_cnt = LOOP_CNT;
	int use_linx_api = LINX_SOCKET;
	size_t msg_size = BURST_SIZE;
	unsigned long burst_cnt = BURST_CNT;
	size_t start_msg_size = START_MSG_SIZE;
	size_t end_msg_size = END_MSG_SIZE;
	unsigned long throughput_instances = THROUGHPUT_INSTANCES;
	int iterations = ITERATIONS;
	LINX_SIGSELECT any_sig[] = { 0 };

	char *path = NULL;
	char *server_name = NULL;
	int run_attach_test = 0;
	int run_com_test = 0;
	int kill_server = 0;
	int all = 0;
	int use_pthreads = 0;

	if (argc < 2) {
		print_usage(argv[0]);
		return 0;
	}

	while ((c = getopt(argc, argv, "S?p:ac:n:m:b:i:s:e:Alt:qP")) != -1) {
		switch (c) {
		case 'S':
			/* Start server */
			server_name = (optarg == NULL ? SERVER_NAME : optarg);
			break;

		case 'P':
			/* Start server as posix thread */
			server_name = SERVER_NAME;
			use_pthreads = 1;
			break;

		case 'p':
			/* Hunt path */
			path = optarg;
			break;

		case 'a':
			/* Run attach test */
			run_attach_test = 1;
			break;

		case 'c':
			/* Connection test */
			run_com_test = atoi(optarg);
			break;

		case 'n':
			/* Loop count */
			loop_cnt = atoi(optarg);
			break;

		case 'm':
			/* Message size */
			msg_size = atol(optarg);
			break;

		case 'b':
			/* Burst count */
			burst_cnt = atol(optarg);
			break;

		case 'i':
			/* Iterations */
			iterations = atoi(optarg);
			break;

		case 's':
			/* Start message size */
			start_msg_size = atol(optarg);
			break;

		case 'e':
			/* End message size */
			end_msg_size = atol(optarg);
			break;

		case 'A':
			/* Run all tests */
			all = 1;
			break;

		case 'l':
			/* Use linx api in tests */
			use_linx_api = LINX_API;
			break;

		case 't':
			/* Number of instances in throughput */
			throughput_instances = atoi(optarg);
			break;

		case 'q':
			/* Quit the server */
			kill_server = 1;
			break;
		default:
			print_usage(argv[0]);
			return 0;
		}
	}

	if(use_pthreads) {
		kill_server = 1;
		if (pthread_create(&server_th, NULL, server,
				   (void *)server_name)) {
			fprintf(stderr, "pthread_create(): %d\n", errno);
			exit(errno);
		}
	} else if (server_name != NULL) {
		(void)server(server_name);
		return 0;
	}

	/* Path to server */
	path = path && *path ? path : CS_PATH SERVER_NAME;

	/* Hunt for server */
	linx = linx_open(CLIENT_NAME, 0, NULL);
	linx_hunt(linx, path, NULL);
	linx_receive_w_tmo(linx, &sig, 1000, any_sig);
	if (sig == NULL) {
		printf("Hunt failed. No server found at path '%s'.\n"
		       "Is the server started and path ok? "
		       "(Server started with -S option)\n", path);
		linx_close(linx);
		return 1;
	}
	if (sig->sigNo != LINX_OS_HUNT_SIG) {
		ERR("Failed to hunt for '%s'", path);
		linx_free_buf(linx, &sig);
		linx_close(linx);
		return 1;
	}
	server_spid = linx_sender(linx, &sig);
	linx_free_buf(linx, &sig);

	/* Attach to server */
	sig = linx_alloc(linx, sizeof(LINX_SIGSELECT), ATTACH_SERV_SIG);
	linx_attach(linx, &sig, server_spid);

	if (run_attach_test) {
		attach_test(linx, path, loop_cnt, server_spid, use_linx_api,
			    use_pthreads);
	}

	switch (run_com_test) {
	case 1:
		/* Start com test 1 */
		linx_bmark_latency(linx, path, loop_cnt, msg_size, msg_size,
				   ONE_ITERATION, server_spid, use_linx_api,
				   use_pthreads);
		break;
	case 2:
		/* Start com test 2 */
		linx_bmark_burst(linx, path, loop_cnt, msg_size,
				 msg_size, ONE_ITERATION,
				 burst_cnt, server_spid, use_linx_api,
				 use_pthreads);
		break;
	case 3:
		/* Start com test 3 */
		linx_bmark_latency(linx, path, loop_cnt, start_msg_size,
				   end_msg_size, iterations, server_spid,
				   use_linx_api, use_pthreads);
		break;
	case 4:
		/* Start com test 4 */
		linx_bmark_burst(linx, path, loop_cnt, start_msg_size,
				 end_msg_size, iterations, burst_cnt,
				 server_spid, use_linx_api, use_pthreads);
		break;
	case 5:
		/* Start com test 5 */
		linx_bmark_throughput(path, loop_cnt, msg_size,
				      server_spid, use_linx_api,
				      throughput_instances, use_pthreads);
		break;
	default:
		break;
	}

	if (all) {
		/* All tests  */
		attach_test(linx, path, loop_cnt, server_spid, use_linx_api,
			    use_pthreads);
		linx_bmark_latency(linx, path, loop_cnt, msg_size, msg_size,
				   ONE_ITERATION, server_spid, use_linx_api,
				   use_pthreads);
		linx_bmark_burst(linx, path, loop_cnt, msg_size, msg_size,
				 ONE_ITERATION, burst_cnt,
				 server_spid, use_linx_api, use_pthreads);
		linx_bmark_latency(linx, path, loop_cnt, start_msg_size,
				   end_msg_size, iterations,
				   server_spid, use_linx_api, use_pthreads);
		linx_bmark_burst(linx, path, loop_cnt, start_msg_size,
				 end_msg_size, iterations, burst_cnt,
				 server_spid, use_linx_api, use_pthreads);
		linx_bmark_throughput(path, loop_cnt, msg_size,
				      server_spid, use_linx_api,
				      throughput_instances, use_pthreads);
	}

	if (kill_server) {
		/* If no test argument specified, let server close */
		sig = linx_alloc(linx, sizeof(LINX_SIGSELECT), CONN_TERM);
		linx_send(linx, &sig, server_spid);
		printf("Waiting for attach from server.\n");
		linx_receive(linx, &sig, any_sig);
		if (sig == LINX_NIL) {
			ERR("No attach signal was received from the server.");
		}
		if (sig->sigNo != ATTACH_SERV_SIG) {
			ERR("Wrong signal received while waiting for "
			    "attach signal from server.");
		}
		linx_free_buf(linx, &sig);

		/* Close client spid */
		linx_close(linx);
	}

	if(use_pthreads)
		pthread_join(server_th, NULL);
	
	return 0;
}