00001
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038 #include "utils.h"
00039 #include "ApMon.h"
00040
00041 #ifdef __ICC
00042
00043 #pragma warning(disable:2259)
00044 #endif
00045
00046 bool apmon_utils::urlModified(char *url, char *lastModified) throw(runtime_error) {
00047 char temp_filename[300];
00048 FILE *tmp_file;
00049 bool lineFound;
00050 char line[MAX_STRING_LEN1];
00051
00052 #ifndef WIN32
00053 long mypid = getpid();
00054 #else
00055 long mypid = _getpid();
00056 #endif
00057
00058 char str1[100], str2[100];
00059 #ifndef WIN32
00060 sprintf(temp_filename, "/tmp/apmon_http%ld", mypid);
00061 #else
00062 char *tmp = getenv("TEMP");
00063 if(tmp == NULL)
00064 tmp = getenv("TMP");
00065 if(tmp == NULL)
00066 tmp = "c:";
00067 sprintf(temp_filename, "%s\\apmon_http%ld", tmp, mypid);
00068 #endif
00069
00070 httpRequest(url, (char*)"HEAD", temp_filename);
00071
00072
00073 tmp_file = fopen(temp_filename, "rt");
00074 if (tmp_file == NULL)
00075 throw runtime_error("[ urlModified() ] Error getting the configuration web page");
00076
00077
00078
00079
00080 fgets(line, MAX_STRING_LEN, tmp_file);
00081 sscanf(line, "%s %s", str1, str2);
00082 if (atoi(str2) != 200) {
00083 fclose(tmp_file);
00084 unlink(temp_filename);
00085 throw runtime_error("[ urlModified() ] Error getting the configuration web page");
00086 }
00087
00088
00089 lineFound = false;
00090 while (fgets(line, MAX_STRING_LEN, tmp_file) != NULL) {
00091 if (strstr(line, "Last-Modified") == line) {
00092 lineFound = true;
00093 break;
00094 }
00095 }
00096
00097 fclose(tmp_file);
00098 unlink(temp_filename);
00099 if (lineFound) {
00100 if (strcmp(line, lastModified) != 0) {
00101 return true;
00102 }
00103 else
00104 return false;
00105 } else
00106
00107 return true;
00108
00109 }
00110
00111 int apmon_utils::httpRequest(char *url, char *reqType, char *temp_filename)
00112 throw(runtime_error) {
00113
00114 char hostname[MAX_STRING_LEN];
00115
00116 char filename[MAX_STRING_LEN];
00117
00118 int port;
00119 char msg[MAX_STRING_LEN];
00120
00121 int sd, rc;
00122
00123 struct sockaddr_in servAddr;
00124 struct hostent *h;
00125 struct timeval optval;
00126
00127 char *request;
00128
00129 char buffer[MAX_STRING_LEN];
00130 int totalSize;
00131 FILE *tmp_file;
00132
00133 parse_URL(url, hostname, &port, filename);
00134
00135 sprintf(msg, "Sending HTTP %s request to: \n Hostname: %s , Port: %d , Filename: %s",
00136 reqType, hostname, port, filename);
00137 logger(INFO, msg);
00138
00139 request = (char *)malloc(MAX_STRING_LEN * sizeof(char));
00140 strcpy(request, reqType);
00141 strcat(request, " ");
00142
00143 request = (char *)strcat( request, filename);
00144 request = (char *)strcat( request, " HTTP/1.0\r\nHOST: ");
00145 request = (char *)strcat( request, hostname);
00146 request = (char *)strcat( request, "\r\n\r\n");
00147
00148 h = gethostbyname(hostname);
00149 if(h==NULL) {
00150 free(request);
00151 sprintf(msg,"[ httpRequest() ] Unknown host: %s ", hostname);
00152 throw runtime_error(msg);
00153 }
00154
00155 servAddr.sin_family = h->h_addrtype;
00156 memcpy((char *) &servAddr.sin_addr.s_addr, h->h_addr_list[0], h->h_length);
00157 servAddr.sin_port = htons(port);
00158
00159 sd = socket(AF_INET, SOCK_STREAM, 0);
00160 if(sd<0) {
00161 free(request);
00162 throw runtime_error(" [ httpRequest() ] Cannot open socket ");
00163 }
00164
00165
00166
00167 optval.tv_sec = 10;
00168 optval.tv_usec = 0;
00169
00170
00171 setsockopt(sd, SOL_SOCKET, SO_RCVTIMEO, (char *) &optval,
00172 sizeof(optval));
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189 rc = connect(sd, (struct sockaddr *) &servAddr, sizeof(servAddr));
00190 if(rc<0) {
00191 free(request);
00192 #ifndef WIN32
00193 close(sd);
00194 #else
00195 closesocket(sd);
00196 #endif
00197 throw runtime_error("[ httpRequest() ] Cannot connect to http server");
00198 }
00199
00200
00201 rc = send(sd, request, strlen(request), 0);
00202 if(rc<0) {
00203 #ifndef WIN32
00204 close(sd);
00205 #else
00206 closesocket(sd);
00207 #endif
00208 free(request);
00209 throw runtime_error("[ httpRequest() ] Cannot send the request to the http server");
00210 }
00211
00212 free(request);
00213
00214
00215 tmp_file = fopen(temp_filename, "wb");
00216 if (tmp_file == NULL) {
00217 #ifndef WIN32
00218 close(sd);
00219 #else
00220 closesocket(sd);
00221 #endif
00222 throw runtime_error("[ httpRequest() ] Unable to open for writing temporary file");
00223 }
00224
00225 rc = 0, totalSize = 0;
00226 do {
00227 memset(buffer,0x0,MAX_STRING_LEN);
00228 rc = recv(sd, buffer, MAX_STRING_LEN, 0);
00229 if( rc > 0) {
00230 fwrite(buffer, rc, 1, tmp_file);
00231 totalSize +=rc;
00232 }
00233 }while(rc>0);
00234
00235 sprintf(msg, "Received response from %s, response size is %d bytes",
00236 hostname, totalSize);
00237 logger(INFO, msg);
00238
00239 #ifndef WIN32
00240 close(sd);
00241 #else
00242 closesocket(sd);
00243 #endif
00244 fclose(tmp_file);
00245 return totalSize;
00246 }
00247
00248 char *apmon_utils::findIP(char *address) throw(runtime_error) {
00249 int isIP = 1;
00250 char *destIP, *s;
00251 struct in_addr addr;
00252 unsigned int j;
00253 bool ipFound;
00254
00255 for (j = 0; j < strlen(address); j++)
00256 if (isalpha(address[j])) {
00257
00258 isIP = 0;
00259 break;
00260 }
00261
00262 if (!isIP) {
00263 struct hostent *he = gethostbyname(address);
00264 if (he == NULL) {
00265 char tmp_msg[40];
00266 sprintf(tmp_msg, "[ findIP() ] Invalid destination address %s", address);
00267 throw runtime_error(tmp_msg);
00268 }
00269 j = 0;
00270
00271
00272 ipFound = false;
00273 while ((he -> h_addr_list)[j] != NULL) {
00274 memcpy(&(addr.s_addr), (he -> h_addr_list)[j], 4);
00275 s = inet_ntoa(addr);
00276 if (strcmp(s, "127.0.0.1") != 0) {
00277 destIP = strdup(s);
00278 ipFound = true;
00279 break;
00280 }
00281 j++;
00282 }
00283 if (!ipFound) {
00284 destIP = strdup("127.0.0.1");
00285 fprintf(stderr, "The destination for datagrams is localhost\n");
00286 }
00287
00288 } else
00289 destIP = strdup(address);
00290
00291 return destIP;
00292 }
00293
00294
00295 void apmon_utils::parse_URL(char *url, char *hostname, int *port, char *identifier)
00296 throw(runtime_error) {
00297 char protocol[MAX_STRING_LEN], scratch[MAX_STRING_LEN], *ptr=0, *nptr=0;
00298 char msg[MAX_STRING_LEN];
00299
00300 strcpy(scratch, url);
00301 ptr = (char *)strchr(scratch, ':');
00302 if (!ptr)
00303 throw runtime_error("[ parse_URL() ] Wrong url: no protocol specified");
00304
00305 strcpy(ptr, "\0");
00306 strcpy(protocol, scratch);
00307 if (strcmp(protocol, "http")) {
00308 sprintf(msg, "[ parse_URL() ] Wrong protocol in URL: %s", protocol);
00309 throw runtime_error(msg);
00310 }
00311
00312 strcpy(scratch, url);
00313 ptr = (char *)strstr(scratch, "//");
00314 if (!ptr) {
00315 throw runtime_error("[ parse_URL() ] Wrong url: no server specified");
00316 }
00317 ptr += 2;
00318
00319 strcpy(hostname, ptr);
00320 nptr = (char *)strchr(ptr, ':');
00321 if (!nptr) {
00322 *port = 80;
00323 nptr = (char *)strchr(hostname, '/');
00324 } else {
00325 sscanf(nptr, ":%d", port);
00326 nptr = (char *)strchr(hostname, ':');
00327 }
00328
00329 if (nptr)
00330 *nptr = '\0';
00331
00332 nptr = (char *)strchr(ptr, '/');
00333 if (!nptr) {
00334 throw runtime_error("[ parse_URL() ] Wrong url: no file specified");
00335 }
00336 strcpy(identifier, nptr);
00337 }
00338
00339
00340 void apmon_utils::freeMat(char **mat, int nRows) {
00341 int i;
00342 for (i = 0; i < nRows; i++)
00343 free(mat[i]);
00344 free(mat);
00345 }
00346
00347 char *apmon_utils::trimString(char *s) {
00348 unsigned int i, j, firstpos, lastpos;
00349 char *ret = (char *)malloc((strlen(s) + 1) * sizeof(char));
00350 j = 0;
00351
00352
00353 for (i = 0; i < strlen(s); i++)
00354 if (!isspace(s[i]))
00355 break;
00356 firstpos = i;
00357
00358 if (firstpos == strlen(s)) {
00359 ret[0] = 0;
00360 return ret;
00361 }
00362
00363
00364 for (i = strlen(s) ; i > 0; i--)
00365 if (!isspace(s[i-1]))
00366 break;
00367 lastpos = i;
00368
00369 for (i = firstpos; i <= lastpos; i++)
00370 ret[j++] = s[i];
00371
00372 ret[j++] = 0;
00373 return ret;
00374 }
00375
00376 int apmon_utils::xdrSize(int type, char *value) {
00377 int size;
00378
00379 switch (type) {
00380
00381 case XDR_INT32:
00382 case XDR_REAL32:
00383 return 4;
00384
00385 case XDR_REAL64:
00386 return 8;
00387 case XDR_STRING:
00388
00389
00390 if (value == NULL) {
00391 logger(WARNING, "[ xdrSize() ] null string argument");
00392 size = 4;
00393 } else {
00394 size = strlen(value) + 4;
00395
00396
00397 if (size % 4 != 0)
00398 size += (4 - size % 4);
00399 return size;
00400 }
00401 }
00402
00403 return RET_ERROR;
00404 }
00405
00406 int apmon_utils::sizeEval(int type, char *value) {
00407
00408 switch (type) {
00409
00410 case XDR_INT32:
00411 case XDR_REAL32:
00412 return 4;
00413
00414 case XDR_REAL64:
00415 return 8;
00416 case XDR_STRING:
00417 return (strlen(value) + 1);
00418 }
00419
00420 return RET_ERROR;
00421 }
00422
00423
00424
00425 void apmon_utils::logParameters(int level, int nParams, char **paramNames,
00426 int *valueTypes, char **paramValues) {
00427 int i;
00428 char typeNames[][15] = {"XDR_STRING", "", "XDR_INT32", "", "XDR_REAL32",
00429 "XDR_REAL64"};
00430 char logmsg[200], val[100];
00431
00432 for (i = 0; i < nParams; i++) {
00433 if (paramNames[i] == NULL || (valueTypes[i] == XDR_STRING &&
00434 paramValues[i] == NULL))
00435 continue;
00436 sprintf(logmsg, "%s (%s) ", paramNames[i], typeNames[valueTypes[i]]);
00437
00438 switch(valueTypes[i]) {
00439 case XDR_STRING:
00440 sprintf(val, "%s", paramValues[i]);
00441 break;
00442 case XDR_INT32:
00443 sprintf(val, "%d", *(int *)paramValues[i]);
00444 break;
00445 case XDR_REAL32:
00446 sprintf(val, "%f", *(float *)paramValues[i]);
00447 break;
00448 case XDR_REAL64:
00449 sprintf(val, "%f", *(double *)(paramValues[i]));
00450 break;
00451 }
00452 strcat(logmsg, val);
00453 logger(level, logmsg);
00454 }
00455 }
00456
00457
00458 bool apmon_utils::isPrivateAddress(char *addr) {
00459 char *s1, *s2;
00460 int n1, n2;
00461 char tmp[MAX_STRING_LEN];
00462
00463
00464
00465 strcpy(tmp, addr);
00466 s1 = strtok(tmp,".");
00467 n1 = atoi(s1);
00468
00469 s2 = strtok(NULL, ".");
00470 n2 = atoi(s2);
00471
00472 if (n1 == 10)
00473 return true;
00474 if (n1 == 172 && n2 >= 16 && n2 <= 31)
00475 return true;
00476 if (n1 == 192 && n2 == 168)
00477 return true;
00478
00479 return false;
00480 }
00481
00482 int apmon_utils::getVectIndex(char *item, char **vect, int vectDim) {
00483 int i;
00484
00485 for (i = 0; i < vectDim; i++)
00486 if (strcmp(item, vect[i]) == 0)
00487 return i;
00488 return -1;
00489 }
00490
00491 void apmon_utils::logger(int msgLevel, const char *msg, int newLevel) {
00492 char time_s[30];
00493 int len;
00494 time_t crtTime = time(NULL);
00495 char *levels[5] = {(char*)"FATAL",
00496 (char*)"WARNING",
00497 (char*)"INFO",
00498 (char*)"FINE",
00499 (char*)"DEBUG"};
00500 static int loglevel = INFO;
00501 #ifndef WIN32
00502 static pthread_mutex_t logger_mutex;
00503 #else
00504 static HANDLE logger_mutex;
00505 #endif
00506 static bool firstTime = true;
00507
00508 if (firstTime) {
00509 #ifndef WIN32
00510 pthread_mutex_init(&logger_mutex, NULL);
00511 #else
00512 logger_mutex = CreateMutex(NULL, FALSE, NULL);
00513 #endif
00514 firstTime = false;
00515 }
00516
00517 pthread_mutex_lock(&logger_mutex);
00518
00519 #ifndef WIN32
00520 char cbuf[50];
00521 strcpy(time_s, ctime_r(&crtTime, cbuf));
00522 #else
00523 strcpy(time_s, ctime(&crtTime));
00524 #endif
00525 len = strlen(time_s); time_s[len - 1] = 0;
00526
00527 if (newLevel >= 0 && newLevel <=4) {
00528 loglevel = newLevel;
00529 if (loglevel>=2)
00530 printf("[TIME: %s] Changed the logging level to %s\n", time_s, levels[newLevel]);
00531 } else {
00532 if (msgLevel >= 0 && msgLevel <= 4) {
00533 if (msgLevel <= loglevel)
00534 printf("[TIME: %s] [%s] %s\n",time_s, levels[msgLevel], msg);
00535 } else
00536 printf("[WARNING] Invalid logging level %d!\n", msgLevel);
00537 }
00538 pthread_mutex_unlock(&logger_mutex);
00539 }