f87a4828551de75b24d3a096cf58268d15821e03
[cacert-devel.git] / includes / general.php
1 <? /*
2 LibreSSL - CAcert web application
3 Copyright (C) 2004-2008 CAcert Inc.
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; version 2 of the License.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17 */
18
19 require_once(dirname(__FILE__)."/lib/general.php");
20
21 session_name("cacert");
22 session_start();
23
24 // session_register("_config");
25 // session_register("profile");
26 // session_register("signup");
27 // session_register("lostpw");
28 // if($_SESSION['profile']['id'] > 0)
29 // session_regenerate_id();
30
31 //cf. http://stackoverflow.com/a/14532168
32 if(!defined('ENT_HTML401')) define('ENT_HTML401', 0);
33 if(!defined('ENT_XML1')) define('ENT_XML1', 16);
34 if(!defined('ENT_XHTML')) define('ENT_XHTML', 32);
35 if(!defined('ENT_HTML5')) define('ENT_HTML5', (32|16));
36
37 $pageLoadTime_Start = microtime(true);
38
39 $junk = array(_("Face to Face Meeting"), _("Trusted Third Parties"), _("Thawte Points Transfer"), _("Administrative Increase"),
40 _("CT Magazine - Germany"), _("Temporary Increase"), _("Unknown"));
41
42 $_SESSION['_config']['errmsg']="";
43
44 $id = 0; if(array_key_exists("id",$_REQUEST)) $id=intval($_REQUEST['id']);
45 $oldid = 0; if(array_key_exists("oldid",$_REQUEST)) $oldid=intval($_REQUEST['oldid']);
46
47 $_SESSION['_config']['filepath'] = "/www";
48
49 require_once($_SESSION['_config']['filepath']."/includes/mysql.php");
50 require_once($_SESSION['_config']['filepath'].'/includes/lib/account.php');
51 require_once($_SESSION['_config']['filepath'].'/includes/lib/l10n.php');
52
53 if(array_key_exists('HTTP_HOST',$_SERVER) &&
54 $_SERVER['HTTP_HOST'] != $_SESSION['_config']['normalhostname'] &&
55 $_SERVER['HTTP_HOST'] != $_SESSION['_config']['securehostname'])
56 {
57 if(array_key_exists('HTTPS',$_SERVER) && $_SERVER['HTTPS'] == "on")
58 header("location: https://".$_SESSION['_config']['normalhostname']);
59 else
60 header("location: http://".$_SESSION['_config']['normalhostname']);
61 exit;
62 }
63
64 if(array_key_exists('HTTP_HOST',$_SERVER) &&
65 ($_SERVER['HTTP_HOST'] == $_SESSION['_config']['securehostname']))
66 {
67 if(array_key_exists('HTTPS',$_SERVER) && $_SERVER['HTTPS'] == "on")
68 {
69 }
70 else
71 {
72 if($_SERVER['HTTP_HOST'] == $_SESSION['_config']['securehostname']){
73 header("location: https://". $_SESSION['_config']['securehostname']);
74 }
75 exit;
76
77 }
78 }
79
80 L10n::detect_language();
81 L10n::init_gettext();
82
83 if(array_key_exists('profile',$_SESSION) && is_array($_SESSION['profile']) && array_key_exists('id',$_SESSION['profile']) && $_SESSION['profile']['id'] > 0)
84 {
85 $locked = mysql_fetch_assoc(mysql_query("select `locked` from `users` where `id`='".intval($_SESSION['profile']['id'])."'"));
86 if($locked['locked'] == 0)
87 {
88 update_points_in_profile();
89 } else {
90 $_SESSION['profile'] = "";
91 unset($_SESSION['profile']);
92 }
93 }
94
95 function loadem($section = "index")
96 {
97 if($section != "index" && $section != "account")
98 {
99 $section = "index";
100 }
101
102 if($section == "account"){
103 include_once($_SESSION['_config']['filepath']."/includes/account_stuff.php");
104 }
105
106 if($section == "index"){
107 include_once($_SESSION['_config']['filepath']."/includes/general_stuff.php");
108 }
109 }
110
111 function includeit($id = "0", $section = "index")
112 {
113 $id = intval($id);
114 if($section != "index" && $section != "account" && $section != "wot" && $section != "help" && $section != "gpg" && $section != "disputes" && $section != "advertising")
115 {
116 $section = "index";
117 }
118
119 if(file_exists($_SESSION['_config']['filepath']."/pages/$section/$id.php")){
120 include_once($_SESSION['_config']['filepath']."/pages/$section/$id.php");
121 }
122 else {
123 $id = "0";
124
125 if(file_exists($_SESSION['_config']['filepath']."/pages/$section/$id.php")){
126 include_once($_SESSION['_config']['filepath']."/pages/$section/$id.php");
127 } else {
128
129 $section = "index";
130 $id = "0";
131
132 if(file_exists($_SESSION['_config']['filepath']."/pages/$section/$id.php")){
133 include_once($_SESSION['_config']['filepath']."/pages/$section/$id.php");
134 } else {
135 include_once($_SESSION['_config']['filepath']."/www/error404.php");
136 }
137 }
138 }
139 }
140
141 function checkpwlight($pwd) {
142 $points = 0;
143
144 if(strlen($pwd) > 15)
145 $points++;
146 if(strlen($pwd) > 20)
147 $points++;
148 if(strlen($pwd) > 25)
149 $points++;
150 if(strlen($pwd) > 30)
151 $points++;
152
153 //echo "Points due to length: $points<br/>";
154
155 if(preg_match("/\d/", $pwd))
156 $points++;
157
158 if(preg_match("/[a-z]/", $pwd))
159 $points++;
160
161 if(preg_match("/[A-Z]/", $pwd))
162 $points++;
163
164 if(preg_match("/\W/", $pwd))
165 $points++;
166
167 if(preg_match("/\s/", $pwd))
168 $points++;
169
170 //echo "Points due to length and charset: $points<br/>";
171
172 // check for historical password proposal
173 if ($pwd === "Fr3d Sm|7h") {
174 return 0;
175 }
176
177 return $points;
178 }
179
180 function checkpw($pwd, $email, $fname, $mname, $lname, $suffix)
181 {
182 $points = checkpwlight($pwd);
183
184 if(@strstr(strtolower($pwd), strtolower($email)))
185 $points--;
186
187 if(@strstr(strtolower($email), strtolower($pwd)))
188 $points--;
189
190 if(@strstr(strtolower($pwd), strtolower($fname)))
191 $points--;
192
193 if(@strstr(strtolower($fname), strtolower($pwd)))
194 $points--;
195
196 if($mname)
197 if(@strstr(strtolower($pwd), strtolower($mname)))
198 $points--;
199
200 if($mname)
201 if(@strstr(strtolower($mname), strtolower($pwd)))
202 $points--;
203
204 if(@strstr(strtolower($pwd), strtolower($lname)))
205 $points--;
206
207 if(@strstr(strtolower($lname), strtolower($pwd)))
208 $points--;
209
210 if($suffix)
211 if(@strstr(strtolower($pwd), strtolower($suffix)))
212 $points--;
213
214 if($suffix)
215 if(@strstr(strtolower($suffix), strtolower($pwd)))
216 $points--;
217
218 //echo "Points due to name matches: $points<br/>";
219
220 $shellpwd = escapeshellarg($pwd);
221 $do = shell_exec("grep -F -- $shellpwd /usr/share/dict/american-english");
222 if($do)
223 $points--;
224
225 //echo "Points due to wordlist: $points<br/>";
226
227 return($points);
228 }
229
230 function extractit()
231 {
232 $bits = explode(": ", $_SESSION['_config']['subject'], 2);
233 $bits = str_replace(", ", "|", str_replace("/", "|", array_key_exists('1',$bits)?$bits['1']:""));
234 $bits = explode("|", $bits);
235
236 $_SESSION['_config']['cnc'] = $_SESSION['_config']['subaltc'] = 0;
237 $_SESSION['_config']['OU'] = "";
238
239 if(is_array($bits))
240 foreach($bits as $val)
241 {
242 if(!strstr($val, "="))
243 continue;
244
245 $split = explode("=", $val);
246
247 $k = $split[0];
248 $split['1'] = trim($split['1']);
249 if($k == "CN" && $split['1'])
250 {
251 $k = $_SESSION['_config']['cnc'].".".$k;
252 $_SESSION['_config']['cnc']++;
253 $_SESSION['_config'][$k] = $split['1'];
254 }
255 if($k == "OU" && $split['1'] && $_SESSION['_config']['OU'] == "")
256 {
257 $_SESSION['_config']['OU'] = $split['1'];
258 }
259 if($k == "subjectAltName" && $split['1'])
260 {
261 $k = $_SESSION['_config']['subaltc'].".".$k;
262 $_SESSION['_config']['subaltc']++;
263 $_SESSION['_config'][$k] = $split['1'];
264 }
265 }
266 }
267
268 function isValidWildcard($name){
269 if(substr($name,0,2) == "*."){
270 $name = substr($name, 2);
271 }
272 if(!preg_match('/^(\\.(?!-)[a-z0-9_-]*[a-z0-9])+$/i','.'.$name)){
273 return false;
274 }
275 return strpos($name, "*") === false;
276 }
277
278 function getcn()
279 {
280 unset($_SESSION['_config']['rows']);
281 unset($_SESSION['_config']['rowid']);
282 unset($_SESSION['_config']['rejected']);
283 $rows=array();
284 $rowid=array();
285 for($cnc = 0; $cnc < $_SESSION['_config']['cnc']; $cnc++)
286 {
287 $CN = $_SESSION['_config']["$cnc.CN"];
288 $bits = explode(".", $CN);
289 $dom = "";
290 $cnok = 0;
291
292 if(!isValidWildcard($CN)){
293 $_SESSION['_config']['rejected'][] = $CN;
294 continue;
295 }
296
297 for($i = count($bits) - 1; $i >= 0; $i--)
298 {
299 if($dom)
300 $dom = $bits[$i].".".$dom;
301 else
302 $dom = $bits[$i];
303 $_SESSION['_config']['row'] = "";
304 $dom = mysql_real_escape_string($dom);
305 $query = "select * from domains where `memid`='".intval($_SESSION['profile']['id'])."' and `domain` = '$dom' and `deleted`=0 and `hash`=''";
306 $res = mysql_query($query);
307 if(mysql_num_rows($res) > 0)
308 {
309 $cnok = 1;
310 $_SESSION['_config']['row'] = mysql_fetch_assoc($res);
311 $rowid[] = $_SESSION['_config']['row']['id'];
312 break;
313 }
314 }
315
316 if($cnok == 0)
317 $_SESSION['_config']['rejected'][] = $CN;
318
319 if($_SESSION['_config']['row'] != "")
320 $rows[] = $CN;
321 }
322 // if(count($rows) <= 0)
323 // {
324 // echo _("There were no valid CommonName fields on the CSR, or I was unable to match any of these against your account. Please review your CSR, or add and verify domains contained in it to your account before trying again.");
325 // exit;
326 // }
327
328 $_SESSION['_config']['rows'] = $rows;
329 $_SESSION['_config']['rowid'] = $rowid;
330 }
331
332 function getalt()
333 {
334 unset($_SESSION['_config']['altrows']);
335 unset($_SESSION['_config']['altid']);
336 $altrows=array();
337 $altid=array();
338 for($altc = 0; $altc < $_SESSION['_config']['subaltc']; $altc++)
339 {
340 $subalt = $_SESSION['_config']["$altc.subjectAltName"];
341 if(substr($subalt, 0, 4) == "DNS:")
342 $alt = substr($subalt, 4);
343 else
344 continue;
345
346 if(!isValidWildcard($alt)){
347 $_SESSION['_config']['rejected'][] = $alt;
348 continue;
349 }
350
351 $bits = explode(".", $alt);
352 $dom = "";
353 $altok = 0;
354 for($i = count($bits) - 1; $i >= 0; $i--)
355 {
356 if($dom)
357 $dom = $bits[$i].".".$dom;
358 else
359 $dom = $bits[$i];
360 $_SESSION['_config']['altrow'] = "";
361 $dom = mysql_real_escape_string($dom);
362 $query = "select * from domains where `memid`='".intval($_SESSION['profile']['id'])."' and `domain` = '$dom' and `deleted`=0 and `hash`=''";
363 $res = mysql_query($query);
364 if(mysql_num_rows($res) > 0)
365 {
366 $altok = 1;
367 $_SESSION['_config']['altrow'] = mysql_fetch_assoc($res);
368 $altid[] = $_SESSION['_config']['altrow']['id'];
369 break;
370 }
371 }
372
373 if($altok == 0)
374 $_SESSION['_config']['rejected'][] = $alt;
375
376 if($_SESSION['_config']['altrow'] != "")
377 $altrows[] = $subalt;
378 }
379 $_SESSION['_config']['altrows'] = $altrows;
380 $_SESSION['_config']['altid'] = $altid;
381 }
382
383 function getcn2()
384 {
385 $rows=array();
386 $rowid=array();
387 for($cnc = 0; $cnc < $_SESSION['_config']['cnc']; $cnc++)
388 {
389 $CN = $_SESSION['_config']["$cnc.CN"];
390 $bits = explode(".", $CN);
391 $dom = "";
392
393 if(!isValidWildcard($CN)){
394 $_SESSION['_config']['rejected'][] = $CN;
395 continue;
396 }
397
398 for($i = count($bits) - 1; $i >= 0; $i--)
399 {
400 if($dom)
401 $dom = $bits[$i].".".$dom;
402 else
403 $dom = $bits[$i];
404 $_SESSION['_config']['row'] = "";
405 $dom = mysql_real_escape_string($dom);
406 $query = "select *, `orginfo`.`id` as `id` from `orginfo`,`orgdomains`,`org` where
407 `org`.`memid`='".intval($_SESSION['profile']['id'])."' and
408 `org`.`orgid`=`orginfo`.`id` and
409 `orgdomains`.`orgid`=`orginfo`.`id` and
410 `orgdomains`.`domain`='$dom'";
411 $res = mysql_query($query);
412 if(mysql_num_rows($res) > 0)
413 {
414 $_SESSION['_config']['row'] = mysql_fetch_assoc($res);
415 $rowid[] = $_SESSION['_config']['row']['id'];
416 break;
417 }
418 }
419
420 if($_SESSION['_config']['row'] != "")
421 $rows[] = $CN;
422 }
423 // if(count($rows) <= 0)
424 // {
425 // echo _("There were no valid CommonName fields on the CSR, or I was unable to match any of these against your account. Please review your CSR, or add and verify domains contained in it to your account before trying again.");
426 // exit;
427 // }
428 $_SESSION['_config']['rows'] = $rows;
429 $_SESSION['_config']['rowid'] = $rowid;
430 }
431
432 function getalt2()
433 {
434 $altrows=array();
435 $altid=array();
436 for($altc = 0; $altc < $_SESSION['_config']['subaltc']; $altc++)
437 {
438 $subalt = $_SESSION['_config']["$altc.subjectAltName"];
439 if(substr($subalt, 0, 4) == "DNS:")
440 $alt = substr($subalt, 4);
441 else
442 continue;
443
444 if(!isValidWildcard($alt)){
445 $_SESSION['_config']['rejected'][] = $alt;
446 continue;
447 }
448
449 $bits = explode(".", $alt);
450 $dom = "";
451 for($i = count($bits) - 1; $i >= 0; $i--)
452 {
453 if($dom)
454 $dom = $bits[$i].".".$dom;
455 else
456 $dom = $bits[$i];
457 $_SESSION['_config']['altrow'] = "";
458 $dom = mysql_real_escape_string($dom);
459 $query = "select * from `orginfo`,`orgdomains`,`org` where
460 `org`.`memid`='".intval($_SESSION['profile']['id'])."' and
461 `org`.`orgid`=`orginfo`.`id` and
462 `orgdomains`.`orgid`=`orginfo`.`id` and
463 `orgdomains`.`domain`='$dom'";
464 $res = mysql_query($query);
465 if(mysql_num_rows($res) > 0)
466 {
467 $_SESSION['_config']['altrow'] = mysql_fetch_assoc($res);
468 $altid[] = $_SESSION['_config']['altrow']['id'];
469 break;
470 }
471 }
472
473 if($_SESSION['_config']['altrow'] != "")
474 $altrows[] = $subalt;
475 }
476 $_SESSION['_config']['altrows'] = $altrows;
477 $_SESSION['_config']['altid'] = $altid;
478 }
479
480 function checkownership($hostname)
481 {
482 $bits = explode(".", $hostname);
483 $dom = "";
484 for($i = count($bits) - 1; $i >= 0; $i--)
485 {
486 if($dom)
487 $dom = $bits[$i].".".$dom;
488 else
489 $dom = $bits[$i];
490 $dom = mysql_real_escape_string($dom);
491 $query = "select * from `org`,`orgdomains`,`orginfo`
492 where `org`.`memid`='".intval($_SESSION['profile']['id'])."'
493 and `orgdomains`.`orgid`=`org`.`orgid`
494 and `orginfo`.`id`=`org`.`orgid`
495 and `orgdomains`.`domain`='$dom'";
496 $res = mysql_query($query);
497 if(mysql_num_rows($res) > 0)
498 {
499 $_SESSION['_config']['row'] = mysql_fetch_assoc($res);
500 return(true);
501 }
502 }
503 return(false);
504 }
505
506 function maxpoints($id = 0)
507 {
508 if($id <= 0)
509 $id = $_SESSION['profile']['id'];
510
511 $points = get_received_total_points($id);
512
513 $dob = date("Y-m-d", mktime(0,0,0,date("m"),date("d"),date("Y")-18));
514 $query = "select * from `users` where `id`='".intval($_SESSION['profile']['id'])."' and `dob` < '$dob'";
515 if(mysql_num_rows(mysql_query($query)) < 1)
516 {
517 if($points >= 100)
518 return(10);
519 else
520 return(0);
521 }
522
523 if($points >= 150)
524 return(35);
525 if($points >= 140)
526 return(30);
527 if($points >= 130)
528 return(25);
529 if($points >= 120)
530 return(20);
531 if($points >= 110)
532 return(15);
533 if($points >= 100)
534 return(10);
535 return(0);
536 }
537
538 /**
539 * Decode UTF-8 byte sequences into HTML entities
540 *
541 * @see https://blog.benny-baumann.de/?p=332
542 */
543 function charset_decode_utf8_callback($match) {
544 $m = $match[0];
545
546 switch(strlen($m)) {
547 case 6:
548 // decode six byte unicode characters
549 return '&#'.((ord($m[0])-252)*1073741824+(ord($m[1])-200)*16777216+(ord($m[2])-200)*262144+(ord($m[3])-128)*4096+(ord($m[4])-128)*64+(ord($m[5])-128)).';';
550 case 5:
551 // decode five byte unicode characters
552 return '&#'.((ord($m[0])-248)*16777216+(ord($m[1])-200)*262144+(ord($m[2])-128)*4096+(ord($m[3])-128)*64+(ord($m[4])-128)).';';
553 case 4:
554 // decode four byte unicode characters
555 return '&#'.((ord($m[0])-240)*262144+(ord($m[1])-128)*4096+(ord($m[2])-128)*64+(ord($m[3])-128)).';';
556 case 3:
557 // decode three byte unicode characters
558 return '&#'.((ord($m[0])-224)*4096+(ord($m[1])-128)*64+(ord($m[2])-128)).';';
559 case 2:
560 // decode two byte unicode characters
561 return '&#'.((ord($m[0])-192)*64+(ord($m[1])-128)).';';
562 default:
563 return $m;
564 }
565 }
566
567 /**
568 * Decode utf-8 strings
569 * @param string $string Encoded string
570 * @return string Decoded string
571 * @see https://blog.benny-baumann.de/?p=332
572 */
573 function charset_decode_utf8 ($string) {
574 // decode 2-6 byte unicode characters
575 $string = preg_replace_callback("/[\374-\375][\200-\277][\200-\277][\200-\277][\200-\277][\200-\277]|".
576 "[\370-\373][\200-\277][\200-\277][\200-\277][\200-\277]|".
577 "[\360-\367][\200-\277][\200-\277][\200-\277]|".
578 "[\340-\357][\200-\277][\200-\277]|".
579 "[\300-\337][\200-\277]/",
580 'charset_decode_utf8_callback', $string);
581
582 // remove broken unicode
583 $string = preg_replace("/[\200-\237]|\240|[\241-\377]/",'?',$string);
584
585 return $string;
586 }
587
588 function gpg_hex2bin($data)
589 {
590 while(strstr($data, "\\x"))
591 {
592 $pos = strlen($data) - strlen(strstr($data, "\\x"));
593 $before = substr($data, 0, $pos);
594 $char = chr(hexdec(substr($data, $pos + 2, 2)));
595 $after = substr($data, $pos + 4);
596 $data = $before.$char.$after;
597 }
598
599 return htmlentities(charset_decode_utf8($data), ENT_QUOTES | ENT_SUBSTITUTE, 'UTF-8', false);
600 }
601
602 function signmail($to, $subject, $message, $from, $replyto = "")
603 {
604 if($replyto == "")
605 $replyto = $from;
606 $tmpfname = tempnam("/tmp", "CSR");
607 $fp = fopen($tmpfname, "w");
608 fputs($fp, $message);
609 fclose($fp);
610 $to_esc = escapeshellarg($to);
611 $do = shell_exec("/usr/bin/gpg --homedir /home/gpg --clearsign \"$tmpfname\"|/usr/sbin/sendmail ".$to_esc);
612 @unlink($tmpfname);
613 }
614
615 function checkEmail($email)
616 {
617 $myemail = mysql_real_escape_string($email);
618 if(preg_match("/^([a-zA-Z0-9])+([a-zA-Z0-9\+\._-])*@([a-zA-Z0-9_-])+([a-zA-Z0-9\._-]+)+$/" , $email))
619 {
620 list($username,$domain)=explode('@',$email,2);
621 $mxhostrr = array();
622 $mxweight = array();
623 if( !getmxrr($domain, $mxhostrr, $mxweight) ) {
624 $mxhostrr = array($domain);
625 $mxweight = array(0);
626 } else if ( empty($mxhostrr) ) {
627 $mxhostrr = array($domain);
628 $mxweight = array(0);
629 }
630
631 $mxhostprio = array();
632 for($i = 0; $i < count($mxhostrr); $i++) {
633 $mx_host = trim($mxhostrr[$i], '.');
634 $mx_prio = $mxweight[$i];
635 if(empty($mxhostprio[$mx_prio])) {
636 $mxhostprio[$mx_prio] = array();
637 }
638 $mxhostprio[$mx_prio][] = $mx_host;
639 }
640
641 array_walk($mxhostprio, function(&$mx) { shuffle($mx); } );
642 ksort($mxhostprio);
643
644 $mxhosts = array();
645 foreach($mxhostprio as $mx_prio => $mxhostnames) {
646 foreach($mxhostnames as $mx_host) {
647 $mxhosts[] = $mx_host;
648 }
649 }
650
651 foreach($mxhosts as $key => $domain)
652 {
653 $fp_opt = array(
654 'ssl' => array(
655 'verify_peer' => false, // Opportunistic Encryption
656 )
657 );
658 $fp_ctx = stream_context_create($fp_opt);
659 $fp = @stream_socket_client("tcp://$domain:25",$errno,$errstr,5,STREAM_CLIENT_CONNECT,$fp_ctx);
660 if($fp)
661 {
662 stream_set_blocking($fp, true);
663
664 $has_starttls = false;
665
666 do {
667 $line = fgets($fp, 4096);
668 } while(substr($line, 0, 4) == "220-");
669 if(substr($line, 0, 3) != "220") {
670 fclose($fp);
671 continue;
672 }
673
674 fputs($fp, "EHLO www.cacert.org\r\n");
675 do {
676 $line = fgets($fp, 4096);
677 $has_starttls |= substr(trim($line),4) == "STARTTLS";
678 } while(substr($line, 0, 4) == "250-");
679 if(substr($line, 0, 3) != "250") {
680 fclose($fp);
681 continue;
682 }
683
684 if($has_starttls) {
685 fputs($fp, "STARTTLS\r\n");
686 do {
687 $line = fgets($fp, 4096);
688 } while(substr($line, 0, 4) == "220-");
689 if(substr($line, 0, 3) != "220") {
690 fclose($fp);
691 continue;
692 }
693
694 stream_socket_enable_crypto($fp, true, STREAM_CRYPTO_METHOD_TLS_CLIENT);
695
696 fputs($fp, "EHLO www.cacert.org\r\n");
697 do {
698 $line = fgets($fp, 4096);
699 } while(substr($line, 0, 4) == "250-");
700 if(substr($line, 0, 3) != "250") {
701 fclose($fp);
702 continue;
703 }
704 }
705
706 fputs($fp, "MAIL FROM:<returns@cacert.org>\r\n");
707 do {
708 $line = fgets($fp, 4096);
709 } while(substr($line, 0, 4) == "250-");
710 if(substr($line, 0, 3) != "250") {
711 fclose($fp);
712 continue;
713 }
714
715 fputs($fp, "RCPT TO:<$email>\r\n");
716 do {
717 $line = fgets($fp, 4096);
718 } while(substr($line, 0, 4) == "250-");
719 if(substr($line, 0, 3) != "250") {
720 fclose($fp);
721 continue;
722 }
723
724 fputs($fp, "QUIT\r\n");
725 fclose($fp);
726
727 $line = mysql_real_escape_string(trim(strip_tags($line)));
728 $query = "insert into `pinglog` set `when`=NOW(), `email`='$myemail', `result`='$line'";
729 if(isset($_SESSION['profile']) && is_array($_SESSION['profile']) && isset($_SESSION['profile']['id'])) $query.=", `uid`='".intval($_SESSION['profile']['id'])."'";
730 mysql_query($query);
731
732 if(substr($line, 0, 3) != "250")
733 return $line;
734 else
735 return "OK";
736 }
737 }
738 }
739 $query = "insert into `pinglog` set `when`=NOW(), `uid`='".intval($_SESSION['profile']['id'])."',
740 `email`='$myemail', `result`='Failed to make a connection to the mail server'";
741 mysql_query($query);
742 return _("Failed to make a connection to the mail server");
743 }
744
745 function waitForResult($table, $certid, $id = 0, $show = 1)
746 {
747 $found = $trycount = 0;
748 if($certid<=0)
749 {
750 if($show) showheader(_("My CAcert.org Account!"));
751 echo _("ERROR: The new Certificate ID is wrong. Please contact support.\n");
752 if($show) showfooter();
753 if($show) exit;
754 return;
755 }
756 while($trycount++ <= 40)
757 {
758 if($table == "gpg")
759 $query = "select * from `$table` where `id`='".intval($certid)."' and `crt` != ''";
760 else
761 $query = "select * from `$table` where `id`='".intval($certid)."' and `crt_name` != ''";
762 $res = mysql_query($query);
763 if(mysql_num_rows($res) > 0)
764 {
765 $found = 1;
766 break;
767 }
768 sleep(3);
769 }
770
771 if(!$found)
772 {
773 if($show) showheader(_("My CAcert.org Account!"));
774 $query = "select * from `$table` where `id`='".intval($certid)."' ";
775 $res = mysql_query($query);
776 $body="";
777 $subject="";
778 if(mysql_num_rows($res) > 0)
779 {
780 printf('<p>' . _("Your certificate request is still queued and hasn't been processed yet. Please wait, and go to Certificates -> View to see it's status." . '</p>'));
781 $subject="[CAcert.org] Certificate TIMEOUT";
782 $body = "A certificate has timed out!\n\n";
783 }
784 else
785 {
786 printf('<p>' . _("Your certificate request has failed to be processed correctly, see %sthe WIKI page%s for reasons and solutions.") . " certid:$table:".intval($certid) . '</p>', "<a href='http://wiki.cacert.org/wiki/FAQ/CertificateRenewal'>", "</a>");
787 $subject="[CAcert.org] Certificate FAILURE";
788 $body = "A certificate has failed: $table $certid $id $show\n\n";
789 }
790
791 $body .= _("Best regards")."\n"._("CAcert.org Support!");
792
793 sendmail("sw-message@cacert.org", $subject, $body, "returns@cacert.org", "", "", "CAcert Support");
794
795 if($show) showfooter();
796 if($show) exit;
797 }
798 }
799
800
801
802 function generateTicket()
803 {
804 $query = "insert into tickets (timestamp) values (now()) ";
805 mysql_query($query);
806 $ticket = mysql_insert_id();
807 return $ticket;
808 }
809
810 function sanitizeHTML($input)
811 {
812 return htmlentities(strip_tags($input), ENT_QUOTES | ENT_SUBSTITUTE, 'ISO-8859-1', false);
813 //In case of problems, please use the following line again:
814 //return htmlentities(strip_tags(utf8_decode($input)), ENT_QUOTES);
815 //return htmlspecialchars(strip_tags($input));
816 }
817
818 function make_hash()
819 {
820 if(function_exists("dio_open"))
821 {
822 $rnd = dio_open("/dev/urandom",O_RDONLY);
823 $hash = md5(dio_read($rnd,64));
824 dio_close($rnd);
825 } else {
826 $rnd = fopen("/dev/urandom", "r");
827 $hash = md5(fgets($rnd, 64));
828 fclose($rnd);
829 }
830 return($hash);
831 }
832
833 function csrf_check($nam, $show=1)
834 {
835 if(!array_key_exists('csrf',$_REQUEST) || !array_key_exists('csrf_'.$nam,$_SESSION))
836 {
837 showheader(_("My CAcert.org Account!"));
838 echo _("CSRF Hash is missing. Please try again.")."\n";
839 showfooter();
840 exit();
841 }
842 if(strlen($_REQUEST['csrf'])!=32)
843 {
844 showheader(_("My CAcert.org Account!"));
845 echo _("CSRF Hash is wrong. Please try again.")."\n";
846 showfooter();
847 exit();
848 }
849 if(!array_key_exists($_REQUEST['csrf'],$_SESSION['csrf_'.$nam]))
850 {
851 showheader(_("My CAcert.org Account!"));
852 echo _("CSRF Hash is wrong. Please try again.")."\n";
853 showfooter();
854 exit();
855 }
856 }
857 function make_csrf($nam)
858 {
859 $hash=make_hash();
860 $_SESSION['csrf_'.$nam][$hash]=1;
861 return($hash);
862 }
863
864 function clean_csr($CSR)
865 {
866 $newcsr = str_replace("\r\n","\n",trim($CSR));
867 $newcsr = str_replace("\n\n","\n",$newcsr);
868 return(preg_replace("/[^A-Za-z0-9\n\r\-\:\=\+\/ ]/","",$newcsr));
869 }
870 function clean_gpgcsr($CSR)
871 {
872 return(preg_replace("/[^A-Za-z0-9\n\r\-\:\=\+\/ ]/","",trim($CSR)));
873 }
874
875 function sanitizeFilename($text)
876 {
877 $text=preg_replace("/[^\w-.@]/","",$text);
878 return($text);
879 }
880
881
882 // returns text message to be shown to the user given the result of is_no_assurer
883 function no_assurer_text($Status)
884 {
885 if ($Status == 0) {
886 $Result = _("You have passed the Assurer Challenge and collected at least 100 Assurance Points, you are an Assurer.");
887 } elseif ($Status == 3) {
888 $Result = _("You have passed the Assurer Challenge, but to become an Assurer you still have to reach 100 Assurance Points!");
889 } elseif ($Status == 5) {
890 $Result = _("You have at least 100 Assurance Points, if you want to become an assurer try the").' <a href="https://cats.cacert.org/">'._("Assurer Challenge").'</a>!';
891 } elseif ($Status == 7) {
892 $Result = _("To become an Assurer you have to collect 100 Assurance Points and pass the").' <a href="https://cats.cacert.org/">'._("Assurer Challenge").'</a>!';
893 } elseif ($Status & 8 > 0) {
894 $Result = _("Sorry, you are not allowed to be an Assurer. Please contact").' <a href="mailto:cacert-support@lists.cacert.org">cacert-support@lists.cacert.org</a>'._(" if you feel that this is not corect.");
895 } else {
896 $Result = _("You are not an Assurer, but the reason is not stored in the database. Please contact").' <a href="mailto:cacert-support@lists.cacert.org">cacert-support@lists.cacert.org</a>.';
897 }
898 return $Result;
899 }
900
901 function is_assurer($userID)
902 {
903 if (get_assurer_status($userID))
904 return 0;
905 else
906 return 1;
907 }
908
909 function get_assurer_reason($userID)
910 {
911 return no_assurer_text(get_assurer_status($userID));
912 }
913
914 function generatecertpath($type,$kind,$id)
915 {
916 $name="../$type/$kind-".intval($id).".$type";
917 $newlayout=1;
918 if($newlayout)
919 {
920 $name="../$type/$kind/".intval($id/1000)."/$kind-".intval($id).".$type";
921 if (!is_dir("../csr")) { mkdir("../csr",0777); }
922 if (!is_dir("../crt")) { mkdir("../crt",0777); }
923
924 if (!is_dir("../csr/$kind")) { mkdir("../csr/$kind",0777); }
925 if (!is_dir("../crt/$kind")) { mkdir("../crt/$kind",0777); }
926 if (!is_dir("../csr/$kind/".intval($id/1000))) { mkdir("../csr/$kind/".intval($id/1000)); }
927 if (!is_dir("../crt/$kind/".intval($id/1000))) { mkdir("../crt/$kind/".intval($id/1000)); }
928 }
929 return $name;
930 }
931
932 /**
933 * Run the sql query given in $sql.
934 * The resource returned by mysql_query is
935 * returned by this function.
936 *
937 * It should be safe to replace every mysql_query
938 * call by a mysql_extended_query call.
939 */
940 function mysql_timed_query($sql)
941 {
942 global $sql_data_log;
943 $query_start = microtime(true);
944 $res = mysql_query($sql);
945 $query_end = microtime(true);
946 $sql_data_log[] = array("sql" => $sql, "duration" => $query_end - $query_start);
947 return $res;
948 }
949
950 /**
951 * Returns the given ip address truncated to /16 (ipv4) or to /48 (ipv6)
952 */
953 function anonymizeIP($ip){
954 $bits = @inet_pton($ip);
955 if($bits === false) {
956 return false;
957 }
958
959 if(strlen($bits) == 4) {
960 $bits[2] = "\0";
961 $bits[3] = "\0";
962 $newIP = @inet_ntop($bits);
963 if($newIP !== false) {
964 $newIP .= "/16";
965 }
966 return $newIP;
967 } else if(strlen($bits) == 16) {
968 for($i=6;$i<16;$i++){
969 $bits[$i]="\0";
970 }
971 $newIP = @inet_ntop($bits);
972 if($newIP !== false) {
973 $newIP .= "/48";
974 }
975 return $newIP;
976 }
977 return false;
978 }