⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sel_clnt.c

📁 操作系统SunOS 4.1.3版本的源码
💻 C
📖 第 1 页 / 共 2 页
字号:
	    seln_null_holder;	return result;    }    return result;}/* VARARGS0 */Seln_resultseln_debug(va_alist)va_dcl{    Seln_request          buffer;    va_list		valist;    char                **requestp;    if (service == (CLIENT *)NULL) {	if ((service = seln_get_service(&service_socket)) == (CLIENT *) NULL) {	    return SELN_FAILED;	}    }    buffer.replier = 0;    buffer.requester.consume = 0;    buffer.requester.context = 0;    buffer.addressee = service_holder.access.client;    buffer.rank = SELN_UNKNOWN;    buffer.status = SELN_SUCCESS;    va_start(valist);    if (attr_make_count((char **)(LINT_CAST(buffer.data)),     	SELN_BUFSIZE / sizeof(char *), valist,	(int *)(LINT_CAST(&(buffer.buf_size)))) == NULL)  {		complain("Debug request wouldn't fit in buffer");		return SELN_FAILED;    }    va_end(valist);    if (clnt_call(service, SELN_CLNT_REQUEST, xdr_seln_request,			   &buffer, xdr_seln_reply, &buffer, seln_std_timeout)	!= RPC_SUCCESS) {	return SELN_FAILED;    }    requestp = (char **) (LINT_CAST(buffer.data));    if (*requestp++ != (char *) SELN_REQ_YIELD) {	return SELN_FAILED;    }    return (Seln_result) *requestp;}voidseln_use_test_service(){    seln_svc_program |= SELN_SVC_TEST;}voidseln_use_timeout(secs)    int                   secs;{    seln_std_timeout.tv_sec = secs;}/* *	Clear_functions:  tell the service all function keys are up */voidseln_clear_functions(){    if (service == (CLIENT *)NULL) {	if ((service = seln_get_service(&service_socket)) == (CLIENT *)NULL) {	    return;	}    }    if (clnt_call(service, SELN_SVC_CLEAR_FUNCTIONS, xdr_void, 0,		  xdr_void, 0, seln_std_timeout) != RPC_SUCCESS) {	clnt_perror(service, "Couldn't tell service to clear functions");    }}Seln_resultseln_stop(auth)    int                 auth;{    if (service == (CLIENT *)NULL) {	if ((service = seln_get_service(&service_socket)) == (CLIENT *)NULL) {	    return SELN_FAILED;	}    }    if (clnt_call(service, SELN_SVC_STOP, xdr_enum, &auth,		  xdr_void, 0, seln_std_timeout)	!= RPC_SUCCESS) {	clnt_perror(service, "Couldn't tell service to stop");	return SELN_FAILED;    } else {	return SELN_SUCCESS;    }}/*	Now calls to other holders * *	Send a request concerning the selection to its holder */Seln_resultseln_request(holder, buffer)    Seln_holder          *holder;    Seln_request         *buffer;{    CLIENT               *client;    Seln_access          *access;    int                   sock = RPC_ANYSOCK;    enum clnt_stat        result;    if (seln_holder_same_process(holder)) {        return seln_local_request(holder, buffer);    }    access = &holder->access;    if (kill(access->pid, 0) == -1 && errno == ESRCH) {	return SELN_NON_EXIST;    }    client = clnttcp_create(&access->tcp_address, access->program,			    SELN_VERSION, &sock, sizeof (Seln_request),			    sizeof (Seln_request));    if (client == NULL) {	clnt_pcreateerror("Seln_request");	complain("Couldn't get client handle for current holder");	return SELN_FAILED;    }    result = clnt_call(client, SELN_CLNT_REQUEST, xdr_seln_request,		       buffer, xdr_seln_reply, buffer, seln_std_timeout);    if (result != RPC_SUCCESS) {	clnt_perror(client, "Request to current holder failed");	clnt_destroy(client);	(void)close(sock);	return SELN_FAILED;    }    clnt_destroy(client);    (void)close(sock);    return SELN_SUCCESS;}/*	short-circuit net if holder of selection is *	in the same process as requester *//*ARGSUSED*/static Seln_resultseln_local_request(holder, buffer)    Seln_holder          *holder;    Seln_request         *buffer;{    Seln_request          request;    Seln_replier_data     replier_info;    request = *buffer;    (void)seln_init_reply(&request, buffer, &replier_info);    if (buffer->requester.consume) {	do {	    if (seln_get_reply_buffer(buffer) != SELN_SUCCESS) {		return SELN_FAILED;	    }	    if (buffer->requester.consume(buffer) == SELN_CANCEL) {		*buffer->replier->request_pointer = 		    (char *) SELN_REQ_END_REQUEST;		(void) seln_get_reply_buffer(buffer);		return SELN_SUCCESS;	    }	} while (buffer->status == SELN_CONTINUED);	return SELN_SUCCESS;    }    if (seln_get_reply_buffer(buffer) != SELN_SUCCESS) {	return SELN_FAILED;    }    if (buffer->status == SELN_CONTINUED) {	(void) seln_get_reply_buffer(buffer);	return SELN_FAILED;    }    return SELN_SUCCESS;}/* *	Procedures which get called remotely *//*	seln_dispatch is called by rpc dispatcher, and in turn calls *	the appropriate response function below; *	that will (typically) call a client callback proc. */static voidseln_dispatch(request, transport)    struct svc_req     *request;    SVCXPRT            *transport;{    switch (request->rq_proc) {      case SELN_SVC_NULLPROC:	if (!svc_sendreply(transport, xdr_void, (char *)0)) {	    complain("Couldn't reply to RPC call");	}	return;      case SELN_CLNT_DO_FUNCTION:	seln_do_function(transport);	return;      case SELN_CLNT_REQUEST:	seln_do_reply(transport);	return;      default:	svcerr_noproc(transport);	return;    }}/* *	Client internal routines */static voidseln_update_service(rank)    Seln_rank           rank;{    Seln_holder         holder;    Seln_result		result;    holder = seln_null_holder;    holder.rank = rank;    (void) clnt_call(service, SELN_SVC_ACQUIRE, xdr_seln_holder, &holder,		     xdr_enum, &result, seln_std_timeout);}static Seln_seize_resultseln_seize(client_data, asked, given)    char                 *client_data;    Seln_rank             asked, *given;{    Seln_result           result;    Seln_holder           holder;    *given = asked;    /* Ask the current holder for it	 */    holder = seln_holder_of_rank(given);    if (holder.state != SELN_EXISTS) {	return Seln_seized_ok;    }    if (seln_holder_same_client(&holder, client_data)) {	return Seln_seized_self;    }    if (kill(holder.access.pid, 0) == -1 && errno == ESRCH) {	seln_update_service(holder.rank);	return Seln_seized_ok;    }    switch (result = seln_send_yield(holder.rank, &holder, FALSE)) {      case SELN_SUCCESS:	return Seln_seized_ok;      case SELN_WRONG_RANK:	       /* server's behind; try again	 */	if (*given == SELN_PRIMARY && asked != SELN_SECONDARY) {	    *given = SELN_SECONDARY;	    holder = seln_holder_of_rank(given);	    if (holder.state != SELN_EXISTS) {		return Seln_seized_ok;	    }	    if (seln_holder_same_client(&holder, client_data)) {		return Seln_seized_self;	    }	    result = seln_send_yield(holder.rank, &holder, TRUE);	} else {	    complain("Other holder confused about selection ranks");	    return Seln_seized_blind;	}	if (result == SELN_SUCCESS) {	    return Seln_seized_ok;	}			       /* else FALL THROUGH  */    }    return Seln_seized_blind;}/* *	Initialize the per-process communication information */static intseln_init_holder_process(){    if ((service = seln_get_service(&service_socket)) == (CLIENT *) NULL) {	return FALSE;    }    if (seln_get_service_holder(&service_holder) != SELN_SUCCESS) {	clnt_destroy(service);	(void)close(service_socket);	service = (CLIENT *) NULL;	service_socket = 0;	return FALSE;    }    if ((seln_my_udp_transport = svcudp_bufcreate(RPC_ANYSOCK,					SELN_RPC_BUFSIZE, SELN_RPC_BUFSIZE))	== (SVCXPRT *) NULL) {	complain("Couldn't get a UDP transport for requesters to talk to us");	return FALSE;    }    seln_my_udp_socket = seln_my_udp_transport->xp_sock;    if (seln_get_access(&seln_my_access) == SELN_FAILED) {	return FALSE;    }    if (!svc_register(seln_my_udp_transport, seln_my_access.program, SELN_VERSION,		      seln_dispatch, NO_PMAP)) {	complain("Couldn't register transport for requesters to talk to us");	svc_destroy(seln_my_udp_transport);	(void)close(seln_my_udp_socket);	return FALSE;    }    (void) notify_set_input_func((Notify_client) seln_my_udp_transport,				 seln_listener, seln_my_udp_socket);    if (seln_get_tcp(seln_my_access.program, seln_dispatch) != SELN_SUCCESS) {    		complain("Couldn't TCP transport for requesters to talk to us");	svc_destroy(seln_my_udp_transport);	(void)close(seln_my_udp_socket);	return FALSE;    }    return TRUE;}static CLIENT *seln_get_service(s)    int                *s;{    struct sockaddr_in  address;    *s = RPC_ANYSOCK;    get_myaddress(&address);    address.sin_port = 0;    return clntudp_bufcreate(&address, seln_svc_program, SELN_VERSION,		  seln_std_timeout, s, SELN_RPC_BUFSIZE, SELN_RPC_BUFSIZE);}static Seln_resultseln_get_service_holder(holder)    Seln_holder	*holder;{    if (clnt_call(service, SELN_SVC_GET_HOLDER, xdr_void, 0,		  xdr_seln_holder, holder, seln_std_timeout)	!= RPC_SUCCESS) {	clnt_perror(service, "No selection service available");	return SELN_FAILED;    } else {	return SELN_SUCCESS;    }}static Seln_resultseln_get_access(access)    Seln_access        *access;{    struct sockaddr_in *addr;    access->pid = getpid();    addr = &access->udp_address;    get_myaddress(addr);    addr->sin_port =  htons(seln_my_udp_transport->xp_port);    access->program = SELN_LIB_PROGRAM;    return SELN_SUCCESS;}static Seln_holderseln_holder_of_rank(rank)    Seln_rank          *rank;{    enum clnt_stat      result;    Seln_holder         holder;    result = clnt_call(service, SELN_SVC_INQUIRE, xdr_enum, rank,		       xdr_seln_holder, &holder, seln_std_timeout);    if (result != RPC_SUCCESS) {	clnt_perror(service, "Couldn't get current holder from service");	return seln_null_holder;    }    *rank = holder.rank;    return holder;}static voidseln_client_remove(target)    Seln_client_node          *target;{    register Seln_client_node *prev;    for (prev = &clients;	 prev->next != (Seln_client_node *) NULL;	 prev = prev->next) {	if (prev->next == target) {	    prev->next = target->next;	    free((char *)(LINT_CAST(target)));	    return;	}    }    complain("Destroying a non-existent client?");}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -