/******************************************************** Authenticate incoming request for a client salt value. Exchange looks like: 1.) Client sends request code 0x80 (SHA-1), 0x00 (version 0), 0x01 (create salt), 0xNN (security level); followed by client challenge (4 bytes, s1) 2.) Server replies with server challenge (4 bytes, s2) 3.) Client replies with hashed key & server challenge (20 bytes, s2hash) 4.) Server replies with hashed key & client challenge (20 bytes, s1hash), as well as client identifier and initial client salt. (8 bytes total). */ static const char *CcsServer_createSalt(SOCKET fd,CCS_AUTH_clients *cl, CcsSecMan *security,CcsSecAttr *attr) { ChMessageInt_t s1; ChMessageInt_t s2=ChMessageInt_new(CCS_RAND_next(&cl->rand)); SHA1_hash_t s2hash; int clientId; struct { SHA1_hash_t s1hash; ChMessageInt_t clientId; ChMessageInt_t clientSalt; } reply; if (-1==skt_recvN(fd,&s1,sizeof(s1))) return "ERROR> CreateSalt challenge recv"; if (-1==skt_sendN(fd,&s2,sizeof(s2))) return "ERROR> CreateSalt challenge send"; if (-1==skt_recvN(fd,&s2hash,sizeof(s2hash))) return "ERROR> CreateSalt reply recv"; if (CCS_AUTH_differ(security->getKey(security,attr),ChMessageInt(s2), NULL,&s2hash)) return "ERROR> CreateSalt client hash mismatch! (bad password?)"; CCS_AUTH_hash(security->getKey(security,attr),ChMessageInt(s1), NULL,&reply.s1hash); clientId=CCS_AUTH_addClient(cl); reply.clientId=ChMessageInt_new(clientId); reply.clientSalt=ChMessageInt_new(CCS_AUTH_clientSalt(cl,clientId)); if (-1==skt_sendN(fd,&reply,sizeof(reply))) return "ERROR> CreateSalt reply send"; /*HACK: this isn't an error return, and returning an error code here is wrong; but all we want is to close the socket (not process a CCS request), and printing out this text isn't a bad idea, so... */ return "Created new client"; }
// Send message to connection recipient, blocks waiting for send bool TCPConnection::sendMessage(const std::string & message){ if(skt_sendN(_socket, message.c_str(), message.size()+1) != 0){ fail(); return false; } return true; }
/** Send a complete HTTP request, with all HTTP headers prebuilt. Returns HTTP status. */ int osl::http_connection::send(const std::string &data) { p.status(1,"Sending HTTP request to "+host); p.status(3,"HTTP request data: "+data); skt_sendN(s,&data[0],data.size()); p.status(1,"Waiting for HTTP response from "+host); std::string status=skt_recv_line(s); p.status(2,"HTTP response status: "+status); unsigned int i=0; while (status[i]!=' ' && i<status.size()) i++; std::string codeDesc=status.substr(i,std::string::npos); int code=0; sscanf(codeDesc.c_str(),"%d",&code); std::string l; while (0!=(l=skt_recv_line(s)).size()) { /* ^ a zero-length line indicates the end of the HTTP headers */ p.status(3,"HTTP response header line: "+l); int firstColon=l.find_first_of(":"); std::string keyword=l.substr(0,firstColon); std::string value=l.substr(firstColon+2,std::string::npos); header[keyword]=value; } return code; }
extern "C" void CcsImpl_kill(void) { skt_set_abort(noMoreErrors); while (killList!=NULL) { SOCKET fd=skt_connect(killList->ip,killList->port,20); if (fd!=INVALID_SOCKET) { skt_sendN(fd,"die\n",strlen("die\n")+1); skt_close(fd); } killList=killList->next; } }
int skt_sendV(SOCKET fd,int nBuffers,const void **bufs,int *lens) { int b,len=0; for (b=0;b<nBuffers;b++) len+=lens[b]; if (len<=skt_sendV_max) { /*Short message: Copy and do one big send*/ char *buf=(char *)malloc(skt_sendV_max); char *dest=buf; int ret; for (b=0;b<nBuffers;b++) { memcpy(dest,bufs[b],lens[b]); dest+=lens[b]; } ret=skt_sendN(fd,buf,len); free(buf); return ret; } else { /*Big message: Just send one-by-one as usual*/ int ret; for (b=0;b<nBuffers;b++) if (0!=(ret=skt_sendN(fd,bufs[b],lens[b]))) return ret; return 0; } }
// Main network access function: void handle_client(SOCKET s, bool intranet) { std::string status="Server "; status+=get_address(&status); status+=": "; if (working_OK) status+="TOTALLY OK"; else status+="not really ok"; status+=", hackability="; if (is_hackable) status+="high"; else status+="not so much"; status+=". Your name?\n"; skt_sendN(s,&status[0],status.size()); std::string name=skt_recv_line(s); if (is_hackable && intranet) { old_say_hello(&name[0]); } else { std::cout<<"Hello, "<<name<<"\n"; } skt_close(s); }
unsigned char *download_url(const char *url_in, int verbose, int *length) { char *url=STRDUP(url_in); // parse the url char *protocol, *host, *path; int port; parse_url(url, &protocol, &host, &port, &path); if (verbose) printf("Connecting to URL: %s://%s:%d%s\n", protocol, host, port, path); int timeout = 60; if (verbose) printf("Looking up IP Address for: %s\n", host); skt_ip_t hostIP = skt_lookup_ip(host); if (verbose) printf("Connecting to %s\n", host); SOCKET s = skt_connect(hostIP, port, timeout); char *send_get = MALLOC(strlen(url)+128); sprintf(send_get, "GET %s HTTP/1.1\r\n" "Host: %s\r\n" "User-Agent: Mozilla/5.0\r\n" "\r\n", path, host); // send our get request skt_sendN(s, send_get, strlen(send_get)); // wait... if (verbose) printf("Waiting for a response from %s\n", host); char *status = skt_recv_line(s); if (verbose) printf("Received status: %s\n", status); //char *status_trim = trim_spaces(status); free(status); // now can get the response code //int code = atoi(status_trim); //free(status_trim); // a zero-length line indicates the end of the HTTP headers... we ignore int len=-1; while (1) { char *line = skt_recv_line(s); if (strlen(line)==0) break; if (strstr(line, "Content-Length") != 0) { char *l = line + strlen("Content-Length") + 2; len=atoi(l); } } if (verbose) printf("Content Length: %d\n", len); if (len==-1) { asfPrintWarning("No Content-Length specified in the HTTP headers.\n"); return NULL; } // receiving data... unsigned char *data = CALLOC(len+12, sizeof(char)); int curr=0, chunkSize=1024; while (1) { int amt = chunkSize < len-curr ? chunkSize : len-curr; skt_recvN(s,data+curr,amt); curr += amt; if (verbose) printf("Retrieved %d Kb so far.\n", curr); if (curr==len) break; else if (curr>len) asfPrintError("Invalid Content-Length?\n"); } if(verbose) printf("Done.\n"); //if (verbose) // printf("Received data:\n" // "-------------------------------------------------------------\n" // "%s\n" // "-------------------------------------------------------------\n", // data); free(protocol); free(host); free(path); free(url); free(send_get); skt_close(s); *length = len; return data; }