Browse code

freshclam/manager.c: add support for http proxy in SubmitDetectionStats (bb#1284)

git-svn-id: file:///var/lib/svn/clamav-devel/branches/clamav-0.94@4456 77e5149b-7576-45b1-b177-96237e5ba77b

Tomasz Kojm authored on 2008/11/22 07:39:38
Showing 2 changed files
... ...
@@ -1,3 +1,8 @@
1
+Fri Nov 21 23:40:19 CET 2008 (tk)
2
+---------------------------------
3
+ * freshclam/manager.c: add support for http proxy in SubmitDetectionStats
4
+			(bb#1284)
5
+
1 6
 Thu Nov 20 21:53:39 EET 2008 (edwin)
2 7
 ------------------------------------
3 8
  * configure, m4/lib-link.m4: more multiarch dir fixes (bb #1277)
... ...
@@ -462,10 +462,78 @@ static const char *readbline(int fd, char *buf, int bufsize, int filesize, int *
462 462
     }
463 463
 }
464 464
 
465
+static unsigned int fmt_base64(char *dest, const char *src, unsigned int len)
466
+{
467
+	unsigned short bits = 0,temp = 0;
468
+	unsigned long written = 0;
469
+	unsigned int i;
470
+	const char base64[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
471
+
472
+
473
+    for(i = 0; i < len; i++) {
474
+	temp <<= 8;
475
+	temp += src[i];
476
+	bits += 8;
477
+	while(bits > 6) {
478
+	    dest[written] = base64[((temp >> (bits - 6)) & 63)];
479
+	    written++;
480
+	    bits -= 6;
481
+	}
482
+    }
483
+
484
+    if(bits) {
485
+	temp <<= (6 - bits);
486
+	dest[written] = base64[temp & 63];
487
+	written++;
488
+    }
489
+
490
+    while(written & 3) {
491
+	dest[written] = '=';
492
+	written++;
493
+    }
494
+
495
+    return written;
496
+}
497
+
498
+static char *proxyauth(const char *user, const char *pass)
499
+{
500
+	int len;
501
+	char *buf, *userpass, *auth;
502
+
503
+
504
+    userpass = malloc(strlen(user) + strlen(pass) + 2);
505
+    if(!userpass) {
506
+	logg("!proxyauth: Can't allocate memory for 'userpass'\n");
507
+	return NULL;
508
+    }
509
+    sprintf(userpass, "%s:%s", user, pass);
510
+
511
+    buf = malloc((strlen(pass) + strlen(user)) * 2 + 4);
512
+    if(!buf) {
513
+	logg("!proxyauth: Can't allocate memory for 'buf'\n");
514
+	free(userpass);
515
+	return NULL;
516
+    }
517
+
518
+    len = fmt_base64(buf, userpass, strlen(userpass));
519
+    free(userpass);
520
+    buf[len] = '\0';
521
+    auth = malloc(strlen(buf) + 30);
522
+    if(!auth) {
523
+	free(buf);
524
+	logg("!proxyauth: Can't allocate memory for 'authorization'\n");
525
+	return NULL;
526
+    }
527
+
528
+    sprintf(auth, "Proxy-Authorization: Basic %s\r\n", buf);
529
+    free(buf);
530
+
531
+    return auth;
532
+}
533
+
465 534
 /*
466 535
  * TODO:
467 536
  * - strptime() is most likely not portable enough
468
- * - proxy support
469 537
  */
470 538
 int submitstats(const char *clamdcfg, const struct cfgstruct *copt)
471 539
 {
... ...
@@ -474,14 +542,14 @@ int submitstats(const char *clamdcfg, const struct cfgstruct *copt)
474 474
 	char query[SUBMIT_MIN_ENTRIES * 256];
475 475
 	char buff[512], statsdat[512], newstatsdat[512], uastr[128];
476 476
 	char logfile[256], fbuff[FILEBUFF];
477
-	char *pt, *pt2;
478
-	const char *line, *country = NULL;
477
+	char *pt, *pt2, *auth = NULL;
478
+	const char *line, *country = NULL, *user, *proxy = NULL;
479 479
 	struct cfgstruct *clamdopt;
480 480
 	const struct cfgstruct *cpt;
481 481
 	struct stat sb;
482 482
 	struct tm tms;
483 483
 	time_t epoch;
484
-	unsigned int qcnt, entries, submitted = 0, permfail = 0;
484
+	unsigned int qcnt, entries, submitted = 0, permfail = 0, port = 0;
485 485
 
486 486
 
487 487
     if((cpt = cfgopt(copt, "DetectionStatsCountry"))->enabled) {
... ...
@@ -558,6 +626,31 @@ int submitstats(const char *clamdcfg, const struct cfgstruct *copt)
558 558
 	snprintf(uastr, sizeof(uastr), PACKAGE"/%s (OS: "TARGET_OS_TYPE", ARCH: "TARGET_ARCH_TYPE", CPU: "TARGET_CPU_TYPE")%s%s", get_version(), country ? ":" : "", country ? country : "");
559 559
     uastr[sizeof(uastr) - 1] = 0;
560 560
 
561
+    if((cpt = cfgopt(copt, "HTTPProxyServer"))->enabled) {
562
+	proxy = cpt->strarg;
563
+	if(!strncasecmp(proxy, "http://", 7))
564
+	    proxy += 7;
565
+
566
+	if((cpt = cfgopt(copt, "HTTPProxyUsername"))->enabled) {
567
+	    user = cpt->strarg;
568
+	    if(!(cpt = cfgopt(copt, "HTTPProxyPassword"))->enabled) {
569
+		logg("!SubmitDetectionStats: HTTPProxyUsername requires HTTPProxyPassword\n");
570
+		close(fd);
571
+		return 56;
572
+	    }
573
+	    auth = proxyauth(user, cpt->strarg);
574
+	    if(!auth) {
575
+		close(fd);
576
+		return 56;
577
+	    }
578
+	}
579
+
580
+	if((cpt = cfgopt(copt, "HTTPProxyPort"))->enabled)
581
+	    port = cpt->numarg;
582
+
583
+	logg("*Connecting via %s\n", proxy);
584
+    }
585
+
561 586
     ret = 0;
562 587
     memset(query, 0, sizeof(query));
563 588
     qcnt = 0;
... ...
@@ -609,7 +702,7 @@ int submitstats(const char *clamdcfg, const struct cfgstruct *copt)
609 609
 	entries++;
610 610
 
611 611
 	if(entries == SUBMIT_MIN_ENTRIES) {
612
-	    sd = wwwconnect("stats.clamav.net", NULL, 0, NULL, cfgopt(copt, "LocalIPAddress")->strarg, cfgopt(copt, "ConnectTimeout")->numarg, NULL, 0, 0);
612
+	    sd = wwwconnect("stats.clamav.net", proxy, port, NULL, cfgopt(copt, "LocalIPAddress")->strarg, cfgopt(copt, "ConnectTimeout")->numarg, NULL, 0, 0);
613 613
 	    if(sd == -1) {
614 614
 		logg("!SubmitDetectionStats: Can't connect to server\n");
615 615
 		ret = 52;
... ...
@@ -618,13 +711,13 @@ int submitstats(const char *clamdcfg, const struct cfgstruct *copt)
618 618
 
619 619
 	    query[sizeof(query) - 1] = 0;
620 620
 	    snprintf(post, sizeof(post),
621
-		"POST /submit.php HTTP/1.0\r\n"
622
-		"Host: stats.clamav.net\r\n"
621
+		"POST http://stats.clamav.net/submit.php HTTP/1.0\r\n"
622
+		"Host: stats.clamav.net\r\n%s"
623 623
 		"Content-Type: application/x-www-form-urlencoded\r\n"
624 624
 		"User-Agent: %s\r\n"
625 625
 		"Content-Length: %u\r\n\n"
626 626
 		"%s",
627
-	    uastr, (unsigned int) strlen(query), query);
627
+	    auth ? auth : "", uastr, (unsigned int) strlen(query), query);
628 628
 
629 629
 	    if(send(sd, post, strlen(post), 0) < 0) {
630 630
 		logg("!SubmitDetectionStats: Can't write to socket\n");
... ...
@@ -691,6 +784,8 @@ int submitstats(const char *clamdcfg, const struct cfgstruct *copt)
691 691
     } while((line = readbline(fd, fbuff, FILEBUFF, sb.st_size, &lread)));
692 692
 
693 693
     close(fd);
694
+    if(auth)
695
+	free(auth);
694 696
 
695 697
     if(submitted || permfail) {
696 698
 	if((fd = open("stats.dat", O_WRONLY | O_CREAT | O_TRUNC, 0600)) == -1) {
... ...
@@ -720,75 +815,6 @@ static int Rfc2822DateTime(char *buf, time_t mtime)
720 720
     return strftime(buf, 36, "%a, %d %b %Y %X GMT", gmt);
721 721
 }
722 722
 
723
-static unsigned int fmt_base64(char *dest, const char *src, unsigned int len)
724
-{
725
-	unsigned short bits = 0,temp = 0;
726
-	unsigned long written = 0;
727
-	unsigned int i;
728
-	const char base64[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
729
-
730
-
731
-    for(i = 0; i < len; i++) {
732
-	temp <<= 8;
733
-	temp += src[i];
734
-	bits += 8;
735
-	while(bits > 6) {
736
-	    dest[written] = base64[((temp >> (bits - 6)) & 63)];
737
-	    written++;
738
-	    bits -= 6;
739
-	}
740
-    }
741
-
742
-    if(bits) {
743
-	temp <<= (6 - bits);
744
-	dest[written] = base64[temp & 63];
745
-	written++;
746
-    }
747
-
748
-    while(written & 3) {
749
-	dest[written] = '=';
750
-	written++;
751
-    }
752
-
753
-    return written;
754
-}
755
-
756
-static char *proxyauth(const char *user, const char *pass)
757
-{
758
-	int len;
759
-	char *buf, *userpass, *auth;
760
-
761
-
762
-    userpass = malloc(strlen(user) + strlen(pass) + 2);
763
-    if(!userpass) {
764
-	logg("!proxyauth: Can't allocate memory for 'userpass'\n");
765
-	return NULL;
766
-    }
767
-    sprintf(userpass, "%s:%s", user, pass);
768
-
769
-    buf = malloc((strlen(pass) + strlen(user)) * 2 + 4);
770
-    if(!buf) {
771
-	logg("!proxyauth: Can't allocate memory for 'buf'\n");
772
-	free(userpass);
773
-	return NULL;
774
-    }
775
-
776
-    len = fmt_base64(buf, userpass, strlen(userpass));
777
-    free(userpass);
778
-    buf[len] = '\0';
779
-    auth = malloc(strlen(buf) + 30);
780
-    if(!auth) {
781
-	free(buf);
782
-	logg("!proxyauth: Can't allocate memory for 'authorization'\n");
783
-	return NULL;
784
-    }
785
-
786
-    sprintf(auth, "Proxy-Authorization: Basic %s\r\n", buf);
787
-    free(buf);
788
-
789
-    return auth;
790
-}
791
-
792 723
 static struct cl_cvd *remote_cvdhead(const char *file, const char *hostname, char *ip, const char *localip, const char *proxy, int port, const char *user, const char *pass, const char *uas, int *ims, int ctimeout, int rtimeout, struct mirdat *mdat, int logerr, unsigned int can_whitelist)
793 724
 {
794 725
 	char cmd[512], head[513], buffer[FILEBUFF], ipaddr[46], *ch, *tmp;