void echo_dgram() { int sock; char buf[XIA_MAXBUF]; sockaddr_x cdag; socklen_t dlen; int n; say("Datagram service started\n"); if ((sock = Xsocket(AF_XIA, SOCK_DGRAM, 0)) < 0) die(-2, "unable to create the datagram socket\n"); struct addrinfo *ai; if (Xgetaddrinfo(NULL, SID_DGRAM, NULL, &ai) != 0) die(-1, "getaddrinfo failure!\n"); sockaddr_x *sa = (sockaddr_x*)ai->ai_addr; Graph g((sockaddr_x*)ai->ai_addr); printf("\nDatagram DAG\n%s\n", g.dag_string().c_str()); if (XregisterName(DGRAM_NAME, sa) < 0 ) die(-1, "error registering name: %s\n", DGRAM_NAME); say("registered name: \n%s\n", DGRAM_NAME); if (Xbind(sock, (sockaddr *)sa, sizeof(sa)) < 0) { die(-3, "unable to bind to the dag\n"); } pid_t pid = 0; // only need to fork if doing stream echo at the same time if (stream == 1) pid = fork(); if (pid == 0) { while (1) { say("Dgram Server waiting\n"); dlen = sizeof(cdag); memset(buf, 0, sizeof(buf)); if ((n = Xrecvfrom(sock, buf, sizeof(buf), 0, (struct sockaddr *)&cdag, &dlen)) < 0) { warn("Recv error on socket %d, closing connection\n", pid); break; } say("dgram received %d bytes\n", n); if ((n = Xsendto(sock, buf, n, 0, (struct sockaddr *)&cdag, dlen)) < 0) { warn("%5d send error\n", pid); break; } say("dgram sent %d bytes\n", n); } Xclose(sock); } }
/* ** do one send/receive operation on the specified socket */ int process(int sock) { int size; int sent, received; char tdag[1024]; size_t dlen; char buf1[XIA_MAXBUF], buf2[XIA_MAXBUF]; if (pktSize == 0) size = (rand() % XIA_MAXBUF) + 1; else size = pktSize; randomString(buf1, size); if ((sent = Xsendto(sock, buf1, size, 0, sdag, strlen(sdag)+1)) < 0) { die(-4, "Send error %d on socket %d\n", errno, sock); } say("Xsock %4d sent %d bytes\n", sock, sent); memset(buf2, sizeof(buf2), 0); dlen = sizeof(tdag); if ((received = Xrecvfrom(sock, buf2, sizeof(buf2), 0, tdag, &dlen)) < 0) die(-5, "Receive error %d on socket %d\n", errno, sock); say("Xsock %4d received %d bytes\n", sock, received); if (sent != received || strcmp(buf1, buf2) != 0) { warn("Xsock %4d received data different from sent data! (bytes sent/recv'd: %d/%d)\n", sock, sent, received); } return 0; }
int main(int argc, char *argv[]) { int sock, n, chunkSock, acceptSock; size_t dlen; char buf[1024],theirDAG[1024]; //char* reply="Got your message"; char reply[1024]; pid_t pid; char myAD[1024]; char myHID[1024]; //Open socket sock=Xsocket(XSOCK_DGRAM); if (sock < 0) error("Opening socket"); // read the localhost AD and HID if ( XreadLocalHostAddr(sock, myAD, sizeof(myAD), myHID, sizeof(myHID)) < 0 ) error("Reading localhost address"); // make the src DAG (the one the server listens on) char * dag = (char*) malloc(snprintf(NULL, 0, "RE %s %s %s", myAD, myHID, SID0) + 1); sprintf(dag, "RE %s %s %s", myAD, myHID, SID0); //Register this service name to the name server char * sname = (char*) malloc(snprintf(NULL, 0, "%s", SNAME) + 1); sprintf(sname, "%s", SNAME); if (XregisterName(sname, dag) < 0 ) error("name register"); //Bind to the DAG Xbind(sock,dag); while (1) { //Receive packet memset(&buf[0], 0, sizeof(buf)); dlen = sizeof(theirDAG); n = Xrecvfrom(sock,buf,1024,0,theirDAG,&dlen); //n = Xrecv(acceptSock,buf,1024,0); if (n < 0) error("recvfrom"); //printf("\nReceived a datagram from:%s len %d strlen %d\n",theirDAG, (int)dlen, (int)strlen(theirDAG)); write(1,buf,n); memset(&reply[0], 0, sizeof(reply)); strcat (reply, "Got your message: "); strcat (reply, buf); //Reply to client Xsendto(sock,reply,strlen(reply)+1,0,theirDAG,strlen(theirDAG)); //Xsend(acceptSock,reply,strlen(reply),0); } return 0; }
int main(int argc, char *argv[]) { int sock, n; size_t dlen; char reply[128]; char buffer[2048],theirDAG[1024]; //Open socket sock=Xsocket(XSOCK_DGRAM); if (sock < 0) error("Opening socket"); //Name query to the name server char * sname = (char*) malloc(snprintf(NULL, 0, "%s", SNAME) + 1); sprintf(sname, "%s", SNAME); char * dag = XgetDAGbyName(sname); while(1) { printf("\nPlease enter the message (0 to exit): "); bzero(buffer,2048); fgets(buffer,2048,stdin); if (buffer[0]=='0'&&strlen(buffer)==2) break; //Use Xconnect() with Xsend() //Xsend(sock,buffer,strlen(buffer),0); //Or use Xsendto() Xsendto(sock,buffer,strlen(buffer),0,dag,strlen(dag)+1); printf("Sent\n"); //Process reply from server dlen = sizeof(theirDAG); n = Xrecvfrom(sock,reply,128,0,theirDAG,&dlen); //n = Xrecv(sock,reply,128,0); if (n < 0) error("recvfrom"); //printf("Received a datagram from:%s\n",theirDAG); write(1,reply,n); printf("\n"); } Xclose(sock); return 0; }
/* ** do one send/receive operation on the specified socket */ int process(int sock) { int size; int sent, received, rc; char buf1[XIA_MAXBUF], buf2[XIA_MAXBUF]; if (pktSize == 0) size = (rand() % XIA_MAXBUF) + 1; else size = pktSize; randomString(buf1, size); if ((sent = Xsendto(sock, buf1, size, 0, (sockaddr*)sa, sizeof(sockaddr_x))) < 0) { die(-4, "Send error %d on socket %d\n", errno, sock); } say("Xsock %4d sent %d bytes\n", sock, sent); struct pollfd pfds[2]; pfds[0].fd = sock; pfds[0].events = POLLIN; if ((rc = Xpoll(pfds, 1, 5000)) <= 0) { die(-5, "Poll returned %d\n", rc); } memset(buf2, 0, sizeof(buf2)); if ((received = Xrecvfrom(sock, buf2, sizeof(buf2), 0, NULL, NULL)) < 0) die(-5, "Receive error %d on socket %d\n", errno, sock); say("Xsock %4d received %d bytes\n", sock, received); if (sent != received || strcmp(buf1, buf2) != 0) { warn("Xsock %4d received data different from sent data! (bytes sent/recv'd: %d/%d)\n", sock, sent, received); } return 0; }
static int udp_tl_keepalive(void) { char buf[4] = "jaK"; eXosip_reg_t *jr; if (eXosip.keep_alive <= 0) { return 0; } if (udp_socket <= 0) return OSIP_UNDEFINED_ERROR; for (jr = eXosip.j_reg; jr != NULL; jr = jr->next) { if (jr->len > 0) { if (Xsendto(udp_socket, (const void *) buf, 4, 0, (struct sockaddr *) &(jr->addr), jr->len) > 0) { OSIP_TRACE(osip_trace (__FILE__, __LINE__, OSIP_INFO1, NULL, "eXosip: Keep Alive sent on UDP!\n")); } } } return OSIP_SUCCESS; }
/*! ** @brief Register a service or hostname with the name server. ** ** Register a host or service name with the XIA nameserver. ** By convention services are indicated by '_s' appended to the service name. ** The memory returned is dynamically allocated and should be released with a ** call to free() when the caller is done with it. ** ** This is a very simple implementation and will be replaced in a ** future release. This version does not check correctness of the name or dag, ** nor does it check to ensure that the client is allowed to bind to name. ** ** @param name - The name of an XIA service or host. ** @param DAG - the DAG to be bound to name. ** ** @returns 0 on success ** @returns -1 on failure with errno set ** */ int XregisterName(const char *name, sockaddr_x *DAG) { int sock; sockaddr_x ns_dag; char pkt[NS_MAX_PACKET_SIZE]; char _name[NS_MAX_DAG_LENGTH], _dag[NS_MAX_DAG_LENGTH]; int result; if ((sock = Xsocket(AF_XIA, SOCK_DGRAM, 0)) < 0) return -1; //Read the nameserver DAG (the one that the name-registration will be sent to) if (XreadNameServerDAG(sock, &ns_dag) < 0) { LOG("Unable to find nameserver address"); errno = NO_RECOVERY; return -1; } if (!DAG) { errno = EINVAL; return -1; } Graph g(DAG); if (g.num_nodes() <= 0) { errno = EINVAL; return -1; } //Construct a registration packet ns_pkt register_pkt; register_pkt.type = NS_TYPE_REGISTER; register_pkt.name = strdup(name); register_pkt.dag = strdup(g.dag_string().c_str()); memset(pkt, 0, sizeof(pkt)); int offset = 0; memcpy(pkt, ®ister_pkt.type, sizeof(register_pkt.type)); offset += sizeof(register_pkt.type); memcpy(pkt+offset, register_pkt.name, strlen(register_pkt.name)+1); offset += strlen(register_pkt.name)+1; memcpy(pkt+offset, register_pkt.dag, strlen(register_pkt.dag)+1); offset += strlen(register_pkt.dag)+1; //Send the name registration packet to the name server //FIXME: use sockaddr here Xsendto(sock, pkt, offset, 0, (const struct sockaddr *)&ns_dag, sizeof(sockaddr_x)); //Check the response from the name server memset(pkt, 0, sizeof(pkt)); int rc = Xrecvfrom(sock, pkt, NS_MAX_PACKET_SIZE, 0, NULL, NULL); if (rc < 0) { perror("recvfrom"); } memset(_name, '\0', NS_MAX_DAG_LENGTH); memset(_dag, '\0', NS_MAX_DAG_LENGTH); ns_pkt *tmp = (ns_pkt *)pkt; char* tmp_name = (char*)(pkt+sizeof(tmp->type)); char* tmp_dag = (char*)(pkt+sizeof(tmp->type)+ strlen(tmp_name)+1); switch (tmp->type) { case NS_TYPE_RESPONSE: sprintf(_name, "%s", tmp_name); sprintf(_dag, "%s", tmp_dag); result = 0; break; case NS_TYPE_RESPONSE_ERROR: result = -1; break; default: fprintf(stderr, "dafault\n"); result = -1; break; } free(register_pkt.name); free(register_pkt.dag); Xclose(sock); return result; }
/*! ** @brief Lookup a DAG based using a host or service name. ** ** The name should be a string such as www_s.example.xia or host.example.xia. ** By convention services are indicated by '_s' appended to the service name. ** The memory returned is dynamically allocated and should be released with a ** call to free() when the caller is done with it. ** ** This is a very simple implementation of the name query function. ** It will be replaces in a future release. ** ** @param name The name of an XIA service or host. ** ** @returns a character point to the dag on success ** @returns NULL on failure ** */ int XgetDAGbyName(const char *name, sockaddr_x *addr, socklen_t *addrlen) { int sock; sockaddr_x ns_dag; char pkt[NS_MAX_PACKET_SIZE]; char *dag; char _name[NS_MAX_DAG_LENGTH], _dag[NS_MAX_DAG_LENGTH]; int result; if (!addr || !addrlen || *addrlen < sizeof(sockaddr_x)) { errno = EINVAL; return -1; } // see if name is registered in the local hosts.xia file if((dag = hostsLookup(name))) { Graph g(dag); free(dag); // check to see if the returned dag was valid // we may want a better check for this in the future if (g.num_nodes() > 0) { std::string s = g.dag_string(); g.fill_sockaddr((sockaddr_x*)addr); *addrlen = sizeof(sockaddr_x); return 0; } } // not found locally, check the name server if ((sock = Xsocket(AF_XIA, SOCK_DGRAM, 0)) < 0) return -1; //Read the nameserver DAG (the one that the name-query will be sent to) if ( XreadNameServerDAG(sock, &ns_dag) < 0 ) { LOG("Unable to find nameserver address"); errno = NO_RECOVERY; return -1; } //Construct a name-query packet ns_pkt query_pkt; query_pkt.type = NS_TYPE_QUERY; query_pkt.name = strdup(name); memset(pkt, 0, sizeof(pkt)); int offset = 0; memcpy(pkt, &query_pkt.type, sizeof(query_pkt.type)); offset += sizeof(query_pkt.type); memcpy(pkt+offset, query_pkt.name, strlen(query_pkt.name)+1); offset += strlen(query_pkt.name)+1; //Send a name query to the name server Xsendto(sock, pkt, offset, 0, (const struct sockaddr*)&ns_dag, sizeof(sockaddr_x)); //Check the response from the name server memset(pkt, 0, sizeof(pkt)); int rc = Xrecvfrom(sock, pkt, NS_MAX_PACKET_SIZE, 0, NULL, NULL); if (rc < 0) { perror("recvfrom"); } memset(_name, '\0', NS_MAX_DAG_LENGTH); memset(_dag, '\0', NS_MAX_DAG_LENGTH); ns_pkt *tmp = (ns_pkt *)pkt; char* tmp_name = (char*)(pkt+sizeof(tmp->type)); char* tmp_dag = (char*)(pkt+sizeof(tmp->type)+ strlen(tmp_name)+1); switch (tmp->type) { case NS_TYPE_RESPONSE: sprintf(_name, "%s", tmp_name); sprintf(_dag, "%s", tmp_dag); result = 1; break; case NS_TYPE_RESPONSE_ERROR: result = -1; break; default: LOG("Unknown nameserver response"); result = -1; break; } Xclose(sock); free(query_pkt.name); if (result < 0) { return result; } Graph g(_dag); g.fill_sockaddr(addr); return 0; }
static int udp_tl_send_message(osip_transaction_t * tr, osip_message_t * sip, char *host, int port, int out_socket) { int len = 0; size_t length = 0; struct addrinfo *addrinfo; /* struct __eXosip_sockaddr addr; */ sockaddr_x addr; char *message = NULL; char ipbuf[sizeof(sockaddr_x)]; int i; osip_naptr_t *naptr_record=NULL; if (udp_socket <= 0) return -1; if (host == NULL) { host = sip->req_uri->host; if (sip->req_uri->port != NULL) port = osip_atoi(sip->req_uri->port); else port = 5060; } eXtl_update_local_target(sip); i = -1; #ifndef MINISIZE if (tr==NULL) { _eXosip_srv_lookup(sip, &naptr_record); if (naptr_record!=NULL) { eXosip_dnsutils_dns_process(naptr_record, 1); if (naptr_record->naptr_state==OSIP_NAPTR_STATE_NAPTRDONE ||naptr_record->naptr_state==OSIP_NAPTR_STATE_SRVINPROGRESS) eXosip_dnsutils_dns_process(naptr_record, 1); } if (naptr_record!=NULL && naptr_record->naptr_state==OSIP_NAPTR_STATE_SRVDONE) { /* 4: check if we have the one we want... */ if (naptr_record->sipudp_record.name[0] != '\0' && naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index].srv[0] != '\0') { /* always choose the first here. if a network error occur, remove first entry and replace with next entries. */ osip_srv_entry_t *srv; int n = 0; for (srv = &naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index]; n < 10 && naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index].srv[0]; srv = &naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index]) { if (srv->ipaddress[0]) i = eXosip_get_addrinfo(&addrinfo, srv->ipaddress, srv->port, IPPROTO_UDP); else i = eXosip_get_addrinfo(&addrinfo, srv->srv, srv->port, IPPROTO_UDP); if (i == 0) { host = srv->srv; port = srv->port; break; } i = eXosip_dnsutils_rotate_srv(&naptr_record->sipudp_record); if (i<=0) { return -1; } if (i>=n) { return -1; } i = -1; /* copy next element */ n++; } } } if (naptr_record!=NULL && naptr_record->keep_in_cache==0) osip_free(naptr_record); naptr_record=NULL; } else { naptr_record = tr->naptr_record; } if (naptr_record!=NULL) { /* 1: make sure there is no pending DNS */ eXosip_dnsutils_dns_process(naptr_record, 0); if (naptr_record->naptr_state==OSIP_NAPTR_STATE_NAPTRDONE ||naptr_record->naptr_state==OSIP_NAPTR_STATE_SRVINPROGRESS) eXosip_dnsutils_dns_process(naptr_record, 0); if (naptr_record->naptr_state==OSIP_NAPTR_STATE_UNKNOWN) { /* fallback to DNS A */ if (naptr_record->keep_in_cache==0) osip_free(naptr_record); naptr_record=NULL; if (tr!=NULL) tr->naptr_record=NULL; /* must never happen? */ } else if (naptr_record->naptr_state==OSIP_NAPTR_STATE_INPROGRESS) { /* 2: keep waiting (naptr answer not received) */ return OSIP_SUCCESS + 1; } else if (naptr_record->naptr_state==OSIP_NAPTR_STATE_NAPTRDONE) { /* 3: keep waiting (naptr answer received/no srv answer received) */ return OSIP_SUCCESS + 1; } else if (naptr_record->naptr_state==OSIP_NAPTR_STATE_SRVINPROGRESS) { /* 3: keep waiting (naptr answer received/no srv answer received) */ return OSIP_SUCCESS + 1; } else if (naptr_record->naptr_state==OSIP_NAPTR_STATE_SRVDONE) { /* 4: check if we have the one we want... */ if (naptr_record->sipudp_record.name[0] != '\0' && naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index].srv[0] != '\0') { /* always choose the first here. if a network error occur, remove first entry and replace with next entries. */ osip_srv_entry_t *srv; int n = 0; for (srv = &naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index]; n < 10 && naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index].srv[0]; srv = &naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index]) { if (srv->ipaddress[0]) i = eXosip_get_addrinfo(&addrinfo, srv->ipaddress, srv->port, IPPROTO_UDP); else i = eXosip_get_addrinfo(&addrinfo, srv->srv, srv->port, IPPROTO_UDP); if (i == 0) { host = srv->srv; port = srv->port; break; } i = eXosip_dnsutils_rotate_srv(&naptr_record->sipudp_record); if (i<=0) { return -1; } if (i>=n) { return -1; } i = -1; /* copy next element */ n++; } } } else if (naptr_record->naptr_state==OSIP_NAPTR_STATE_NOTSUPPORTED ||naptr_record->naptr_state==OSIP_NAPTR_STATE_RETRYLATER) { /* 5: fallback to DNS A */ if (naptr_record->keep_in_cache==0) osip_free(naptr_record); naptr_record=NULL; if (tr!=NULL) tr->naptr_record=NULL; } } #endif /* if SRV was used, destination may be already found */ if (i != 0) { i = eXosip_get_addrinfo(&addrinfo, host, port, IPPROTO_UDP); } if (i != 0) { return -1; } memcpy(&addr, addrinfo->ai_addr, addrinfo->ai_addrlen); len = addrinfo->ai_addrlen; eXosip_freeaddrinfo(addrinfo); /* remove preloaded route if there is no tag in the To header */ { osip_route_t *route = NULL; osip_generic_param_t *tag = NULL; osip_message_get_route(sip, 0, &route); osip_to_get_tag(sip->to, &tag); if (tag == NULL && route != NULL && route->url != NULL) { osip_list_remove(&sip->routes, 0); } i = osip_message_to_str(sip, &message, &length); if (tag == NULL && route != NULL && route->url != NULL) { osip_list_add(&sip->routes, route, 0); } } if (i != 0 || length <= 0) { osip_free(message); return -1; } /* switch (((struct sockaddr *) &addr)->sa_family) { case AF_INET: inet_ntop(((struct sockaddr *) &addr)->sa_family, &(((struct sockaddr_in *) &addr)->sin_addr), ipbuf, sizeof(ipbuf)); break; case AF_INET6: inet_ntop(((struct sockaddr *) &addr)->sa_family, &(((struct sockaddr_in6 *) &addr)->sin6_addr), ipbuf, sizeof(ipbuf)); break; default: strncpy(ipbuf, "(unknown)", sizeof(ipbuf)); break; } OSIP_TRACE(osip_trace(__FILE__, __LINE__, OSIP_INFO1, NULL, "Message sent: (to dest=%s:%i)\n%s\n", ipbuf, port, message)); */ /* Graph g(&addr); char * dag_str = g.dag_string().c_str(); */ memcpy(ipbuf, &addr, len); if (osip_strcasecmp(host, ipbuf)!=0 && MSG_IS_REQUEST(sip)) { if (MSG_IS_REGISTER(sip)) { struct eXosip_dns_cache entry; memset(&entry, 0, sizeof(struct eXosip_dns_cache)); snprintf(entry.host, sizeof(entry.host), "%s", host); snprintf(entry.ip, sizeof(entry.ip), "%s", ipbuf); eXosip_set_option(EXOSIP_OPT_ADD_DNS_CACHE, (void *) &entry); } } if (tr != NULL) { if (tr->ict_context != NULL) osip_ict_set_destination(tr->ict_context, osip_strdup(ipbuf), port); if (tr->nict_context != NULL) osip_nict_set_destination(tr->nict_context, osip_strdup(ipbuf), port); } if (0 > Xsendto(udp_socket, (const void *) message, length, 0, (struct sockaddr *) &addr, len)) { #ifndef MINISIZE if (naptr_record!=NULL) { /* rotate on failure! */ if (eXosip_dnsutils_rotate_srv(&naptr_record->sipudp_record)>0) { osip_free(message); return OSIP_SUCCESS + 1; /* retry for next retransmission! */ } } #endif /* SIP_NETWORK_ERROR; */ osip_free(message); return -1; } if (eXosip.keep_alive > 0) { if (MSG_IS_REGISTER(sip)) { eXosip_reg_t *reg = NULL; if (_eXosip_reg_find(®, tr) == 0) { memcpy(&(reg->addr), &addr, len); reg->len = len; } } } #ifndef MINISIZE if (naptr_record!=NULL) { if (tr!=NULL && MSG_IS_REGISTER(sip) && tr->last_response==NULL) { /* failover for outgoing transaction */ time_t now; now = time(NULL); OSIP_TRACE(osip_trace (__FILE__, __LINE__, OSIP_INFO2, NULL, "not yet answered\n")); if (tr != NULL && now - tr->birth_time > 10 && now - tr->birth_time < 13) { /* avoid doing this twice... */ if (eXosip_dnsutils_rotate_srv(&naptr_record->sipudp_record)>0) { OSIP_TRACE(osip_trace(__FILE__, __LINE__, OSIP_INFO1, NULL, "Doing failover: %s:%i->%s:%i\n", host, port, naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index].srv, naptr_record->sipudp_record.srventry[naptr_record->sipudp_record.index].port)); osip_free(message); return OSIP_SUCCESS + 1; /* retry for next retransmission! */ } } } } #endif osip_free(message); return OSIP_SUCCESS; }
int main() { int sock; socklen_t len; char buf[XIA_MAXBUF]; sockaddr_x client; time_t now; struct tm *t; // create a datagram socket if ((sock = Xsocket(AF_XIA, SOCK_DGRAM, 0)) < 0) { printf("error: unable to create the listening socket.\n"); exit(1); } struct addrinfo *ai; if (Xgetaddrinfo(NULL, SID0, NULL, &ai) != 0) { printf("error: unable to create source dag."); exit(1); } sockaddr_x *sa = (sockaddr_x*)ai->ai_addr; //Register this service name to the name server if (XregisterName(SNAME, sa) < 0) { printf("error: unable to register name/dag combo"); exit(1); } // bind to the DAG if (Xbind(sock, (struct sockaddr*)sa, sizeof(sockaddr_x)) < 0) { Xclose(sock); printf("error: unable to bind to %s\n", SNAME); exit(1); } while (1) { len = sizeof(client); if (Xrecvfrom(sock, buf, sizeof(buf), 0, (struct sockaddr*)&client, &len) < 0) { printf("error receiving client request\n"); // assume it's ok, and just keep listening continue; } // we don't care what the client said, so we'll just ignore it now = time(NULL); t = gmtime(&now); strftime(buf, sizeof(buf), "%c %Z", t); Graph g(&client); printf("request from:\n%s\n", g.dag_string().c_str()); //Reply to client if (Xsendto(sock, buf, strlen(buf) + 1, 0, (struct sockaddr*)&client, sizeof(client)) < 0) printf("error sending time to the client\n"); } Xclose(sock); return 0; }
/*! ** @brief Lookup a DAG based using a host or service name. ** ** The name should be a string such as www_s.example.xia or host.example.xia. ** By convention services are indicated by '_s' appended to the service name. ** The memory returned is dynamically allocated and should be released with a ** call to free() when the caller is done with it. ** ** This is a very simple implementation of the name query function. ** It will be replaces in a future release. ** ** @param name The name of an XIA service or host. ** ** @returns a character point to the dag on success ** @returns NULL on failure ** */ char *XgetDAGbyName(const char *name) { int sock; char pkt[NS_MAX_PACKET_SIZE],ddag[NS_MAX_PACKET_SIZE], ns_dag[NS_MAX_PACKET_SIZE]; char *dag; char _name[NS_MAX_DAG_LENGTH], _dag[NS_MAX_DAG_LENGTH]; int result; //Open socket sock=Xsocket(XSOCK_DGRAM); //Read the nameserver DAG (the one that the name-query will be sent to) if ( XreadNameServerDAG(sock, ns_dag) < 0 ) error("Reading nameserver address"); //Construct a name-query packet ns_pkt query_pkt; query_pkt.type = NS_TYPE_QUERY; query_pkt.name = (char*)malloc(strlen(name)+1); sprintf(query_pkt.name, "%s", name); //query_pkt.dag = (char*)malloc(strlen(DAG)+1); //sprintf(query_pkt.dag, "%s", DAG); memset(pkt, 0, sizeof(pkt)); int offset = 0; memcpy(pkt, &query_pkt.type, sizeof(query_pkt.type)); offset += sizeof(query_pkt.type); memcpy(pkt+offset, query_pkt.name, strlen(query_pkt.name)+1); offset += strlen(query_pkt.name)+1; //memcpy(pkt+offset, query_pkt.dag, strlen(query_pkt.dag)+1); //offset += strlen(query_pkt.dag)+1; //Send a name query to the name server Xsendto(sock, pkt, offset, 0, ns_dag, strlen(ns_dag)+1); //Check the response from the name server memset(pkt, 0, sizeof(pkt)); memset(ddag, 0, sizeof(ddag)); size_t ddaglen = sizeof(ddag); int rc = Xrecvfrom(sock, pkt, NS_MAX_PACKET_SIZE, 0, ddag, &ddaglen); if (rc < 0) { error("recvfrom"); } memset(_name, '\0', NS_MAX_DAG_LENGTH); memset(_dag, '\0', NS_MAX_DAG_LENGTH); ns_pkt *tmp = (ns_pkt *)pkt; char* tmp_name = (char*)(pkt+sizeof(tmp->type)); char* tmp_dag = (char*)(pkt+sizeof(tmp->type)+ strlen(tmp_name)+1); switch (tmp->type) { case NS_TYPE_RESPONSE: sprintf(_name, "%s", tmp_name); sprintf(_dag, "%s", tmp_dag); result = 1; break; case NS_TYPE_RESPONSE_ERROR: result = -1; break; default: fprintf(stderr, "dafault\n"); result = -1; break; } if (result < 0) { return NULL; } dag = (char*)malloc(sizeof(_dag) + 1); strcpy(dag, _dag); //Close socket Xclose(sock); free(query_pkt.name); return dag; }