inc/security.php
010bf846
 <?php
c208bd90
 /*
 This file belongs to the Webinterface of schokokeks.org Hosting
 
f12aba6d
 Written 2008-2013 by schokokeks.org Hosting, namely
c208bd90
   Bernd Wurst <bernd@schokokeks.org>
   Hanno Böck <hanno@schokokeks.org>
 
 To the extent possible under law, the author(s) have dedicated all copyright and related and neighboring rights to this software to the public domain worldwide. This software is distributed without any warranty.
 
 You should have received a copy of the CC0 Public Domain Dedication along with this software. If not, see 
 http://creativecommons.org/publicdomain/zero/1.0/
 
 Nevertheless, in case you use a significant part of this code, we ask (but not require, see the license) that you keep the authors' names in place and return your changes to the public. We would be especially happy if you tell us what you're going to do with this code.
 */
010bf846
 
33986238
 require_once('inc/error.php');
 
010bf846
 
a78147ca
 function strong_password($password)
 {
4c7e58dd
   if ($password == '' || strlen($password) < 4) {
     DEBUG("Passwort zu kurz!");
     return "Passwort ist zu kurz!";
   }
 
17c66ad0
   if (! function_exists("crack_opendict"))
   {
     DEBUG("cracklib not available!");
     return true;
   }
75feee8b
   if (config('use_cracklib') === NULL or config('use_cracklib') === false) {
f550c0ef
     DEBUG('Cracklib deaktiviert');
     return true;
   }
75feee8b
   DEBUG("Öffne Wörterbuch: ".config('cracklib_dict'));
d96a86aa
   if (! ($dict = crack_opendict(config('cracklib_dict'))))
a78147ca
   {
3048f62f
     logger(LOG_ERR, "inc/security", "cracklib", "could not open cracklib-dictionary »".config('cracklib_dict')."«");
9cbd3c51
     #system_failure("Kann Crack-Lib-Wörterbuch nicht öffnen: ".config('cracklib_dict'));
     DEBUG('cracklib tut nicht, dann wird das PW akzeptiert');
     warning('Das Passwort konnte aufgrund eines internen Fehlers nicht auf die Passwortstärke geprüft werden.');
     return true;
a78147ca
   }
   // Führe eine Überprüfung des Passworts durch
   $check = crack_check($dict, $password);
 
   $message = crack_getlastmessage();
   crack_closedict($dict);
 
   if ($check === True)
   {
     DEBUG("Passwort ok");
     return true;
   }
   else
   {
     DEBUG("Passwort nicht ok: {$message}");
     return $message;
   }
 }
 
 
010bf846
 function filter_input_general( $input )
 {
33986238
   return htmlspecialchars(iconv('UTF-8', 'UTF-8', $input), ENT_QUOTES, 'UTF-8');
 }
 
 
 function verify_input_general( $input )
 {
8b3e6a38
   if (filter_input_general($input) != $input) {
33986238
     system_failure("Ihre Daten enthielten ungültige Zeichen!");
3048f62f
     logger(LOG_WARNING, 'inc/security', 'verify_input_general', 'Ungültige Daten: '.$input);
8b3e6a38
   }
010bf846
 }
 
 
 function filter_input_username( $input )
 {
77b5d4c4
   return preg_replace("/[^[:alnum:]\_\.\+\-]/", "", $input );
391c907d
 }
 
 function verify_input_username( $input )
 {
8b3e6a38
   if (filter_input_username( $input ) != $input) {
3048f62f
     logger(LOG_WARNING, 'inc/security', 'verify_input_username', 'Ungültige Daten: '.$input);
3e33855c
     system_failure("Ihre Daten enthielten ungültige Zeichen!");
8b3e6a38
   }
010bf846
 }
 
33986238
 
 
c9a403b2
 function filter_input_hostname( $input, $wildcard=false )
07263d42
 {
c9a403b2
   // FIXME: Eine "filter"-Funktion sollte keinen system_failure verursachen sondern einfach einen bereinigten String liefern.
   
733161de
   DEBUG('filter_input_hostname("'.$input.'", $wildcard='.$wildcard.')');
33986238
   $input = str_replace(array('Ä', 'Ö', 'Ü'), array('ä', 'ö', 'ü'), strtolower($input));
bd9c37c5
   $input = rtrim($input, "\t\n\r\x00 .");
   $input = ltrim($input, "\t\n\r\x00 .");
77b5d4c4
   if (preg_replace("/[^[:alnum:]äöü*\.\-]/", "", $input ) != $input)
33986238
     system_failure("Ihre Daten enthielten ungültige Zeichen!");
20664c3d
   if (preg_match("/^.+\*/", $input ))
     system_failure("Ihre Daten enthielten ungültige Zeichen (Wildcard-Stern muss ganz vorne stehen)!");
   if (! $wildcard && preg_replace("/^\*/", "", $input ) != $input)
c9a403b2
     system_failure("Ihre Daten enthielten ungültige Zeichen (Keine Wildcards erlaubt)!");
b0d6649b
   if (strstr($input, '..'))
     system_failure("Ungültiger Hostname");
33986238
   return $input;
07263d42
 }
 
c9a403b2
 function verify_input_hostname( $input, $wildcard=false )
3e33855c
 {
c9a403b2
   if (filter_input_hostname( $input, $wildcard ) != $input) {
3048f62f
     logger(LOG_WARNING, 'inc/security', 'verify_input_hostname', 'Ungültige Daten: '.$input);
3e33855c
     system_failure("Ihre Daten enthielten ungültige Zeichen!");
   }
 }
 
 
 function verify_input_ipv4( $input )
 {
   if (! preg_match("/^([1-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])(\.([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])){3}$/", $input))
     system_failure('Keine IP-Adresse');
 }
 
 
 function verify_input_ipv6( $input )
 {
   // ripped from Perl module Net-IPv6Addr v0.2
   if (! preg_match("/^(([0-9a-f]{1,4}:){7}[0-9a-f]{1,4}|[0-9a-f]{0,4}::|:(?::[a-f0-9]{1,4}){1,6}|(?:[a-f0-9]{1,4}:){1,6}:|(?:[a-f0-9]{1,4}:)(?::[a-f0-9]{1,4}){1,6}|(?:[a-f0-9]{1,4}:){2}(?::[a-f0-9]{1,4}){1,5}|(?:[a-f0-9]{1,4}:){3}(?::[a-f0-9]{1,4}){1,4}|(?:[a-f0-9]{1,4}:){4}(?::[a-f0-9]{1,4}){1,3}|(?:[a-f0-9]{1,4}:){5}(?::[a-f0-9]{1,4}){1,2}|(?:[a-f0-9]{1,4}:){6}(?::[a-f0-9]{1,4}))$/i", $input))
     system_failure("Ungültige IPv6-Adresse");
 }
33986238
 
 
0dae1273
 function filter_quotes( $input )
 {
77b5d4c4
   return preg_replace('/["\'`]/', '', $input );
0dae1273
 }
 
33986238
 
 
19a2c966
 function filter_shell( $input )
 {
77b5d4c4
   return preg_replace('/[^-[:alnum:]\_\.\+ßäöüÄÖÜ/%§=]/', '', $input );
33986238
 }
 
 function verify_shell( $input )
 {
   if (filter_shell($input) != $input)
     system_failure("Ihre Daten enthielten ungültige Zeichen!");
19a2c966
 }
010bf846
 
33986238
 
 
af8c8976
 function check_path( $input )
 {
4278a08c
   DEBUG("checking {$input} for valid path name");
af8c8976
   if ($input != filter_input_general($input))
4278a08c
   {
3048f62f
     logger(LOG_WARNING, 'inc/security', 'check_path', 'HTML-Krams im Pfad: '.$input);
4278a08c
     DEBUG("HTML-Krams im Pfad");
af8c8976
     return False;
4278a08c
   }
af8c8976
   $components = explode("/", $input);
   foreach ($components AS $item)
   {
     if ($item == '..')
     {
3048f62f
       logger(LOG_WARNING, 'inc/security', 'check_path', '»..« im Pfad: '.$input);
07263d42
       DEBUG("»..« im Pfad");
af8c8976
       return False;
     }
   }
3d075722
   return (preg_match('/^[ A-Za-z0-9.@\/_-]*$/',$input) == 1);
af8c8976
 }
 
 
d5f2f3f4
 function in_homedir($path)
 {
   DEBUG("Prüfe »{$path}«");
   if (! check_path($path))
   {
     DEBUG('Kein Pfad');
     return False;
   }
   if (! isset($_SESSION['userinfo']['homedir']))
   {
     DEBUG("Kann homedir nicht ermitteln");
     return False;
   }
   return strncmp($_SESSION['userinfo']['homedir'], $path, count($_SESSION['userinfo']['homedir'])) == 0;
 }
 
92f2aa62
 function check_date( $input )
 {
   return (bool) preg_match("/[0-9]{4}-(0?[1-9]|11|12)-([012]?[0-9]|30|31)/", $input);
 }
 
d5f2f3f4
 
0d1b7607
 function check_emailaddr( $input )
 {
e56dbcb2
   return (bool) filter_var($input, FILTER_VALIDATE_EMAIL) == $input;
dd4ea394
 }
 
 function check_domain( $input )
 {
   return (bool) preg_match("/[a-z0-9\.\-]+\.[a-z]{2,4}$/i", $input );
0d1b7607
 }