static function FindFiles($directory,$options = array()){
		$options += array(
			"pattern" => null, // '/^.*\.(log|err)$/'
			"invert_pattern" => null, // '/^\./' - do not find files starting with dot
			"min_mtime" => null, // time() - 2 * 60 * 60
			"max_mtime" => null, // time() - 60 * 60

			"maxdepth" => null // TODO: add maxdepth like in system command find
		);

		if(!preg_match('/\/$/',$directory)){
			$directory = "$directory/"; // "./tmp" -> "./tmp/"
		}

		$pattern = $options["pattern"];
		$invert_pattern = $options["invert_pattern"];
		$min_mtime = $options["min_mtime"];
		$max_mtime = $options["max_mtime"];
		$maxdepth = $options["maxdepth"];

		if(isset($maxdepth) && $maxdepth<=0){
			return array();
		}

		// getting file list
		$files = array();
		$dir = opendir($directory);
		while(is_string($item = readdir($dir))){
			if($item=="." || $item==".."){ continue; }
			$files[] = $item;
		}
		closedir($dir);
		asort($files);

		$out = array();

		foreach($files as $file){
			$_f = $file; // "application.log"
			$file = "$directory$file"; // "./log/application.log"

			if(is_dir($file) && !is_link($file)){
				$_options = $options;
				if(isset($_options["maxdepth"])){ $_options["maxdepth"]--; }
				foreach(self::FindFiles($file,$_options) as $_file){
					$out[] = $_file;
				}
			}

			if(!is_file($file)){
				continue;
			}
		
			if($pattern && !preg_match($pattern,$_f)){
				continue;
			}

			if($invert_pattern && preg_match($invert_pattern,$_f)){
				continue;
			}

			if(isset($min_mtime) && filemtime($file)<$min_mtime){
				continue;
			}

			if(isset($max_mtime) && filemtime($file)>$max_mtime){
				continue;
			}

			$out[] = $file;
		}

		return $out;
	}