bool putClassAdAndEOM(Sock & sock, classad::ClassAd &ad) { if (sock.type() != Stream::reli_sock) { return putClassAd(&sock, ad) && sock.end_of_message(); } ReliSock & rsock = static_cast<ReliSock&>(sock); Selector selector; selector.add_fd(sock.get_file_desc(), Selector::IO_WRITE); int timeout = sock.timeout(0); sock.timeout(timeout); timeout = timeout ? timeout : 20; selector.set_timeout(timeout); if (!putClassAd(&sock, ad, PUT_CLASSAD_NON_BLOCKING)) { return false; } int retval = rsock.end_of_message_nonblocking(); while (true) { if (rsock.clear_backlog_flag()) { Py_BEGIN_ALLOW_THREADS selector.execute(); Py_END_ALLOW_THREADS if (selector.timed_out()) {THROW_EX(RuntimeError, "Timeout when trying to write to remote host");} } else if (retval == 1) {
void *threadGet(void *par) { struct BIS *pp = (struct BIS*) par; Message m; sleep(2); Sock *sock = new Sock(SOCK_STREAM, 0); SockDist *host = new SockDist(pp->ps->adresse, (short)pp->port); if (connect(sock->getsDesc(),(sockaddr*)host->getAdrDist(), host->getsLen()) < 0) { perror("erreur connection"); } int sockBis = sock->getsDesc(); char octet; recv(sockBis, &octet, 1, 0); if (octet == '0') { cout << "fichier inexistant" << endl; return NULL; } cout << "début du transfert" << endl; bool terminer = false; struct timeval tt; char buffer[TAILLE_BUFFER_MAX]; while (!terminer) { int nbr = 0; int ret = 0; fd_set readfs; tt.tv_sec = 5; tt.tv_usec = 0; FD_ZERO(&readfs); FD_SET(sockBis, &readfs); ret = select(sockBis + 1, &readfs, NULL, NULL, &tt); if (FD_ISSET(sockBis, &readfs)) { nbr = recv(sockBis, buffer, TAILLE_BUFFER_MAX, 0); pp->ps->fichierRecu.write(buffer, nbr); } if (ret <= 0) { pp->ps->fichierRecu.close(); close(sockBis); delete sock; delete host; terminer = true; cout << "fin de Get" << endl; } } }
void EvalXTCPRecv(const void *obj, qCtx *ctx, qStr *out, qArgAry *args) { Sock *s = (Sock *) obj; int len; char *line = NULL; if (args->Count() > 0) { len = ParseInt((*args)[0]); len = s->Read(len); line = s->GetBuf(); } else { len = s->ReadLine(&line); } if (len > 0) out->PutS(line, len); else if (len < 0 ) { if (len == Sock::ERR_TIMEOUT) { ctx->ThrowF(out, 702, "Timeout while waiting to read data from host %s:%d, %y", s->GetHost(), s->GetPort()); } else { ctx->ThrowF(out, 702, "Error while reading data from host %s:%d, %y", s->GetHost(), s->GetPort(), GetLastError()); } } }
void CCBServer::ForwardRequestToTarget( CCBServerRequest *request, CCBTarget *target ) { Sock *sock = target->getSock(); ClassAd msg; msg.Assign( ATTR_COMMAND, CCB_REQUEST ); msg.Assign( ATTR_MY_ADDRESS, request->getReturnAddr() ); msg.Assign( ATTR_CLAIM_ID, request->getConnectID() ); // for easier debugging msg.Assign( ATTR_NAME, request->getSock()->peer_description() ); MyString reqid_str; CCBIDToString( request->getRequestID(), reqid_str); msg.Assign( ATTR_REQUEST_ID, reqid_str ); sock->encode(); if( !msg.put( *sock ) || !sock->end_of_message() ) { dprintf(D_ALWAYS, "CCB: failed to forward request id %lu from %s to target " "daemon %s with ccbid %lu\n", request->getRequestID(), request->getSock()->peer_description(), target->getSock()->peer_description(), target->getCCBID()); RequestFinished( request, false, "failed to forward request to target" ); return; } // Now wait for target to respond (HandleRequestResultsMsg). // We will get the response next time we poll the socket. // To get a faster response, we _could_ register the socket // now, if it has not already been registered. }
void *threadUpload (void * par) { ParamSocket *ps = ((ParamSocket*)(par)); //char messageRecu[TAILLE_MESSAGE_MAX]; // On attends que le serveur recoive notre message de depart sleep(1); Sock *sock = new Sock(SOCK_STREAM, 0); SockDist *host = new SockDist(ps->adresse, (short)PORT_PUT); if (connect(sock->getsDesc(),(sockaddr*)host->getAdrDist(), host->getsLen()) < 0) { perror("erreur connection"); } int sockBis = sock->getsDesc(); char *buffer = new char[TAILLE_BUFFER_MAX]; bool continuer=true; cout << "départ" << endl; while(continuer) { Message m; m.option = PUT; m.ctrl = ENCOURS; if(ps->fichierEnvoye.good()) { ps->fichierEnvoye.read(buffer, TAILLE_BUFFER_MAX); int nbrCaracteresLu = ps->fichierEnvoye.gcount(); if (nbrCaracteresLu < 512) { cout << "fini" << endl; m.ctrl = FIN; continuer = false; } m.taille = nbrCaracteresLu; //strcpy(m.data, buffer); for(int i=0;i<nbrCaracteresLu;i++) m.data[i] = buffer[i]; send(sockBis, buffer, nbrCaracteresLu, 0); } } delete buffer; delete sock; delete host; ps->fichierEnvoye.close(); pthread_exit(NULL); }
bool DCStartd::drainJobs(int how_fast,bool resume_on_completion,char const *check_expr,char const *start_expr,std::string &request_id) { std::string error_msg; ClassAd request_ad; Sock *sock = startCommand( DRAIN_JOBS, Sock::reli_sock, 20 ); if( !sock ) { formatstr(error_msg,"Failed to start DRAIN_JOBS command to %s",name()); newError(CA_FAILURE,error_msg.c_str()); return false; } request_ad.Assign(ATTR_HOW_FAST,how_fast); request_ad.Assign(ATTR_RESUME_ON_COMPLETION,resume_on_completion); if( check_expr ) { request_ad.AssignExpr(ATTR_CHECK_EXPR,check_expr); } if( start_expr ) { request_ad.AssignExpr(ATTR_START_EXPR,start_expr); } if( !putClassAd(sock, request_ad) || !sock->end_of_message() ) { formatstr(error_msg,"Failed to compose DRAIN_JOBS request to %s",name()); newError(CA_FAILURE,error_msg.c_str()); delete sock; return false; } sock->decode(); ClassAd response_ad; if( !getClassAd(sock, response_ad) || !sock->end_of_message() ) { formatstr(error_msg,"Failed to get response to DRAIN_JOBS request to %s",name()); newError(CA_FAILURE,error_msg.c_str()); delete sock; return false; } response_ad.LookupString(ATTR_REQUEST_ID,request_id); bool result = false; int error_code = 0; response_ad.LookupBool(ATTR_RESULT,result); if( !result ) { std::string remote_error_msg; response_ad.LookupString(ATTR_ERROR_STRING,remote_error_msg); response_ad.LookupInteger(ATTR_ERROR_CODE,error_code); formatstr(error_msg, "Received failure from %s in response to DRAIN_JOBS request: error code %d: %s", name(),error_code,remote_error_msg.c_str()); newError(CA_FAILURE,error_msg.c_str()); delete sock; return false; } delete sock; return true; }
void qObjProto::EvalXTCP(qCtx *ctx, qStr *out, qArgAry *args) { if (args->Count() < 1) { ctx->Throw(out, 655, "USAGE: %connect-tcp(host,body[,timeout]])"); return; } CStrAry hosts; CStr serv = (*args)[0]; CStr bodyStr = args->GetAt(1); double timeout = ParseDbl((*args)[2]); if (serv.IsEmpty()) return; int port = 0; char * p = strchr((const char *)serv, ':'); if (p) { port = atoi(p+1); *p = '\0'; ++p; } if (!port) port = IPPORT_TELNET; int sock_rval; Sock sock; CStr body, dom, ref; qCtxTmp tmpCtx(ctx); if (!bodyStr.IsEmpty()) { tmpCtx.MapObj(&sock, EvalXTCPSend,"send"); tmpCtx.MapObj(&sock, EvalXTCPRecv,"recv"); } PROTO_OPEN_SOCK(); if (timeout > 1) sock.SetTimeout((float) timeout); tmpCtx.Parse(bodyStr, out); sock.Close(); return; }
void EvalXTCPSend(const void *obj, qCtx *ctx, qStr *out, qArgAry *args) { Sock *s = (Sock *) obj; CStr str = (*args)[0]; int len = s->Write(str, str.Length()); if (len < 0 ) { if (len == Sock::ERR_TIMEOUT) { ctx->ThrowF(out, 702, "Timeout while waiting to write data from host %s:%d, %y", s->GetHost(), s->GetPort()); } else { ctx->ThrowF(out, 702, "Error while writing data from host %s:%d, %y", s->GetHost(), s->GetPort(), GetLastError()); } } }
bool DCStartd::cancelDrainJobs(char const *request_id) { std::string error_msg; ClassAd request_ad; Sock *sock = startCommand( CANCEL_DRAIN_JOBS, Sock::reli_sock, 20 ); if( !sock ) { formatstr(error_msg,"Failed to start CANCEL_DRAIN_JOBS command to %s",name()); newError(CA_FAILURE,error_msg.c_str()); return false; } if( request_id ) { request_ad.Assign(ATTR_REQUEST_ID,request_id); } if( !putClassAd(sock, request_ad) || !sock->end_of_message() ) { formatstr(error_msg,"Failed to compose CANCEL_DRAIN_JOBS request to %s",name()); newError(CA_FAILURE,error_msg.c_str()); return false; } sock->decode(); ClassAd response_ad; if( !getClassAd(sock, response_ad) || !sock->end_of_message() ) { formatstr(error_msg,"Failed to get response to CANCEL_DRAIN_JOBS request to %s",name()); newError(CA_FAILURE,error_msg.c_str()); delete sock; return false; } bool result = false; int error_code = 0; response_ad.LookupBool(ATTR_RESULT,result); if( !result ) { std::string remote_error_msg; response_ad.LookupString(ATTR_ERROR_STRING,remote_error_msg); response_ad.LookupInteger(ATTR_ERROR_CODE,error_code); formatstr(error_msg, "Received failure from %s in response to CANCEL_DRAIN_JOBS request: error code %d: %s", name(),error_code,remote_error_msg.c_str()); newError(CA_FAILURE,error_msg.c_str()); delete sock; return false; } delete sock; return true; }
void MachAttributes::credd_test() { // Attempt to perform a NOP on our CREDD_HOST. This will test // our ability to authenticate with DAEMON-level auth, and thus // fetch passwords. If we succeed, we'll advertise the CREDD_HOST char *credd_host = param("CREDD_HOST"); if (credd_host == NULL) { if (m_local_credd != NULL) { free(m_local_credd); m_local_credd = NULL; } return; } if (m_local_credd != NULL) { if (strcmp(m_local_credd, credd_host) == 0) { free(credd_host); return; } else { free(m_local_credd); m_local_credd = NULL; m_last_credd_test = 0; } } time_t now = time(NULL); double thresh = (double)param_integer("CREDD_TEST_INTERVAL", 300); if (difftime(now, m_last_credd_test) > thresh) { Daemon credd(DT_CREDD); if (credd.locate()) { Sock *sock = credd.startCommand(CREDD_NOP, Stream::reli_sock, 20); if (sock != NULL) { sock->decode(); if (sock->end_of_message()) { m_local_credd = credd_host; } } } m_last_credd_test = now; } if (credd_host != m_local_credd) { free(credd_host); } }
int CCBListener::ReverseConnected(Stream *stream) { Sock *sock = (Sock *)stream; ClassAd *msg_ad = (ClassAd *)daemonCore->GetDataPtr(); ASSERT( msg_ad ); if( sock ) { daemonCore->Cancel_Socket( sock ); } if( !sock || !sock->is_connected() ) { ReportReverseConnectResult(msg_ad,false,"failed to connect"); } else { // The reverse-connect protocol is designed to look like a // raw cedar command, in case the thing we are connecting // to is a cedar command socket. sock->encode(); int cmd = CCB_REVERSE_CONNECT; if( !sock->put(cmd) || !msg_ad->put( *sock ) || !sock->end_of_message() ) { ReportReverseConnectResult(msg_ad,false,"failure writing reverse connect command"); } else { ((ReliSock*)sock)->isClient(false); daemonCore->HandleReqAsync(sock); sock = NULL; // daemonCore took ownership of sock ReportReverseConnectResult(msg_ad,true); } } delete msg_ad; if( sock ) { delete sock; } decRefCount(); // we incremented ref count when setting up callback return KEEP_STREAM; }
void execCommand(string& str) { cdb::StringUtils::trim(str); if (str.empty()) return; if (str == "exit" || str == "quit") { g_keepGoing = false; return; } vector< string > tokens; cdb::StringUtils::split(str, " ", tokens); if (tokens.size() == 2 && tokens[0] == "start") { int threadCount = boost::lexical_cast<int>(tokens[1]); loadTest(threadCount); return; } int ret; uint16_t length = str.length(); ret = g_sock.send((const char*)& length, 2); if (ret != 2) THROW("Failed to send command's length"); ret = g_sock.send(str.c_str(), length); if (ret != length) THROW("Failed to send command"); ret = g_sock.receive((char*) &length, 2); if (ret != 2) THROW("Failed to receive response length"); if (g_buffer.size() < length) { g_buffer.extend(length - g_buffer.size() + 1); } g_buffer.clear(); ret = g_sock.receive(g_buffer.raw(), length); if (ret != length) THROW("Failed to receive response"); g_buffer.commit(length); g_buffer.closeText(); cout << g_buffer.raw() << endl; }
int GetMyProxyPasswordFromSchedD (int cluster_id, int proc_id, char ** password) { // This might seem not necessary, but it IS // For some reason you can't just pass cluster_id to sock->code() directly!!!! int cluster, proc; cluster = cluster_id; proc = proc_id; dprintf ( D_FULLDEBUG, " GetMyProxyPasswordFromSchedD %d, %d\n", cluster_id, proc_id); // Get At Schedd Daemon schedd( DT_SCHEDD ); if( ! schedd.locate() ) { dprintf( D_ALWAYS, "GetMyProxyPasswordFromSchedD: Can't find address of local schedd\n" ); return FALSE; } // Start command Sock* sock; if (!(sock = schedd.startCommand( GET_MYPROXY_PASSWORD, Stream::reli_sock, 0))) { dprintf( D_ALWAYS, "GetMyProxyPasswordFromSchedD: Could not connect to local schedd\n" ); return FALSE; } sock->encode(); if (!sock->code (cluster) || !sock->code(proc)) { dprintf( D_ALWAYS, "GetMyProxyPasswordFromSchedD: Could not encode clusterId, procId\n" ); return FALSE; } sock->end_of_message(); sock->decode(); if (!sock->code (*password)) { dprintf( D_ALWAYS, "GetMyProxyPasswordFromSchedD: Can't retrieve password\n" ); return FALSE; } sock->end_of_message(); sock->close(); delete sock; return TRUE; }
void CCBServer::SendHeartbeatResponse( CCBTarget *target ) { Sock *sock = target->getSock(); ClassAd msg; msg.Assign( ATTR_COMMAND, ALIVE ); sock->encode(); if( !msg.put( *sock ) || !sock->end_of_message() ) { dprintf(D_ALWAYS, "CCB: failed to send heartbeat to target " "daemon %s with ccbid %lu\n", target->getSock()->peer_description(), target->getCCBID()); RemoveTarget( target ); return; } dprintf(D_FULLDEBUG,"CCB: sent heartbeat to target %s\n", sock->peer_description()); }
bool CCBListener::DoReversedCCBConnect( char const *address, char const *connect_id, char const *request_id, char const *peer_description ) { Daemon daemon( DT_ANY, address ); CondorError errstack; Sock *sock = daemon.makeConnectedSocket( Stream::reli_sock,CCB_TIMEOUT,0,&errstack,true /*nonblocking*/); ClassAd *msg_ad = new ClassAd; ASSERT( msg_ad ); msg_ad->Assign( ATTR_CLAIM_ID, connect_id ); msg_ad->Assign( ATTR_REQUEST_ID, request_id ); // the following is put in the message because that is an easy (lazy) // way to make it available to ReportReverseConnectResult msg_ad->Assign( ATTR_MY_ADDRESS, address); if( !sock ) { // Failed to create socket or initiate connect ReportReverseConnectResult(msg_ad,false,"failed to initiate connection"); delete msg_ad; return false; } if( peer_description ) { char const *peer_ip = sock->peer_ip_str(); if( peer_ip && !strstr(peer_description,peer_ip)) { MyString desc; desc.formatstr("%s at %s",peer_description,sock->get_sinful_peer()); sock->set_peer_description(desc.Value()); } else { sock->set_peer_description(peer_description); } } incRefCount(); // do not delete self until called back MyString sock_desc; int rc = daemonCore->Register_Socket( sock, sock->peer_description(), (SocketHandlercpp)&CCBListener::ReverseConnected, "CCBListener::ReverseConnected", this); if( rc < 0 ) { ReportReverseConnectResult(msg_ad,false,"failed to register socket for non-blocking reversed connection"); delete msg_ad; delete sock; decRefCount(); return false; } rc = daemonCore->Register_DataPtr(msg_ad); ASSERT( rc ); return true; }
void workConsole() { g_sock.connect("localhost", g_port); g_buffer.init(1024); bool newCmd = true; string cmd = ""; while (g_keepGoing) { char* s = NULL; try { if (g_silent) { if (!cin.good()) break; string str; getline(cin, str); s = strdup(str.c_str()); } else { s = readline( newCmd ? "=> " : "..."); } if (s == 0) break; size_t len = strlen(s); if (len == 0) { free(s); if (cmd.empty()) continue; } else if (s[len-1] == '\\') { newCmd = false; s[len-1] = '\0'; cmd += s; free(s); continue; } else { cmd += s; free(s); } add_history(cmd.c_str()); execCommand(cmd); cmd = ""; newCmd = true; } catch(std::runtime_error& e) { cerr << "FAILED: " << e.what() << endl; cmd = ""; newCmd = true; } } }
static void execCommand(Sock& sock, string& str, Buffer& buffer) { int ret; uint16_t length = str.length(); ret = sock.send((const char*)& length, 2); if (ret != 2) THROW("Failed to send command's length"); ret = sock.send(str.c_str(), length); if (ret != length) THROW("Failed to send command"); ret = sock.receive((char*) &length, 2); if (ret != 2) THROW("Failed to receive response length"); if (buffer.size() < length) { buffer.extend(length - buffer.size() + 1); } buffer.clear(); ret = sock.receive(buffer.raw(), length); if (ret != length) THROW("Failed to receive response"); buffer.commit(length); buffer.closeText(); }
// Read history from a remote schedd static void readHistoryRemote(classad::ExprTree *constraintExpr) { printHeader(); if(longformat && use_xml) { std::string out; AddClassAdXMLFileHeader(out); printf("%s\n", out.c_str()); } classad::ClassAd ad; classad::ExprList *projList(new classad::ExprList()); classad::ExprTree *projTree = static_cast<classad::ExprTree*>(projList); ad.Insert(ATTR_PROJECTION, projTree); ad.Insert(ATTR_REQUIREMENTS, constraintExpr); ad.InsertAttr(ATTR_NUM_MATCHES, specifiedMatch <= 0 ? -1 : specifiedMatch); DCSchedd schedd(g_name.size() ? g_name.c_str() : NULL, g_pool.size() ? g_pool.c_str() : NULL); if (!schedd.locate(Daemon::LOCATE_FOR_LOOKUP)) { fprintf(stderr, "Unable to locate remote schedd (name=%s, pool=%s).\n", g_name.c_str(), g_pool.c_str()); exit(1); } Sock* sock; if (!(sock = schedd.startCommand(QUERY_SCHEDD_HISTORY, Stream::reli_sock, 0))) { fprintf(stderr, "Unable to send history command to remote schedd;\n" "Typically, either the schedd is not responding, does not authorize you, or does not support remote history.\n"); exit(1); } classad_shared_ptr<Sock> sock_sentry(sock); if (!putClassAd(sock, ad) || !sock->end_of_message()) { fprintf(stderr, "Unable to send request to remote schedd; likely a server or network error.\n"); exit(1); } while (true) { compat_classad::ClassAd ad; if (!getClassAd(sock, ad)) { fprintf(stderr, "Failed to recieve remote ad.\n"); exit(1); } long long intVal; if (ad.EvaluateAttrInt(ATTR_OWNER, intVal) && (intVal == 0)) { // Last ad. if (!sock->end_of_message()) { fprintf(stderr, "Unable to close remote socket.\n"); } sock->close(); std::string errorMsg; if (ad.EvaluateAttrInt(ATTR_ERROR_CODE, intVal) && intVal && ad.EvaluateAttrString(ATTR_ERROR_STRING, errorMsg)) { fprintf(stderr, "Error %lld: %s\n", intVal, errorMsg.c_str()); exit(intVal); } if (ad.EvaluateAttrInt("MalformedAds", intVal) && intVal) { fprintf(stderr, "Remote side had parse errors on history file"); exit(1); } if (!ad.EvaluateAttrInt(ATTR_NUM_MATCHES, intVal) || (intVal != matchCount)) { fprintf(stderr, "Client and server do not agree on number of ads sent;\n" "Indicates lost network packets or an internal error\n"); exit(1); } break; } matchCount++; printJob(ad); } if(longformat && use_xml) { std::string out; AddClassAdXMLFileFooter(out); printf("%s\n", out.c_str()); } }
void qObjProto::EvalWhois(qCtx *ctx, qStr *out, qArgAry *args) { if (args->Count() < 1) { ctx->Throw(out, 655, "USAGE: %whois(host[;host;host...][,body[,server[,bindip]]])"); return; } CStrAry hosts; CStr hostStr = (*args)[0]; CStr bodyStr = (*args)[1]; CStr serv = (*args)[2]; CStr bindip = (*args)[3]; ProtoParseHosts(hosts, hostStr); if (hosts.Count() == 0) return; int port; if(serv.IsEmpty()) serv = DEFAULT_WHOIS_HOST; port = IPPORT_WHOIS; int sock_rval, i; Sock sock; if(!bindip.IsEmpty()) sock.Bind(bindip); CStr body, dom, ref, reg, url; qCtxTmp tmpCtx(ctx); if (!bodyStr.IsEmpty()) { tmpCtx.MapObj(&body, "results"); tmpCtx.MapObj(&body, "body"); tmpCtx.MapObj(&dom, "domain"); tmpCtx.MapObj(&ref, "refer"); tmpCtx.MapObj(&dom, "domain-name"); tmpCtx.MapObj(®, "registrar"); tmpCtx.MapObj(&ref, "whois-server"); tmpCtx.MapObj(&url, "referral-url"); } for (i = 0; i < hosts.Count(); ++i) { PROTO_OPEN_SOCK(); body = CStr(); ref = CStr(); dom = hosts[i]; sock.Write(hosts[i]<<"\r\n", hosts[i].Length()+2); do { if ((sock_rval = sock.Read(SOCK_DEFAULT_BUF_SIZE)) < 0) { if (sock_rval == Sock::ERR_TIMEOUT) ctx->ThrowF(out, 705, "Time out while reading from host %s:%d, %y", (const char *) serv, port, GetLastError()); else if (sock_rval) ctx->ThrowF(out, 706, "Error reading from host %s:%d, %y", (const char *) serv, port, GetLastError()); return; } if (!bodyStr.IsEmpty()) body << CStr(sock.GetBuf(), sock_rval); else out->PutS(sock.GetBuf(), sock_rval); } while( sock_rval > 0); // If something was received if (!bodyStr.IsEmpty()) { const char *p; if ((p = stristr(body.GetBuffer(),"Whois Server:"))) { p += 14; while (isspace(*p)) ++p; char *e = strchr(p, '\n'); ref = CStr(p, e-p); } if ((p = stristr(body.GetBuffer(),"Registrar:"))) { p += 14; while (isspace(*p)) ++p; char *e = strchr(p, '\n'); reg = CStr(p, e-p); } if ((p = stristr(body.GetBuffer(),"Referral URL:"))) { p += 14; while (isspace(*p)) ++p; char *e = strchr(p, '\n'); url = CStr(p, e-p); } tmpCtx.Parse(bodyStr, out); } sock.Close(); } return; }
int qsmtp(qMailOpts *popts) { Sock *pSock = NULL; int rval = 0; try { if (popts->timeout == 0.0F) popts->timeout = QM_TIMEOUT; else if (popts->timeout < QM_TIMEOUT_MIN) popts->timeout = QM_TIMEOUT_MIN; if (!popts->port) popts->port = QM_SMTP_PORT; if (!popts->smtp) throw qEx(199, "Host was not specified"); if (!popts->rcpt) throw qEx(198, "Must specify recipient."); if (!popts->to && !strchr((const char *)popts->rcpt,';')) popts->to = popts->rcpt; if (!popts->helo) popts->helo = popts->smtp; const char *host = popts->smtp; int port = popts->port; pSock = new Sock; pSock->SetTimeout(popts->timeout); int sock_err = pSock->Open(host, port); if (sock_err == Sock::ERR_GETHOST) throw qEx(QM_ERR_SOCK_GETHOST, QM_ERR_SOCK_GETHOST_RC, host); else if (sock_err == Sock::ERR_CONNECT) throw qEx(QM_ERR_SOCK_CONNECT, QM_ERR_SOCK_CONNECT_RC, host, port); else if (sock_err == Sock::ERR_TIMEOUT) throw qEx(QM_ERR_SOCK_CONNECT, QM_ERR_SOCK_CONNECT_RC, host, port); else if (sock_err) throw qEx(sock_err, "Connect to host %s, error #%d", host, sock_err); qMailState state; int multi; char *line, *pcur; int errs; CStr request; state.opts = popts; state.proto = 1; state.code = 0; pSock->ReadLine(&line); do { errs = smtp_next(&state, request); if (errs > Q_ERRTHRESH) { char *p = request.Length() ? strrchr((const char *) request,'\r') : NULL; if (p) *p = '\0'; throw qEx(QM_ERR_SMTP_THRESH, QM_ERR_SMTP_THRESH_RC, errs, (const char *) request); } if (pSock->Write(request, request.Length()) < 0) throw qEx(QM_ERR_SOCK_WRITE_REQ, QM_ERR_SOCK_WRITE_REQ_RC, host); if (state.proto != qsBlock && state.proto != qsQuit) { do { if (pSock->ReadLine(&line) < 0) throw qEx(QM_ERR_SOCK_READ_REQ, QM_ERR_SOCK_READ_REQ_RC, host); state.code = strtol(line, &pcur, 10); multi = (*pcur++ == '-'); smtp_resp(&state, pcur); } while (multi); } } while (state.proto); } catch (CEx pEx) { if (pSock) delete pSock; pSock = NULL; throw pEx; } catch (...) { rval = 999; } if (pSock) delete pSock; return rval; }
int main(int argc, char* argv[]) { bool LongFlag=false; bool HierFlag=true; int ResetUsage=0; int DeleteUser=0; int SetFactor=0; int SetPrio=0; int SetAccum=0; int SetBegin=0; int SetLast=0; bool ResetAll=false; int GetResList=0; std::string pool; bool GroupRollup = false; myDistro->Init( argc, argv ); config(); MinLastUsageTime=time(0)-60*60*24; // Default to show only users active in the last day for (int i=1; i<argc; i++) { if (IsArg(argv[i],"setprio")) { if (i+2>=argc) usage(argv[0]); SetPrio=i; i+=2; } else if (IsArg(argv[i],"setfactor")) { if (i+2>=argc) usage(argv[0]); SetFactor=i; i+=2; } else if (IsArg(argv[i],"setbegin")) { if (i+2>=argc) usage(argv[0]); SetBegin=i; i+=2; } else if (IsArg(argv[i],"setaccum")) { if (i+2>=argc) usage(argv[0]); SetAccum=i; i+=2; } else if (IsArg(argv[i],"setlast")) { if (i+2>=argc) usage(argv[0]); SetLast=i; i+=2; } else if (IsArg(argv[i],"resetusage")) { if (i+1>=argc) usage(argv[0]); ResetUsage=i; i+=1; } else if (IsArg(argv[i],"delete",3)) { if (i+1>=argc) usage(argv[0]); DeleteUser=i; i+=1; } else if (IsArg(argv[i],"resetall")) { ResetAll=true; } else if (IsArg(argv[i],"long",1)) { LongFlag=true; } else if (IsArg(argv[i],"hierarchical",2) || IsArg(argv[i],"heir")) { HierFlag=true; DashHier=true; } else if (IsArg(argv[i],"flat",2)) { HierFlag=false; DashHier=true; } else if (IsArg(argv[i],"grouprollup")) { GroupRollup=true; } else if (IsArg(argv[i],"grouporder")) { GroupOrder=true; HierFlag = false; DashHier = true; } else if (IsArg(argv[i],"quotas",1)) { DetailFlag |= DetailQuotas; DashQuota = true; } else if (IsArg(argv[i],"surplus")) { DetailFlag |= DetailSurplus; DashQuota = true; } else if (IsArg(argv[i],"sortkey",2)) { DetailFlag |= DetailSortKey; DashSortKey = true; } else if (IsArg(argv[i],"all")) { DetailFlag |= DetailAll; DashAll = true; } else if (IsArg(argv[i],"most",2)) { DetailFlag |= DetailMost; #ifdef DEBUG DetailFlag |= DetailGroup; #endif DashAll = true; } else if (IsArg(argv[i],"groupid")) { DetailFlag |= DetailGroup; } else if (IsArg(argv[i],"order")) { DetailFlag |= DetailOrder; } else if (IsArg(argv[i],"activefrom")) { if (argc-i<=3) usage(argv[0]); int month=atoi(argv[i+1]); int day=atoi(argv[i+2]); int year=atoi(argv[i+3]); MinLastUsageTime=CalcTime(month,day,year); // printf("Date translation: %d/%d/%d = %d\n",month,day,year,FromDate); i+=3; } else if (IsArg(argv[i],"allusers")) { MinLastUsageTime=-1; } else if (IsArg(argv[i],"usage",2)) { DetailFlag |= DetailUsage | DetailUseTime1 | DetailUseTime2; } else if (IsArg(argv[i],"priority",4)) { DetailFlag |= DetailPrios; } else if (IsArg(argv[i],"getreslist",6)) { if (argc-i<=1) usage(argv[0]); GetResList=i; i+=1; } else if (IsArg(argv[i],"pool",1)) { if (argc-i<=1) usage(argv[0]); pool = argv[i+1]; i++; } else { usage(argv[0]); } } //---------------------------------------------------------- // Get info on our negotiator Daemon negotiator(DT_NEGOTIATOR, NULL, (pool != "") ? pool.c_str() : NULL); if (!negotiator.locate()) { fprintf(stderr, "%s: Can't locate negotiator in %s\n", argv[0], (pool != "") ? pool.c_str() : "local pool"); exit(1); } if (SetPrio) { // set priority char* tmp; if( ! (tmp = strchr(argv[SetPrio+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the priority of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } float Priority=atof(argv[SetPrio+2]); // send request Sock* sock; if( !(sock = negotiator.startCommand(SET_PRIORITY, Stream::reli_sock, 0) ) || !sock->put(argv[SetPrio+1]) || !sock->put(Priority) || !sock->end_of_message()) { fprintf( stderr, "failed to send SET_PRIORITY command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The priority of %s was set to %f\n",argv[SetPrio+1],Priority); } else if (SetFactor) { // set priority char* tmp; if( ! (tmp = strchr(argv[SetFactor+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the priority of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } float Factor=atof(argv[SetFactor+2]); if (Factor<1) { fprintf( stderr, "Priority factors must be greater than or equal to " "1.\n"); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(SET_PRIORITYFACTOR, Stream::reli_sock, 0) ) || !sock->put(argv[SetFactor+1]) || !sock->put(Factor) || !sock->end_of_message()) { fprintf( stderr, "failed to send SET_PRIORITYFACTOR command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The priority factor of %s was set to %f\n",argv[SetFactor+1],Factor); } else if (SetAccum) { // set accumulated usage char* tmp; if( ! (tmp = strchr(argv[SetAccum+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the Accumulated usage of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } float accumUsage=atof(argv[SetAccum+2]); if (accumUsage<0.0) { fprintf( stderr, "Usage must be greater than 0 seconds\n"); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(SET_ACCUMUSAGE, Stream::reli_sock, 0) ) || !sock->put(argv[SetAccum+1]) || !sock->put(accumUsage) || !sock->end_of_message()) { fprintf( stderr, "failed to send SET_ACCUMUSAGE command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The Accumulated Usage of %s was set to %f\n",argv[SetAccum+1],accumUsage); } else if (SetBegin) { // set begin usage time char* tmp; if( ! (tmp = strchr(argv[SetBegin+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the begin usage time of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } int beginTime=atoi(argv[SetBegin+2]); if (beginTime<0) { fprintf( stderr, "Time must be greater than 0 seconds\n"); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(SET_BEGINTIME, Stream::reli_sock, 0) ) || !sock->put(argv[SetBegin+1]) || !sock->put(beginTime) || !sock->end_of_message()) { fprintf( stderr, "failed to send SET_BEGINTIME command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The Begin Usage Time of %s was set to %d\n", argv[SetBegin+1],beginTime); } else if (SetLast) { // set last usage time char* tmp; if( ! (tmp = strchr(argv[SetLast+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the last usage time of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } int lastTime=atoi(argv[SetLast+2]); if (lastTime<0) { fprintf( stderr, "Time must be greater than 0 seconds\n"); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(SET_LASTTIME, Stream::reli_sock, 0) ) || !sock->put(argv[SetLast+1]) || !sock->put(lastTime) || !sock->end_of_message()) { fprintf( stderr, "failed to send SET_LASTTIME command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The Last Usage Time of %s was set to %d\n", argv[SetLast+1],lastTime); } else if (ResetUsage) { // set priority char* tmp; if( ! (tmp = strchr(argv[ResetUsage+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the priority of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(RESET_USAGE, Stream::reli_sock, 0) ) || !sock->put(argv[ResetUsage+1]) || !sock->end_of_message()) { fprintf( stderr, "failed to send RESET_USAGE command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The accumulated usage of %s was reset\n",argv[ResetUsage+1]); } else if (DeleteUser) { // remove a user record from the accountant char* tmp; if( ! (tmp = strchr(argv[DeleteUser+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the record you wish\n", argv[0] ); fprintf( stderr, "\tto delete (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(DELETE_USER, Stream::reli_sock, 0) ) || !sock->put(argv[DeleteUser+1]) || !sock->end_of_message()) { fprintf( stderr, "failed to send DELETE_USER command to negotiator\n" ); exit(1); } sock->close(); delete sock; printf("The accountant record named %s was deleted\n",argv[DeleteUser+1]); } else if (ResetAll) { // send request if( ! negotiator.sendCommand(RESET_ALL_USAGE, Stream::reli_sock, 0) ) { fprintf( stderr, "failed to send RESET_ALL_USAGE command to negotiator\n" ); exit(1); } printf("The accumulated usage was reset for all users\n"); } else if (GetResList) { // get resource list char* tmp; if( ! (tmp = strchr(argv[GetResList+1], '@')) ) { fprintf( stderr, "%s: You must specify the full name of the submittor you wish\n", argv[0] ); fprintf( stderr, "\tto update the priority of (%s or %s)\n", "*****@*****.**", "*****@*****.**" ); exit(1); } // send request Sock* sock; if( !(sock = negotiator.startCommand(GET_RESLIST, Stream::reli_sock, 0) ) || !sock->put(argv[GetResList+1]) || !sock->end_of_message()) { fprintf( stderr, "failed to send GET_RESLIST command to negotiator\n" ); exit(1); } // get reply sock->decode(); AttrList* ad=new AttrList(); if (!ad->initAttrListFromStream(*sock) || !sock->end_of_message()) { fprintf( stderr, "failed to get classad from negotiator\n" ); exit(1); } sock->close(); delete sock; if (LongFlag) ad->fPrint(stdout); else PrintResList(ad); } else { // list priorities Sock* sock; if (!(sock = negotiator.startCommand((GroupRollup) ? GET_PRIORITY_ROLLUP : GET_PRIORITY, Stream::reli_sock, 0)) || !sock->end_of_message()) { fprintf(stderr, "failed to send %s command to negotiator\n", (GroupRollup) ? "GET_PRIORITY_ROLLUP" : "GET_PRIORITY"); exit(1); } // get reply sock->decode(); AttrList* ad=new AttrList(); if (!ad->initAttrListFromStream(*sock) || !sock->end_of_message()) { fprintf( stderr, "failed to get classad from negotiator\n" ); exit(1); } sock->close(); delete sock; // if no details specified, show priorities if ( ! DetailFlag) { DetailFlag = DetailDefault; #ifdef DEBUG DetailFlag |= DetailGroup; #endif } // if showing only prio, don't bother showing groups if ( ! (DetailFlag & ~DetailPrios) && GroupPrioIsMeaningless) { if ( ! DashHier ) HierFlag = false; HideGroups = !HierFlag; } if (LongFlag) ad->fPrint(stdout); else ProcessInfo(ad,GroupRollup,HierFlag); } exit(0); return 0; }
void CCBServer::HandleRequestResultsMsg( CCBTarget *target ) { // Reply from target daemon about whether it succeeded in // connecting to the requested client. Sock *sock = target->getSock(); ClassAd msg; sock->decode(); if( !msg.initFromStream( *sock ) || !sock->end_of_message() ) { // disconnect dprintf(D_FULLDEBUG, "CCB: received disconnect from target daemon %s " "with ccbid %lu.\n", sock->peer_description(), target->getCCBID() ); RemoveTarget( target ); return; } int command = 0; if( msg.LookupInteger( ATTR_COMMAND, command ) && command == ALIVE ) { SendHeartbeatResponse( target ); return; } target->decPendingRequestResults(); bool success = false; MyString error_msg; MyString reqid_str; CCBID reqid; MyString connect_id; msg.LookupBool( ATTR_RESULT, success ); msg.LookupString( ATTR_ERROR_STRING, error_msg ); msg.LookupString( ATTR_REQUEST_ID, reqid_str ); msg.LookupString( ATTR_CLAIM_ID, connect_id ); if( !CCBIDFromString( reqid, reqid_str.Value() ) ) { MyString msg_str; msg.sPrint(msg_str); dprintf(D_ALWAYS, "CCB: received reply from target daemon %s with ccbid %lu " "without a valid request id: %s\n", sock->peer_description(), target->getCCBID(), msg_str.Value()); RemoveTarget( target ); return; } CCBServerRequest *request = GetRequest( reqid ); if( request && request->getSock()->readReady() ) { // Request socket must have just closed. To avoid noise in // logs when we fail to write to it, delete the request now. RemoveRequest( request ); request = NULL; } char const *request_desc = "(client which has gone away)"; if( request ) { request_desc = request->getSock()->peer_description(); } if( success ) { dprintf(D_FULLDEBUG,"CCB: received 'success' from target daemon %s " "with ccbid %lu for " "request %s from %s.\n", sock->peer_description(), target->getCCBID(), reqid_str.Value(), request_desc); } else { dprintf(D_FULLDEBUG,"CCB: received error from target daemon %s " "with ccbid %lu for " "request %s from %s: %s\n", sock->peer_description(), target->getCCBID(), reqid_str.Value(), request_desc, error_msg.Value()); } if( !request ) { if( success ) { // expected: the client has gone away; it got what it wanted return; } dprintf( D_FULLDEBUG, "CCB: client for request %s to target daemon %s with ccbid " "%lu disappeared before receiving error details.\n", reqid_str.Value(), sock->peer_description(), target->getCCBID()); return; } if( connect_id != request->getConnectID() ) { MyString msg_str; msg.sPrint(msg_str); dprintf( D_FULLDEBUG, "CCB: received wrong connect id (%s) from target daemon %s " "with ccbid %lu for " "request %s\n", connect_id.Value(), sock->peer_description(), target->getCCBID(), reqid_str.Value()); RemoveTarget( target ); return; } RequestFinished( request, success, error_msg.Value() ); }
void qObjProto::EvalRWhois(qCtx *ctx, qStr *out, qArgAry *args) { if (args->Count() < 1) { ctx->Throw(out, 655, "USAGE: %rwhois(host[;host;host...][,body[,server]])"); return; } CStrAry hosts; CStr hostStr = (*args)[0]; CStr bodyStr = (*args)[1]; CStr serv = (*args)[2]; ProtoParseHosts(hosts, hostStr); if (hosts.Count() == 0) return; int port; if (serv.IsEmpty()) serv = DEFAULT_RWHOIS_HOST; port = IPPORT_RWHOIS; int sock_rval, i; Sock sock; qCtx *tmpCtx = NULL; CStr body; if (!bodyStr.IsEmpty()) { tmpCtx = new qCtxTmp(ctx); tmpCtx->MapObj(&body, "results"); } PROTO_OPEN_SOCK(); sock.Write("-holdconnect on\r\n"); char *line = NULL; bool done; PROTO_READ_LINE(); if (line && (*line != '%')) { ctx->ThrowF(out, 709, "RWhoIs not supported at host %s:%d", (const char *) serv, port); return; } PROTO_READ_LINE(); if (line && stricmp(line,"%ok")) { CStr err; if (strnicmp(line,"%info",5)) { err = line; } PROTO_READ_LINE(); while (line && (*line != '%')) { err << line; err << '\n'; PROTO_READ_LINE(); } ctx->ThrowF(out, 709, "RWhoIs at %s:%d failed (%s)", (const char *) serv, port, (const char *) err); return; } for (i = 0; i < hosts.Count(); ++i) { sock.Write("domain ", 7); sock.Write(hosts[i], hosts[i].Length()); sock.Write("\r\n", 2); done = false; if (line && !stricmp(line,"%ok")) { PROTO_READ_LINE(); while (line && (*line != '%')) { out->PutS(line); PROTO_READ_LINE(); out->PutC('\n'); } } } sock.Write("-quit\r\n",14); return; }
int main(int args,char* argv[]) { int port, desCurrentClient, DesServer, localBR, nb_connected_client(0); struct sockaddr_in brCv; socklen_t sizeLocalBr; int nb_client = 5; client_t listeClientsEntreprise[nb_client]; // On définit un pointeur sur la structure data data_t data = (data_t)malloc(sizeof(data_t)); data->ptr_client_list = listeClientsEntreprise; data->nb_connected_client= &nb_connected_client; // Test création client client_t testcli = (client_t) malloc(sizeof(Client)); sprintf(testcli->name,"tintin"); sprintf(testcli->password,"milou"); testcli->claimed_report=false; testcli->received_report=0; testcli->controller=false; client_t testcli2 = (client_t) malloc(sizeof(Client)); sprintf(testcli2->name,"bob"); sprintf(testcli2->password,"boby"); testcli2->claimed_report=true; testcli2->received_report=0; testcli2->controller=false; client_t testcli3 = (client_t) malloc(sizeof(Client)); sprintf(testcli3->name,"tutu"); sprintf(testcli3->password,"boby"); testcli3->claimed_report=true; testcli3->received_report=1; testcli3->controller=false; client_t testcli4 = (client_t) malloc(sizeof(Client)); sprintf(testcli4->name,"beber"); sprintf(testcli4->password,"boby"); testcli4->claimed_report=false; testcli4->received_report=2; testcli4->controller=false; client_t testController = (client_t) malloc(sizeof(Client)); sprintf(testController->name,"haddock"); // enfin lui ! sprintf(testController->password,"boby"); testController->controller=true; testController->received_report=0; listeClientsEntreprise[0] = testcli; listeClientsEntreprise[1] = testcli2; listeClientsEntreprise[2] = testcli3; listeClientsEntreprise[3] = testcli4; listeClientsEntreprise[4] = testController; data->nb_client = &nb_client; if(args == 2) { cout << "N° port saisi : "<< argv[1] << endl; port = atoi(argv[1]); } else { cout << "Numéro du port du server : "; cin >> port; } /* Création de la BR Publique */ Sock* server = new Sock(SOCK_STREAM,(short)htons(port),0); if(server->good()) { cout << "Server lancé !" << endl; DesServer = server->getsDesc(); localBR = server-> getsRetour(); sizeLocalBr = sizeof(brCv); } else { perror("Erreur employee->des_client()"); exit(EXIT_FAILURE); } if(listen(DesServer,10) == -1) perror("Erreur listen()"); while(1) { /* Acceptation de la connexion du Client */ desCurrentClient = accept(DesServer,(struct sockaddr *)&brCv,&sizeLocalBr); if(desCurrentClient == -1) perror("Erreur accept "); else { pthread_t idThread; cout<< endl <<endl << " <=== Nouveau Client accepté ===>" << endl; data->descripteur = desCurrentClient; if(pthread_create(&idThread,NULL,th_new_client,(void*)data) != 0) { perror("Erreur création th_new_client"); } }// End if Client accepté } // End loop pthread_mutex_destroy(&mutex); /* Fermeture employee->des_clientet server */ close(DesServer); return EXIT_SUCCESS; }
int CondorQ::fetchQueueFromHostAndProcessV2(const char *host, const char *constraint, StringList &attrs, int fetch_opts, int match_limit, condor_q_process_func process_func, void * process_func_data, int connect_timeout, int useFastPath, CondorError *errstack, ClassAd ** psummary_ad) { classad::ClassAdParser parser; classad::ExprTree *expr = NULL; parser.ParseExpression(constraint, expr); if (!expr) return Q_INVALID_REQUIREMENTS; classad::ClassAd request_ad; // query ad to send to schedd ClassAd *ad = NULL; // job ad result request_ad.Insert(ATTR_REQUIREMENTS, expr); char *projection = attrs.print_to_delimed_string("\n"); if (projection) { request_ad.InsertAttr(ATTR_PROJECTION, projection); free(projection); } bool want_authentication = false; if (fetch_opts == fetch_DefaultAutoCluster) { request_ad.InsertAttr("QueryDefaultAutocluster", true); request_ad.InsertAttr("MaxReturnedJobIds", 2); // TODO: make this settable by caller of this function. } else if (fetch_opts == fetch_GroupBy) { request_ad.InsertAttr("ProjectionIsGroupBy", true); request_ad.InsertAttr("MaxReturnedJobIds", 2); // TODO: make this settable by caller of this function. } else { if (fetch_opts & fetch_MyJobs) { const char * owner = my_username(); if (owner) { request_ad.InsertAttr("Me", owner); } request_ad.InsertAttr("MyJobs", owner ? "(Owner == Me)" : "true"); want_authentication = true; } if (fetch_opts & fetch_SummaryOnly) { request_ad.InsertAttr("SummaryOnly", true); } if (fetch_opts & fetch_IncludeClusterAd) { request_ad.InsertAttr("IncludeClusterAd", true); } } if (match_limit >= 0) { request_ad.InsertAttr(ATTR_LIMIT_RESULTS, match_limit); } // determine if authentication can/will happen. three reasons why it might not: // 1) security negotiation is disabled (NEVER or OPTIONAL for outgoing connections) // 2) Authentication is disabled (NEVER) by the client // 3) Authentication is disabled (NEVER) by the server. this is actually impossible to // get correct without actually querying the server but we make an educated guess by // paraming the READ auth level. bool can_auth = true; char *paramer = NULL; paramer = SecMan::getSecSetting ("SEC_%s_NEGOTIATION", CLIENT_PERM); if (paramer != NULL) { char p = toupper(paramer[0]); free(paramer); if (p == 'N' || p == 'O') { // authentication will not happen since no security negotiation will occur can_auth = false; } } paramer = SecMan::getSecSetting ("SEC_%s_AUTHENTICATION", CLIENT_PERM); if (paramer != NULL) { char p = toupper(paramer[0]); free(paramer); if (p == 'N') { // authentication will not happen since client doesn't allow it. can_auth = false; } } // authentication will not happen since server probably doesn't allow it. // on the off chance that someone's config manages to trick us, leave an // undocumented knob as a last resort to disable our inference. if (param_boolean("CONDOR_Q_INFER_SCHEDD_AUTHENTICATION", true)) { paramer = SecMan::getSecSetting ("SEC_%s_AUTHENTICATION", READ); if (paramer != NULL) { char p = toupper(paramer[0]); free(paramer); if (p == 'N') { can_auth = false; } } paramer = SecMan::getSecSetting ("SCHEDD.SEC_%s_AUTHENTICATION", READ); if (paramer != NULL) { char p = toupper(paramer[0]); free(paramer); if (p == 'N') { can_auth = false; } } } if (!can_auth) { dprintf (D_ALWAYS, "detected that authentication will not happen. falling back to QUERY_JOB_ADS without authentication.\n"); } DCSchedd schedd(host); int cmd = QUERY_JOB_ADS; if (want_authentication && can_auth && (useFastPath > 2)) { cmd = QUERY_JOB_ADS_WITH_AUTH; } Sock* sock; if (!(sock = schedd.startCommand(cmd, Stream::reli_sock, connect_timeout, errstack))) return Q_SCHEDD_COMMUNICATION_ERROR; classad_shared_ptr<Sock> sock_sentry(sock); if (!putClassAd(sock, request_ad) || !sock->end_of_message()) return Q_SCHEDD_COMMUNICATION_ERROR; dprintf(D_FULLDEBUG, "Sent classad to schedd\n"); int rval = 0; do { ad = new ClassAd(); if ( ! getClassAd(sock, *ad) || ! sock->end_of_message()) { rval = Q_SCHEDD_COMMUNICATION_ERROR; break; } dprintf(D_FULLDEBUG, "Got classad from schedd.\n"); long long intVal; if (ad->EvaluateAttrInt(ATTR_OWNER, intVal) && (intVal == 0)) { // Last ad. sock->close(); dprintf(D_FULLDEBUG, "Ad was last one from schedd.\n"); std::string errorMsg; if (ad->EvaluateAttrInt(ATTR_ERROR_CODE, intVal) && intVal && ad->EvaluateAttrString(ATTR_ERROR_STRING, errorMsg)) { if (errstack) errstack->push("TOOL", intVal, errorMsg.c_str()); rval = Q_REMOTE_ERROR; } if (psummary_ad && rval == 0) { std::string val; if (ad->LookupString(ATTR_MY_TYPE, val) && val == "Summary") { ad->Delete(ATTR_OWNER); // remove the bogus owner attribute *psummary_ad = ad; // return the final ad, because it has summary information ad = NULL; // so we don't delete it below. } } break; } // Note: According to condor_q.h, process_func() will return false if taking // ownership of ad, so only delete if it returns true, else set to NULL // so we don't delete it here. Either way, next set ad to NULL since either // it has been deleted or will be deleted later by process_func(). if (process_func(process_func_data, ad)) { delete ad; } ad = NULL; } while (true); // Make sure ad is not leaked no matter how we break out of the above loop. delete ad; return rval; }
// fetch all ads from the collector that satisfy the constraints QueryResult CondorQuery:: fetchAds (ClassAdList &adList, const char *poolName, CondorError* errstack) { Sock* sock; int more; QueryResult result; ClassAd queryAd(extraAttrs), *ad; if ( !poolName ) { return Q_NO_COLLECTOR_HOST; } // contact collector Daemon my_collector( DT_COLLECTOR, poolName, NULL ); if( !my_collector.locate() ) { // We were passed a bogus poolName, abort gracefully return Q_NO_COLLECTOR_HOST; } // make the query ad result = getQueryAd (queryAd); if (result != Q_OK) return result; if( IsDebugLevel( D_HOSTNAME ) ) { dprintf( D_HOSTNAME, "Querying collector %s (%s) with classad:\n", my_collector.addr(), my_collector.fullHostname() ); queryAd.dPrint( D_HOSTNAME ); dprintf( D_HOSTNAME, " --- End of Query ClassAd ---\n" ); } int mytimeout = param_integer ("QUERY_TIMEOUT",60); if (!(sock = my_collector.startCommand(command, Stream::reli_sock, mytimeout, errstack)) || !queryAd.put (*sock) || !sock->end_of_message()) { if (sock) { delete sock; } return Q_COMMUNICATION_ERROR; } // get result sock->decode (); more = 1; while (more) { if (!sock->code (more)) { sock->end_of_message(); delete sock; return Q_COMMUNICATION_ERROR; } if (more) { ad = new ClassAd; if( !ad->initFromStream(*sock) ) { sock->end_of_message(); delete ad; delete sock; return Q_COMMUNICATION_ERROR; } adList.Insert (ad); } } sock->end_of_message(); // finalize sock->close(); delete sock; return (Q_OK); }
int DCStartd::activateClaim( ClassAd* job_ad, int starter_version, ReliSock** claim_sock_ptr ) { int reply; dprintf( D_FULLDEBUG, "Entering DCStartd::activateClaim()\n" ); setCmdStr( "activateClaim" ); if( claim_sock_ptr ) { // our caller wants a pointer to the socket we used to // successfully activate the claim. right now, set it to // NULL to signify error, and if everything works out, // we'll give them a pointer to the real object. *claim_sock_ptr = NULL; } if( ! claim_id ) { newError( CA_INVALID_REQUEST, "DCStartd::activateClaim: called with NULL claim_id, failing" ); return CONDOR_ERROR; } // if this claim is associated with a security session ClaimIdParser cidp(claim_id); char const *sec_session = cidp.secSessionId(); Sock* tmp; tmp = startCommand( ACTIVATE_CLAIM, Stream::reli_sock, 20, NULL, NULL, false, sec_session ); if( ! tmp ) { newError( CA_COMMUNICATION_ERROR, "DCStartd::activateClaim: Failed to send command ACTIVATE_CLAIM to the startd" ); return CONDOR_ERROR; } if( ! tmp->put_secret(claim_id) ) { newError( CA_COMMUNICATION_ERROR, "DCStartd::activateClaim: Failed to send ClaimId to the startd" ); delete tmp; return CONDOR_ERROR; } if( ! tmp->code(starter_version) ) { newError( CA_COMMUNICATION_ERROR, "DCStartd::activateClaim: Failed to send starter_version to the startd" ); delete tmp; return CONDOR_ERROR; } if( ! putClassAd(tmp, *job_ad) ) { newError( CA_COMMUNICATION_ERROR, "DCStartd::activateClaim: Failed to send job ClassAd to the startd" ); delete tmp; return CONDOR_ERROR; } if( ! tmp->end_of_message() ) { newError( CA_COMMUNICATION_ERROR, "DCStartd::activateClaim: Failed to send EOM to the startd" ); delete tmp; return CONDOR_ERROR; } // Now, try to get the reply tmp->decode(); if( !tmp->code(reply) || !tmp->end_of_message()) { std::string err = "DCStartd::activateClaim: "; err += "Failed to receive reply from "; err += _addr ? _addr : "NULL"; newError( CA_COMMUNICATION_ERROR, err.c_str() ); delete tmp; return CONDOR_ERROR; } dprintf( D_FULLDEBUG, "DCStartd::activateClaim: " "successfully sent command, reply is: %d\n", reply ); if( reply == OK && claim_sock_ptr ) { *claim_sock_ptr = (ReliSock*)tmp; } else { // in any other case, we're going to leak this ReliSock // object if we don't delete it here... delete tmp; } return reply; }
// process ads from the collector, handing each to the callback // callback will return 'false' if it took ownership of the ad. QueryResult CondorQuery:: processAds (bool (*callback)(void*, ClassAd *), void* pv, const char * poolName, CondorError* errstack /*= NULL*/) { Sock* sock; QueryResult result; ClassAd queryAd(extraAttrs); if ( !poolName ) { return Q_NO_COLLECTOR_HOST; } // contact collector Daemon my_collector( DT_COLLECTOR, poolName, NULL ); if( !my_collector.locate() ) { // We were passed a bogus poolName, abort gracefully return Q_NO_COLLECTOR_HOST; } // make the query ad result = getQueryAd (queryAd); if (result != Q_OK) return result; if (IsDebugLevel(D_HOSTNAME)) { dprintf( D_HOSTNAME, "Querying collector %s (%s) with classad:\n", my_collector.addr(), my_collector.fullHostname() ); dPrintAd( D_HOSTNAME, queryAd ); dprintf( D_HOSTNAME, " --- End of Query ClassAd ---\n" ); } int mytimeout = param_integer ("QUERY_TIMEOUT",60); if (!(sock = my_collector.startCommand(command, Stream::reli_sock, mytimeout, errstack)) || !putClassAd (sock, queryAd) || !sock->end_of_message()) { if (sock) { delete sock; } return Q_COMMUNICATION_ERROR; } // get result sock->decode (); int more = 1; while (more) { if (!sock->code (more)) { sock->end_of_message(); delete sock; return Q_COMMUNICATION_ERROR; } if (more) { ClassAd * ad = new ClassAd; if( !getClassAd(sock, *ad) ) { sock->end_of_message(); delete ad; delete sock; return Q_COMMUNICATION_ERROR; } if (callback(pv, ad)) { delete ad; } } } sock->end_of_message(); // finalize sock->close(); delete sock; return (Q_OK); }
int main( int argc, char *argv[] ) { const char *filename=0; char *pool=0; int command=-1; int i; bool use_tcp = false; bool with_ack = false; bool allow_multiple = false; param_functions *p_funcs = NULL; myDistro->Init( argc, argv ); config(); p_funcs = get_param_functions(); for( i=1; i<argc; i++ ) { if(!strcmp(argv[i],"-help")) { usage(argv[0]); exit(0); } else if(!strcmp(argv[i],"-pool")) { i++; if(!argv[i]) { fprintf(stderr,"-pool requires an argument.\n\n"); usage(argv[0]); exit(1); } pool = argv[i]; } else if(!strncmp(argv[i],"-tcp",strlen(argv[i]))) { use_tcp = true; } else if(!strncmp(argv[i],"-multiple",strlen(argv[i]))) { // We don't set allow_multiple=true by default, because // existing users (e.g. glideinWMS) have stray blank lines // in the input file. allow_multiple = true; } else if(!strcmp(argv[i],"-version")) { version(); exit(0); } else if(!strcmp(argv[i],"-debug")) { // dprintf to console Termlog = 1; p_funcs = get_param_functions(); dprintf_config ("TOOL", p_funcs); } else if(argv[i][0]!='-' || !strcmp(argv[i],"-")) { if(command==-1) { command = getCollectorCommandNum(argv[i]); if(command==-1) { fprintf(stderr,"Unknown command name %s\n\n",argv[i]); usage(argv[0]); exit(1); } } else if(!filename) { filename = argv[i]; } else { fprintf(stderr,"Extra argument: %s\n\n",argv[i]); usage(argv[0]); exit(1); } } else { fprintf(stderr,"Unknown argument: %s\n\n",argv[i]); usage(argv[0]); exit(1); } } FILE *file; ClassAdList ads; Daemon *collector; Sock *sock; switch( command ) { case UPDATE_STARTD_AD_WITH_ACK: with_ack = true; break; } if( with_ack ) { use_tcp = true; } if(!filename || !strcmp(filename,"-")) { file = stdin; filename = "(stdin)"; } else { file = safe_fopen_wrapper_follow(filename,"r"); } if(!file) { fprintf(stderr,"couldn't open %s: %s\n",filename,strerror(errno)); return 1; } while(!feof(file)) { int eof=0,error=0,empty=0; char const *delim = "\n"; if( !allow_multiple ) { delim = "***"; } ClassAd *ad = new ClassAd(file,const_cast<char *>(delim),eof,error,empty); if(error) { fprintf(stderr,"couldn't parse ClassAd in %s\n",filename); delete ad; return 1; } if( empty ) { delete ad; break; } if( !allow_multiple && ads.Length() > 0 ) { fprintf(stderr,"ERROR: failed to parse '%s' as a ClassAd attribute\n",delim); delete ad; return 1; } ads.Insert(ad); } if(ads.Length() == 0) { fprintf(stderr,"%s is empty\n",filename); return 1; } CollectorList * collectors; if ( pool ) { collector = new Daemon( DT_COLLECTOR, pool, 0 ); collectors = new CollectorList(); collectors->append (collector); } else { collectors = CollectorList::create(); } bool had_error = false; collectors->rewind(); while (collectors->next(collector)) { dprintf(D_FULLDEBUG,"locating collector %s...\n", collector->name()); if(!collector->locate()) { fprintf(stderr,"couldn't locate collector: %s\n",collector->error()); had_error = true; continue; } dprintf(D_FULLDEBUG,"collector is %s located at %s\n", collector->hostname(),collector->addr()); sock = NULL; ClassAd *ad; int success_count = 0; int failure_count = 0; ads.Rewind(); while( (ad=ads.Next()) ) { // If there's no "MyAddress", generate one.. if( !ad->Lookup( ATTR_MY_ADDRESS ) ) { MyString tmp; tmp.formatstr( "<%s:0>", my_ip_string() ); ad->Assign( ATTR_MY_ADDRESS, tmp.Value() ); } if ( use_tcp ) { if( !sock ) { sock = collector->startCommand(command,Stream::reli_sock,20); } else { // Use existing connection. sock->encode(); sock->put(command); } } else { // We must open a new UDP socket each time. delete sock; sock = collector->startCommand(command,Stream::safe_sock,20); } int result = 0; if ( sock ) { result += ad->put( *sock ); result += sock->end_of_message(); } if ( result != 2 ) { fprintf(stderr,"failed to send classad to %s\n",collector->addr()); had_error = true; failure_count++; delete sock; sock = NULL; continue; } if( with_ack ) { sock->decode(); int ok = 0; if( !sock->get(ok) || !sock->end_of_message() ) { fprintf(stderr,"failed to get ack from %s\n",collector->addr()); had_error = true; failure_count++; delete sock; sock = NULL; continue; } // ack protocol does not allow for multiple updates, // so close the socket now delete sock; sock = NULL; } success_count++; } if( sock ) { CondorVersionInfo const *ver = sock->get_peer_version(); if( !ver || ver->built_since_version(7,7,3) ) { // graceful hangup so the collector knows we are done sock->encode(); command = DC_NOP; sock->put(command); sock->end_of_message(); } delete sock; sock = NULL; } printf("Sent %d of %d ad%s to %s.\n", success_count, success_count + failure_count, success_count+failure_count == 1 ? "" : "s", collector->name()); } delete collectors; return (had_error)?1:0; }
bool DCShadow::updateJobInfo( ClassAd* ad, bool insure_update ) { if( ! ad ) { dprintf( D_FULLDEBUG, "DCShadow::updateJobInfo() called with NULL ClassAd\n" ); return false; } if( ! shadow_safesock && ! insure_update ) { shadow_safesock = new SafeSock; shadow_safesock->timeout(20); // years of research... :) if( ! shadow_safesock->connect(_addr) ) { dprintf( D_ALWAYS, "updateJobInfo: Failed to connect to shadow " "(%s)\n", _addr ); delete shadow_safesock; shadow_safesock = NULL; return false; } } ReliSock reli_sock; Sock* tmp; bool result; if( insure_update ) { // For now, if we have to ensure that the update gets // there, we use a ReliSock (TCP). reli_sock.timeout(20); // years of research... :) if( ! reli_sock.connect(_addr) ) { dprintf( D_ALWAYS, "updateJobInfo: Failed to connect to shadow " "(%s)\n", _addr ); return false; } result = startCommand( SHADOW_UPDATEINFO, (Sock*)&reli_sock ); tmp = &reli_sock; } else { result = startCommand( SHADOW_UPDATEINFO, (Sock*)shadow_safesock ); tmp = shadow_safesock; } if( ! result ) { dprintf( D_FULLDEBUG, "Failed to send SHADOW_UPDATEINFO command to shadow\n" ); if( shadow_safesock ) { delete shadow_safesock; shadow_safesock = NULL; } return false; } if( ! putClassAd(tmp, *ad) ) { dprintf( D_FULLDEBUG, "Failed to send SHADOW_UPDATEINFO ClassAd to shadow\n" ); if( shadow_safesock ) { delete shadow_safesock; shadow_safesock = NULL; } return false; } if( ! tmp->end_of_message() ) { dprintf( D_FULLDEBUG, "Failed to send SHADOW_UPDATEINFO EOM to shadow\n" ); if( shadow_safesock ) { delete shadow_safesock; shadow_safesock = NULL; } return false; } return true; }