Projet

Général

Profil

Paste
Statistiques
| Branche: | Révision:

ryxeo-glpi-git / inc / common.function.php @ b67d8923

Historique | Voir | Annoter | Télécharger (46,9 ko)

1
<?php
2
/*
3
 * @version $Id: common.function.php 7882 2009-01-23 18:24:05Z moyo $
4
 -------------------------------------------------------------------------
5
 GLPI - Gestionnaire Libre de Parc Informatique
6
 Copyright (C) 2003-2009 by the INDEPNET Development Team.
7

8
 http://indepnet.net/   http://glpi-project.org
9
 -------------------------------------------------------------------------
10

11
 LICENSE
12

13
 This file is part of GLPI.
14

15
 GLPI is free software; you can redistribute it and/or modify
16
 it under the terms of the GNU General Public License as published by
17
 the Free Software Foundation; either version 2 of the License, or
18
 (at your option) any later version.
19

20
 GLPI is distributed in the hope that it will be useful,
21
 but WITHOUT ANY WARRANTY; without even the implied warranty of
22
 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23
 GNU General Public License for more details.
24

25
 You should have received a copy of the GNU General Public License
26
 along with GLPI; if not, write to the Free Software
27
 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
28
 --------------------------------------------------------------------------
29
 */
30

    
31
// ----------------------------------------------------------------------
32
// Original Author of file:
33
// Purpose of file:
34
// ----------------------------------------------------------------------
35

    
36

    
37
if (!defined('GLPI_ROOT')){
38
        die("Sorry. You can't access directly to this file");
39
        }
40

    
41
//******************************************************************************************************
42
//******************************************************************************************************
43
//********************************  Fonctions diverses ************************************
44
//******************************************************************************************************
45
//******************************************************************************************************
46

    
47
        /**
48
        * Set the directory where are store the session file
49
        *
50
        **/
51
        function setGlpiSessionPath(){
52
                if (ini_get("session.save_handler")=="files") {
53
                        session_save_path(GLPI_SESSION_DIR);
54
               }
55
        }
56
        /**
57
        * Start the GLPI php session 
58
        *
59
        **/
60
        function startGlpiSession(){
61
                if(!session_id()){@session_start();}
62
                // Define current time for sync of action timing
63
                $_SESSION["glpi_currenttime"]=date("Y-m-d H:i:s");        
64
        }
65

    
66
        /**
67
        * Is GLPI used in mutli-entities mode ?
68
        *@return boolean
69
        * 
70
        **/
71
        function isMultiEntitiesMode(){
72
                if (!isset($_SESSION['glpi_multientitiesmode'])){
73
                        if (countElementsInTable("glpi_entities")>0){
74
                                $_SESSION['glpi_multientitiesmode']=1;
75
                        } else {
76
                                $_SESSION['glpi_multientitiesmode']=0;
77
                        }
78
                }
79
                return $_SESSION['glpi_multientitiesmode'];
80
        }
81
        /**
82
        * Is the user have right to see all entities ?
83
        *@return boolean
84
        * 
85
        **/
86
        function isViewAllEntities(){
87
                return ((countElementsInTable("glpi_entities")+1)==count($_SESSION["glpiactiveentities"]));
88
        }
89
        /**
90
        * Log a message in log file
91
        *@param $name string: name of the log file
92
        *@param $text string: text to log 
93
        *@param $force boolean: force log in file not seeing use_errorlog config
94
        * 
95
        **/
96
        function logInFile($name,$text,$force=false){
97
                global $CFG_GLPI;
98
                if ($CFG_GLPI["use_errorlog"]||$force){ 
99
                        error_log(convDateTime(date("Y-m-d H:i:s"))."\n".$text,3,GLPI_LOG_DIR."/".$name.".log");
100
                }
101
        }
102
        
103
        /**
104
        * Specific error handler
105
        *@param $errno integer: level of the error raised.
106
        *@param $errmsg string: error message.
107
        *@param $filename string: filename that the error was raised in.
108
        *@param $linenum integer: line number the error was raised at. 
109
        *@param $vars array: that points to the active symbol table at the point the error occurred.
110
        *
111
        **/
112
        function userErrorHandler($errno, $errmsg, $filename, $linenum, $vars){
113
                global $CFG_GLPI;
114
                // Date et heure de l'erreur
115
                //$dt = date("Y-m-d H:i:s (T)");
116
                $errortype = array (
117
                        E_ERROR              => 'Error',
118
                        E_WARNING            => 'Warning',
119
                        E_PARSE              => 'Parsing Error',
120
                        E_NOTICE             => 'Notice',
121
                        E_CORE_ERROR         => 'Core Error',
122
                        E_CORE_WARNING       => 'Core Warning',
123
                        E_COMPILE_ERROR      => 'Compile Error',
124
                        E_COMPILE_WARNING    => 'Compile Warning',
125
                        E_USER_ERROR         => 'User Error',
126
                        E_USER_WARNING       => 'User Warning',
127
                        E_USER_NOTICE        => 'User Notice',
128
                        // Need php 5.0
129
                        2048         /*E_STRICT*/             => 'Runtime Notice',
130
                        // Need php 5.2.0
131
                        4096 /*E_RECOVERABLE_ERROR*/  => 'Catchable Fatal Error',
132
                        // Need php 5.3.0
133
                        8192 /* E_DEPRECATED */ => 'Deprecated function',
134
                        16384 /* E_USER_DEPRECATED */ => 'User deprecated function'
135
                        );                        
136
                // Les niveaux qui seront enregistrés
137
                $user_errors = array(E_USER_ERROR, E_USER_WARNING, E_USER_NOTICE);
138

    
139
                // In PHP 5.3 a lot of fonction are deprecated. Will be fixed in 0.72 
140
                if ($errno==8192) return;                        
141
                        
142
                $err = $errortype[$errno] . "($errno): $errmsg\n";
143
                if (in_array($errno, $user_errors)) {
144
                        $err .= "Variables:".wddx_serialize_value($vars,"Variables")."\n";
145
                }
146
                if (function_exists("debug_backtrace")) {
147
                        $err .= "Backtrace :\n";
148
                        $traces=debug_backtrace();
149
                        foreach ($traces as $trace) {
150
                                if (isset($trace["file"]) && isset($trace["line"])) {
151
                                        $err .= $trace["file"] . ":" . $trace["line"] . "\t\t"
152
                                                . (isset($trace["class"]) ? $trace["class"] : "")
153
                                                . (isset($trace["type"]) ? $trace["type"] : "")
154
                                                . (isset($trace["function"]) ? $trace["function"]."()" : "")
155
                                                . "\n";
156
                                }
157
                        }
158
                } else {
159
                        $error .= "Script: $filename, Line: $linenum\n" ; 
160
                }
161
                
162
                // sauvegarde de l'erreur, et mail si c'est critique
163
                logInFile("php-errors",$err."\n");
164
                
165
                if (!isCommandLine()){
166
                        echo '<div style="position:fload-left; background-color:red; z-index:10000"><strong>PHP ERROR: </strong>';
167
                        echo $errmsg." in ".$filename." at line ".$linenum;
168
                        echo '</div>';
169
                } else {
170
                        echo "PHP ERROR: ".$errmsg." in ".$filename." at line ".$linenum."\n";
171
                }
172
        }
173
        /**
174
        * Is the script launch in Command line ?
175
        *@return boolean
176
        *
177
        **/
178
        function isCommandLine(){
179
                return (!isset($_SERVER["SERVER_NAME"]));
180
        }
181

    
182
        /**
183
        * substr function for utf8 string
184
        *@param $str string: string
185
        *@param $start integer: start of the result substring
186
        *
187
        *@return substring
188
        **/
189
        function utf8_substr($str,$start){
190
                   preg_match_all("/./su", $str, $ar);
191

    
192
                   if(func_num_args() >= 3) {
193
                       $end = func_get_arg(2);
194
                       return join("",array_slice($ar[0],$start,$end));
195
                   } else {
196
                       return join("",array_slice($ar[0],$start));
197
                   }
198
        }
199
        /**
200
        * strlen function for utf8 string
201
        * @param $str string: string 
202
        * @return length of the string
203
        **/
204
        function utf8_strlen($str){
205
            $i = 0;
206
            $count = 0;
207
            $len = strlen ($str);
208
            while ($i < $len){
209
                    $chr = ord ($str[$i]);
210
                    $count++;
211
                    $i++;
212
                    if ($i >= $len){
213
                        break;
214
                    }
215
                    if ($chr & 0x80){
216
                        $chr <<= 1;
217
                        while ($chr & 0x80){
218
                                $i++;
219
                                $chr <<= 1;
220
                        }
221
                    }
222
            }
223
            return $count;
224
        }
225
        /**
226
        * html_entity_decode function for utf8 string
227
        * @param $string string: string
228
        *
229
        * @return converted string
230
        **/
231
        function utf8_html_entity_decode($string){
232
                static $trans_tbl;
233
        
234
                // replace numeric entities
235
                $string = preg_replace('~&#x([0-9a-f]+);~ei', 'code2utf(hexdec("\\1"))', $string);
236
                $string = preg_replace('~&#([0-9]+);~e', 'code2utf(\\1)', $string);
237
        
238
                // replace literal entities
239
                if (!isset($trans_tbl)){
240
                        $trans_tbl = array();
241
        
242
                        foreach (get_html_translation_table(HTML_ENTITIES) as $val=>$key){
243
                        $trans_tbl[$key] = utf8_encode($val);
244
                        }
245
                }   
246
                return strtr($string, $trans_tbl);
247
        }
248

    
249
        /** Returns the utf string corresponding to the unicode value (from php.net, courtesy - romans@void.lv)
250
        * @param $num integer: character code
251
        */
252
        function code2utf($num){
253
            if ($num < 128) return chr($num);
254
            if ($num < 2048) return chr(($num >> 6) + 192) . chr(($num & 63) + 128);
255
            if ($num < 65536) return chr(($num >> 12) + 224) . chr((($num >> 6) & 63) + 128) . chr(($num & 63) + 128);
256
            if ($num < 2097152) return chr(($num >> 18) + 240) . chr((($num >> 12) & 63) + 128) . chr((($num >> 6) & 63) + 128) . chr(($num & 63) + 128);
257
            return '';
258
        }
259

    
260
        /**
261
         * Clean log cron function
262
         *
263
         **/
264
        function cron_logs(){
265
                global $CFG_GLPI,$DB;
266

    
267
                // Expire Event Log
268
                if ($CFG_GLPI["expire_events"] > 0) {
269
                        $secs = $CFG_GLPI["expire_events"] * DAY_TIMESTAMP;
270
                        $query_exp = "DELETE FROM glpi_event_log WHERE UNIX_TIMESTAMP(date) < UNIX_TIMESTAMP()-$secs";
271
                        $DB->query($query_exp);
272
                        logInFile("cron","Cleaning log events passed from more than ".$CFG_GLPI["expire_events"]." days\n");
273
                }
274
        }
275

    
276
        /**
277
         * Clean log cron function
278
         *
279
         **/
280
        function cron_optimize(){
281
                global $CFG_GLPI,$DB;
282

    
283
                logInFile("cron","Start optimize tables\n");
284
                optimize_tables();
285
                logInFile("cron","Optimize tables done\n");
286
        }
287

    
288
        /**
289
         * Clean cache cron function
290
         *
291
         **/
292
        function cron_cache(){
293
                global $CFG_GLPI;
294
                $max_recursion=5;
295
                $lifetime=DEFAULT_CACHE_LIFETIME;
296
                while ($max_recursion>0&&(($size=filesizeDirectory(GLPI_CACHE_DIR))>MAX_CACHE_SIZE)){
297
                        $cache_options = array(
298
                                'cacheDir' => GLPI_CACHE_DIR,
299
                                'lifeTime' => $lifetime,
300
                                'automaticSerialization' => true,
301
                                'caching' => $CFG_GLPI["use_cache"],
302
                                'hashedDirectoryLevel' => 2,
303
                                'fileLocking' => CACHE_FILELOCKINGCONTROL,
304
                                'writeControl' => CACHE_WRITECONTROL,
305
                                'readControl' => CACHE_READCONTROL,
306
                        );
307
                        $cache = new Cache_Lite($cache_options);
308
                        $cache->clean(false,"old");
309

    
310
                        logInFile("cron","Clean cache created since more than $lifetime seconds\n");
311
                        $lifetime/=2;
312
                        $max_recursion--;
313
                }
314
                if ($max_recursion>0){
315
                        return 1;
316
                } else {
317
                        return -1;
318
                }
319
        }
320

    
321
        /**
322
         * Garbage collector for expired file session
323
         *
324
         **/
325
        function cron_session(){
326
                global $CFG_GLPI;
327
                // max time to keep the file session
328
                $maxlifetime = session_cache_expire();
329
                $do=false;                        
330
                foreach (glob(GLPI_SESSION_DIR."/sess_*") as $filename) {
331
                        if (filemtime($filename) + $maxlifetime < time()) {
332
                                // Delete session file if not delete before
333
                                @unlink($filename);
334
                                $do=true;
335
                        }
336
                }
337
                if ($do){
338
                        logInFile("cron","Clean session files created since more than $maxlifetime seconds\n");
339
                }
340
                return true;
341
        }
342

    
343
/**
344
 * Get the filesize of a complete directory (from php.net)
345
 *
346
 * @param $path string: directory or file to get size
347
 * @return size of the $path
348
 **/
349
function filesizeDirectory($path){
350
        if(!is_dir($path)){
351
                return filesize($path);
352
        }
353
           if ($handle = opendir($path)) {
354
               $size = 0;
355
               while (false !== ($file = readdir($handle))) {
356
                    if($file!='.' && $file!='..'){
357
                        $size += filesize($path.'/'.$file);
358
                    $size += filesizeDirectory($path.'/'.$file);
359
                }
360
            }
361
            closedir($handle);
362
               return $size;
363
           }
364
}
365

    
366

    
367
/**
368
 * Clean cache function
369
 *
370
 * @param $group string: group to clean (if not set clean all the cache)
371
 * @return nothing
372
 **/
373
function cleanCache($group=""){
374

    
375
        include_once (GLPI_CACHE_LITE_DIR."/Lite.php");
376

    
377
        $cache_options = array(
378
                'cacheDir' => GLPI_CACHE_DIR,
379
                'lifeTime' => 0,
380
                'hashedDirectoryLevel' => 2,
381
                'fileLocking' => CACHE_FILELOCKINGCONTROL,
382
                'writeControl' => CACHE_WRITECONTROL,
383
                'readControl' => CACHE_READCONTROL,
384
                );
385
        $CACHE = new Cache_Lite($cache_options);
386
        if (empty($group)){
387
                $CACHE->clean();
388
        } else {
389
                $CACHE->clean($group,"ingroup");
390
        }
391

    
392
}
393

    
394
/**
395
 * Clean cache function for relations using a specific table
396
 *
397
 * @param $table string: table used. Need to clean all cache using this table
398
 * @return nothing
399
 **/
400
function cleanRelationCache($table){
401
        global $LINK_ID_TABLE,$CFG_GLPI;
402
        if ($CFG_GLPI["use_cache"]){
403
                $RELATION=getDbRelations();
404
                if (isset($RELATION[$table])){
405
                        foreach ($RELATION[$table] as $tablename => $field){
406
                                if ($key=array_search($tablename,$LINK_ID_TABLE)){
407
                                        cleanCache("GLPI_$key");
408
                                }
409
                        }
410
                }
411
        }
412
}
413

    
414
/**
415
 * Clean all dict cache
416
 *
417
 * @param $group string: cache group
418
 * @param $item  string: remove cache for item
419
 * @return nothing
420
 **/
421
function cleanAllItemCache($item,$group){
422
        global $CFG_GLPI;
423
        if ($CFG_GLPI["use_cache"]){
424
                foreach ($CFG_GLPI["languages"] as $key => $val){
425
                        // clean main sheet
426
                        $CFG_GLPI["cache"]->remove($item."_".$key,$group,true);
427
                }
428
        }
429
}
430

    
431

    
432
/**
433
 * Get the SEARCH_OPTION array using cache
434
 *
435
 * @return the SEARCH_OPTION array
436
 **/
437
function getSearchOptions(){
438
        global $LANG,$CFG_GLPI,$PLUGIN_HOOKS;
439
        $options = array(
440
                'cacheDir' => GLPI_CACHE_DIR,
441
                'lifeTime' => DEFAULT_CACHE_LIFETIME,
442
                'automaticSerialization' => true,
443
                'caching' => $CFG_GLPI["use_cache"],
444
                'hashedDirectoryLevel' => 2,
445
                'masterFile' => GLPI_ROOT . "/inc/search.constant.php",
446
                'fileLocking' => CACHE_FILELOCKINGCONTROL,
447
                'writeControl' => CACHE_WRITECONTROL,
448
                'readControl' => CACHE_READCONTROL,
449
        );
450
        $cache = new Cache_Lite_File($options);
451

    
452
        // Set a id for this cache : $file
453
        if (!($SEARCH_OPTION = $cache->get("OPTIONS","GLPI_SEARCH_".$_SESSION["glpilanguage"]))) {
454
                // Cache miss !
455
                // Put in $SEARCH_OPTION datas to put in cache
456
                include (GLPI_ROOT . "/inc/search.constant.php");
457
                $cache->save($SEARCH_OPTION,"OPTIONS","GLPI_SEARCH_".$_SESSION["glpilanguage"]);
458
        }
459
        
460
        $plugsearch=getPluginSearchOption();
461
        if (count($plugsearch)){
462
                foreach ($plugsearch as $key => $val){
463
                        if (!isset($SEARCH_OPTION[$key])){
464
                                $SEARCH_OPTION[$key]=array();
465
                        } else {
466
                                $SEARCH_OPTION[$key]+=array('plugins'=>$LANG["common"][29]);
467
                        }
468

    
469
                        $SEARCH_OPTION[$key]+=$val;
470
                }
471
        }
472

    
473
        return $SEARCH_OPTION;
474
}
475

    
476
/**
477
 * Get the $RELATION array using cache. It's defined all relations between tables in the DB.
478
 *
479
 * @return the $RELATION array
480
 **/
481
function getDbRelations(){
482
        global $CFG_GLPI;
483
        $options = array(
484
                'cacheDir' => GLPI_CACHE_DIR,
485
                'lifeTime' => DEFAULT_CACHE_LIFETIME,
486
                'automaticSerialization' => true,
487
                'caching' => $CFG_GLPI["use_cache"],
488
                'hashedDirectoryLevel' => 2,
489
                'masterFile' => GLPI_ROOT . "/inc/relation.constant.php",
490
                'fileLocking' => CACHE_FILELOCKINGCONTROL,
491
                'writeControl' => CACHE_WRITECONTROL,
492
                'readControl' => CACHE_READCONTROL,
493
        );
494
        $cache = new Cache_Lite_File($options);
495

    
496
        // Set a id for this cache : $file
497
        if (!($RELATION = $cache->get("OPTIONS","GLPI_RELATION"))) {
498
                // Cache miss !
499
                // Put in $SEARCH_OPTION datas to put in cache
500
                include (GLPI_ROOT . "/inc/relation.constant.php");
501
                $cache->save($RELATION,"OPTIONS","GLPI_RELATION");
502
        }
503

    
504
        // Add plugins relations
505
        $plug_rel=getPluginsDatabaseRelations();
506
        if (count($plug_rel)>0){
507
                $RELATION=array_merge_recursive($RELATION,$plug_rel);
508
        }
509
        
510
        return $RELATION;
511
}
512

    
513
/**
514
 * Check Write Access to a directory
515
 *
516
 * @param $dir string: directory to check
517
 * @return 2 : creation error 1 : delete error 0: OK
518
 **/
519
function testWriteAccessToDirectory($dir){
520

    
521
        $rand=rand();
522
        // Check directory creation which can be denied by SElinux
523
        $sdir = sprintf("%s/test_glpi_%08x", $dir, $rand);
524
        if (!mkdir($sdir)) {
525
                return 4;
526
        }
527
        else if (!rmdir($sdir)) {
528
                return 3;
529
        }
530

    
531
        // Check file creation
532
        $path = sprintf("%s/test_glpi_%08x.txt", $dir, $rand);
533
        $fp = fopen($path,'w');
534

    
535
        if (empty($fp)) {
536
                return 2;
537
        }
538
        else {
539
                $fw = fwrite($fp,"This file was created for testing reasons. ");
540
                fclose($fp);
541
                $delete = unlink($path);
542
                if (!$delete) {
543
                        return 1;
544
                }
545
        }
546
        return 0;
547
}
548

    
549
/**
550
* Common Checks needed to use GLPI
551
*
552
* @return 2 : creation error 1 : delete error 0: OK
553
**/
554
function commonCheckForUseGLPI(){
555
        global $LANG;
556

    
557
        // memory test
558
        echo "<tr class='tab_bg_1'><td><b>".$LANG["install"][86]."</b></td>";
559

    
560
        $mem=ini_get("memory_limit");
561

    
562
        // Cette bidouille me plait pas
563
        //if(empty($mem)) {$mem=get_cfg_var("memory_limit");}  // Sous Win l'ini_get ne retourne rien.....
564

    
565
        preg_match("/([0-9]+)([KMG]*)/",$mem,$matches);
566

    
567
        // no K M or G 
568
        if (!isset($matches[2])){
569
                $mem=$matches[1];
570
        } else {
571
                $mem=$matches[1];
572
                switch ($matches[2]){
573
                        case "G" : $mem*=1024;
574
                        case "M" : $mem*=1024;
575
                        case "K" : $mem*=1024;
576
                        break;
577
                }
578
        }
579

    
580
        if( $mem == "" ){          // memory_limit non compilé -> no memory limit
581
                echo "<td>".$LANG["install"][95]." - ".$LANG["install"][89]."</td></tr>";
582
        }
583
        else if( $mem == "-1" ){   // memory_limit compilé mais illimité
584
                echo "<td>".$LANG["install"][96]." - ".$LANG["install"][89]."</td></tr>";
585
        }
586
        else{        
587
                if ($mem<32*1024*1024){ // memoire insuffisante
588
                        echo "<td  class='red'><b>".$LANG["install"][87]." $mem octets</b><br>".$LANG["install"][88]."<br>".$LANG["install"][90]."</td></tr>";
589
                }
590
                else{ // on a sufisament de mémoire on passe à la suite
591
                        echo "<td>".$LANG["install"][91]." - ".$LANG["install"][89]."</td></tr>";
592
                }
593
        }
594
        return checkWriteAccessToDirs();
595
}
596

    
597
/**
598
* Check Write Access to needed directories
599
*
600
* @return 2 : creation error 1 : delete error 0: OK
601
**/
602
function checkWriteAccessToDirs(){
603
        global $LANG;
604
        $dir_to_check=array(
605
                GLPI_DUMP_DIR => $LANG["install"][16],
606
                GLPI_DOC_DIR => $LANG["install"][21],
607
                GLPI_CONFIG_DIR => $LANG["install"][23],
608
                GLPI_SESSION_DIR => $LANG["install"][50],
609
                GLPI_CRON_DIR => $LANG["install"][52],
610
                GLPI_CACHE_DIR => $LANG["install"][99],
611
                GLPI_LOG_DIR => $LANG["install"][53]
612
        );
613
        $error=0;        
614
        foreach ($dir_to_check as $dir => $message){
615
                echo "<tr class='tab_bg_1'><td><strong>".$message."</strong></td>";
616
                $tmperror=testWriteAccessToDirectory($dir);
617
        
618
                switch($tmperror){
619
                        // Error on creation
620
                        case 4 :
621
                                echo "<td><p class='red'>".$LANG["install"][100]."</p> ".$LANG["install"][97]."'".$dir."'. ".$LANG["install"][98]."</td></tr>";
622
                                $error=2;
623
                                break;
624
                        case 3 :
625
                                echo "<td><p class='red'>".$LANG["install"][101]."</p> ".$LANG["install"][97]."'".$dir."'. ".$LANG["install"][98]."</td></tr>";
626
                                $error=1;
627
                                break;
628
                        // Error on creation
629
                        case 2 :
630
                                echo "<td><p class='red'>".$LANG["install"][17]."</p> ".$LANG["install"][97]."'".$dir."'. ".$LANG["install"][98]."</td></tr>";
631
                                $error=2;
632
                                break;
633
                        case 1 :
634
                                echo "<td><p class='red'>".$LANG["install"][19]."</p> ".$LANG["install"][97]."'".$dir."'. ".$LANG["install"][98]."</td></tr>";
635
                                $error=1;
636
                                break;
637
                        default :
638
                                echo "<td>".$LANG["install"][20]."</td></tr>";
639
                                break;
640
                }
641
        }
642
        return $error;
643
}
644

    
645
/**
646
 * Strip slash  for variable & array
647
 *
648
 * @param $value array or string: item to stripslashes (array or string)
649
 * @return stripslashes item
650
 */
651
function stripslashes_deep($value) {
652
        $value = is_array($value) ?
653
                array_map('stripslashes_deep', $value) :
654
                        (is_null($value) ? NULL : stripslashes($value));
655

    
656
        return $value;
657
}
658

    
659
/**
660
 *  Add slash for variable & array 
661
 *
662
 * @param $value array or string: value to add slashes (array or string)
663
 * @return addslashes value
664
 */
665
function addslashes_deep($value) {
666
        $value = is_array($value) ?
667
                array_map('addslashes_deep', $value) :
668
                        (is_null($value) ? NULL : addslashes($value));
669
        return $value;
670
}
671

    
672
/**
673
 * Prevent from XSS
674
 * Clean code 
675
 *
676
 * @param $value array or string: item to prevent (array or string)
677
 * @return clean item
678
 *
679
 * @see unclean_cross_side_scripting_deep*
680
 */
681
function clean_cross_side_scripting_deep($value) {
682
        $in=array("<",">");
683
        $out=array("&lt;","&gt;");
684
        $value = is_array($value) ?
685
                array_map('clean_cross_side_scripting_deep', $value) :
686
                        (is_null($value) ? NULL : str_replace($in,$out,$value));
687
        return $value;
688
}
689
/**
690
 *  Invert fonction from clean_cross_side_scripting_deep
691
 *
692
 * @param $value array or string: item to unclean from clean_cross_side_scripting_deep
693
 * @return unclean item
694
 * @see clean_cross_side_scripting_deep
695
 */
696
function unclean_cross_side_scripting_deep($value) {
697
        $in=array("<",">");
698
        $out=array("&lt;","&gt;");
699
        $value = is_array($value) ?
700
                array_map('clean_cross_side_scripting_deep', $value) :
701
                        (is_null($value) ? NULL : str_replace($out,$in,$value));
702
        return $value;
703
}
704
/**
705
 *  Utf8 decode for variable & array
706
 *
707
 * @param $value array or string: item to utf8_decode (array or string)
708
 * @return decoded item
709
 */
710
function utf8_decode_deep($value) {
711
        $value = is_array($value) ?
712
                array_map('utf8_decode_deep', $value) :
713
                        (is_null($value) ? NULL : utf8_decode($value));
714
        return $value;
715
}
716

    
717
/**
718
 *  Resume text for followup
719
 *
720
 * @param $string string: string to resume
721
 * @param $length integer: resume length
722
 * @return cut string
723
 */
724
function resume_text($string,$length=255){
725
        
726
        if (strlen($string)>$length){
727
                $string=utf8_substr($string,0,$length)."&nbsp;(...)";
728
        }
729
        return $string;
730
}
731

    
732
/**
733
 *  Format mail row
734
 *
735
 * @param $string string: label string
736
 * @param $value string: value string
737
 * @return string
738
 */
739
function mailRow($string,$value){
740
        $row=utf8_str_pad( $string . ': ',25,' ', STR_PAD_RIGHT).$value."\n";
741

    
742
        return $row;
743
}
744

    
745
/**
746
 *  Replace str_pad()
747
 *  who bug with utf8
748
 *
749
 * @param $ps_input string: input string
750
 * @param $pn_pad_length integer: padding length
751
 * @param $ps_pad_string string: padding string
752
 * @param $pn_pad_type: integer: padding type
753
 * @return string
754
 */
755
function utf8_str_pad($ps_input, $pn_pad_length, $ps_pad_string = " ", $pn_pad_type = STR_PAD_RIGHT) {
756
        $ret = "";
757
        
758
        $hn_length_of_padding = $pn_pad_length - utf8_strlen($ps_input);
759
        $hn_psLength = utf8_strlen($ps_pad_string); // pad string length
760
        
761
        if ($hn_psLength <= 0 || $hn_length_of_padding <= 0) {
762
                // Padding string equal to 0:
763
                //
764
                $ret = $ps_input;
765
        } else {
766
                $hn_repeatCount = floor($hn_length_of_padding / $hn_psLength); // how many times repeat
767
        
768
                if ($pn_pad_type == STR_PAD_BOTH) {
769
                        $hs_lastStrLeft = "";
770
                        $hs_lastStrRight = "";
771
                        $hn_repeatCountLeft = $hn_repeatCountRight = ($hn_repeatCount - $hn_repeatCount % 2) / 2;
772
                        
773
                        $hs_lastStrLength = $hn_length_of_padding - 2 * $hn_repeatCountLeft * $hn_psLength; // the rest length to pad
774
                        $hs_lastStrLeftLength = $hs_lastStrRightLength = floor($hs_lastStrLength / 2);      // the rest length divide to 2 parts
775
                        $hs_lastStrRightLength += $hs_lastStrLength % 2; // the last char add to right side
776
                        
777
                        $hs_lastStrLeft = utf8_substr($ps_pad_string, 0, $hs_lastStrLeftLength);
778
                        $hs_lastStrRight = utf8_substr($ps_pad_string, 0, $hs_lastStrRightLength);
779
                        
780
                        $ret = str_repeat($ps_pad_string, $hn_repeatCountLeft) . $hs_lastStrLeft;
781
                        $ret .= $ps_input;
782
                        $ret .= str_repeat($ps_pad_string, $hn_repeatCountRight) . $hs_lastStrRight;
783
                } else {
784
                        $hs_lastStr = utf8_substr($ps_pad_string, 0, $hn_length_of_padding % $hn_psLength); // last part of pad string
785
                
786
                        if ($pn_pad_type == STR_PAD_LEFT){
787
                                $ret = str_repeat($ps_pad_string, $hn_repeatCount) . $hs_lastStr . $ps_input;
788
                        } else {
789
                                $ret = $ps_input . str_repeat($ps_pad_string, $hn_repeatCount) . $hs_lastStr;
790
                        }
791
                }
792
        }
793
        
794
        return $ret;
795
}
796

    
797

    
798

    
799
//  Inspired From SPIP
800
// Suppression basique et brutale de tous les <...>
801
/*function removeTags($string, $rempl = "") {
802
        $string = preg_replace(",<[^>]*>,U", $rempl, $string);
803
        // ne pas oublier un < final non ferme
804
        // mais qui peut aussi etre un simple signe plus petit que
805
        $string = str_replace('<', ' ', $string);
806
        return $string;
807
}
808

809
//  Inspired from SPIP
810
/*function textBrut($string) {
811

812
        $string = preg_replace("/\s+/u", " ", $string);
813
        $string = preg_replace("/<(p|br)( [^>]*)?".">/i", "\n\n", $string);
814
        $string = preg_replace("/^\n+/", "", $string);
815
        $string = preg_replace("/\n+$/", "", $string);
816
        $string = preg_replace("/\n +/", "\n", $string);
817
        $string = removeTags($string);
818
        $string = preg_replace("/(&nbsp;| )+/", " ", $string);
819
        // nettoyer l'apostrophe curly qui pose probleme a certains rss-readers, lecteurs de mail...
820
        $string = str_replace("&#8217;","'",$string);
821
        return $string;
822
}
823

824
*/
825

    
826
/**
827
 * Clean display value deleting html tags
828
 *
829
 *@param $value string: string value
830
 *
831
 *@return clean value
832
 **/
833
function html_clean($value){
834
//  Inspired from SPIP and http://fr3.php.net/strip-tags
835
/*
836
        $search=array(
837
                        "/<a[^>]+>/i",
838
                        "/<img[^>]+>/i",
839
                        "/<span[^>]+>/i",
840
                        "/<\/span>/i",
841
                        "/<\/a>/i",
842
                        "/<strong>/i",
843
                        "/<\/strong>/i",
844
                        "/<small>/i",
845
                        "/<\/small>/i",
846
                        "/<i>/i",
847
                        "/<\/i>/i",
848
                        "/<br>/i",
849
                        "/<br \/>/i",
850
                        "/&nbsp;;/",
851
                        "/&nbsp;/",
852
                        "/<p>/i",
853
                        "/<\/p>/i",
854
                        "/<div[^>]+>/i",
855
                        "/<\/div>/i",
856
                        "/<ul>/i",
857
                        "/<\/ul>/i",
858
                        "/<li>/i",
859
                        "/<\/li>/i",
860
                        "/<ol>/i",
861
                        "/<\/ol>/i",
862
                        "/<h[0-9]>/i",
863
                        "/<\/h[0-9]>/i",
864
                        "/<font[^>]+>/i",
865
                        "/<\/font>/i",
866

867
                     );
868
        $replace=array(
869
                        "",
870
                        "",
871
                        "",
872
                        "",
873
                        "",
874
                        "",
875
                        "",
876
                        "",
877
                        "",
878
                        "",
879
                        "",
880
                        ", ",
881
                        "",
882
                        " ",
883
                        " ",
884
                        "",
885
                        "\n",
886
                        "",
887
                        "\n",
888
                        "",
889
                        "\n",
890
                        "",
891
                        "\n",
892
                        "",
893
                        "\n",
894
                        "",
895
                        "\n",
896
                        "",
897
                        "",
898
                      );
899
        
900
        $value=preg_replace($search,$replace,$value);
901
        return trim($value);
902
*/
903

    
904

    
905

    
906
        $search = array('@<script[^>]*?>.*?</script[^>]*?>@si',  // Strip out javascript
907
               '@<style[^>]*?>.*?</style[^>]*?>@siU',    // Strip style tags properly
908
               '@<[\/\!]*?[^<>]*?>@si',            // Strip out HTML tags
909
               '@<![\s\S]*?--[ \t\n\r]*>@'        // Strip multi-line comments including CDATA
910
        );
911
        $value = preg_replace($search, ' ', $value);
912

    
913
        $value = preg_replace("/(&nbsp;| )+/", " ", $value);
914
        // nettoyer l'apostrophe curly qui pose probleme a certains rss-readers, lecteurs de mail...
915
        $value = str_replace("&#8217;","'",$value);
916

    
917
        $value = preg_replace("/<(p|br)( [^>]*)?".">/i", "\n", $value);
918

    
919
        $value = preg_replace("/ +/u", " ", $value);
920
//        $value = preg_replace("/^\n+/", " ", $value);
921
//        $value = preg_replace("/\n+$/", " ", $value);
922

    
923
        $value = preg_replace("/\n{2,}/", "\n\n", $value,-1);
924

    
925
        return trim($value);
926
}
927

    
928

    
929
/**
930
 * Convert a date YY-MM-DD HH:MM to DD-MM-YY HH:MM for display in a html table
931
 *
932
 * @param $time datetime: datetime to convert 
933
 * @return $time or $date
934
 */
935
function convDateTime($time) { 
936
        global $CFG_GLPI;
937
        if (is_null($time)) return $time;
938
        if (isset($CFG_GLPI["dateformat"])&&$CFG_GLPI["dateformat"]!=0) {
939
                $date = substr($time,8,2)."-";        // jour 
940
                $date = $date.substr($time,5,2)."-";  // mois 
941
                $date = $date.substr($time,0,4). " "; // année 
942
                $date = $date.substr($time,11,5);     // heures et minutes 
943
                return $date; 
944
        }else {
945
                return $time;
946
        }
947
}
948

    
949
/**
950
 * Convert a date YY-MM-DD to DD-MM-YY for calendar
951
 *
952
 * @param $time date: date to convert 
953
 * @return $time or $date
954
 */
955
function convDate($time) { 
956
        global $CFG_GLPI;
957
        if (is_null($time)) return $time;
958
        if (isset($CFG_GLPI["dateformat"])&&$CFG_GLPI["dateformat"]!=0) {
959
                $date = substr($time,8,2)."-";        // jour 
960
                $date = $date.substr($time,5,2)."-";  // mois 
961
                $date = $date.substr($time,0,4); // année 
962
                //$date = $date.substr($time,11,5);     // heures et minutes 
963
                return $date; 
964
        }else {
965
                return $time;
966
        }
967
}
968

    
969
/**
970
 * Convert a number to correct display
971
 *
972
 * @param $number float: Number to display
973
 * @param $edit boolean: display number for edition ? (id edit use . in all case)
974
 * @param $forcedecimal integer: Force decimal number (do not use default value)
975
 *
976
 * @return formatted number
977
 */
978
function formatNumber($number,$edit=false,$forcedecimal=-1) { 
979
        global $CFG_GLPI;
980

    
981
        // Php 5.3 : number_format() expects parameter 1 to be double,
982
        if ($number=="") {
983
                $number=0;        
984
        }
985
        $decimal=$CFG_GLPI["decimal_number"];
986
        if ($forcedecimal>=0){
987
                $decimal=$forcedecimal;
988
        }
989

    
990
        // Edit : clean display for mysql
991
        if ($edit){
992
                return number_format($number,$decimal,'.','');
993
        }
994

    
995
        // Display : clean display
996
        switch ($CFG_GLPI["numberformat"]){
997
                case 2: // Other French
998
                        return number_format($number,$decimal,',',' ');
999
                        break;
1000
                case 0: // French
1001
                        return number_format($number,$decimal,'.',' ');
1002
                        break;
1003
                default: // English
1004
                        return number_format($number,$decimal,'.',',');
1005
                        break;
1006
        }        
1007
}
1008

    
1009
/**
1010
 *  Send a file to the navigator
1011
 *
1012
 * @param $file string: storage filename
1013
 * @param $filename string: file title
1014
 * @return nothing
1015
 */
1016
function sendFile($file,$filename){
1017
        global $DB;
1018

    
1019
        // Test securite : document in DOC_DIR
1020
        $tmpfile=ereg_replace(GLPI_DOC_DIR,"",$file);
1021
        if (ereg("\.\.",$tmpfile)){
1022
                echo "Security attack !!!";
1023
                logEvent($file, "sendFile", 1, "security", $_SESSION["glpiname"]." try to get a non standard file.");
1024
                return;
1025
        }
1026

    
1027
        if (!file_exists($file)){
1028
                echo "Error file $file does not exist";
1029
                return;
1030
        } else {
1031
                $splitter=split("/",$file);
1032
                $filedb=$splitter[count($splitter)-2]."/".$splitter[count($splitter)-1];
1033
                $query="SELECT mime from glpi_docs WHERE filename LIKE '$filedb'";
1034
                $result=$DB->query($query);
1035
                $mime="application/octetstream";
1036
                if ($result&&$DB->numrows($result)==1){
1037
                        $mime=$DB->result($result,0,0);
1038
                } else {
1039
                        // fichiers DUMP SQL et XML
1040
                        if ($splitter[count($splitter)-2]=="dump"){
1041
                                $splitter2=split("\.",$file);
1042
                                switch ($splitter2[count($splitter2)-1]) {
1043
                                        case "sql" : 
1044
                                                $mime="text/x-sql";
1045
                                        break;
1046
                                        case "xml" :
1047
                                                $mime="text/xml";
1048
                                        break;
1049
                                }
1050
                        } else {
1051
                                // Cas particulier
1052
                                switch ($splitter[count($splitter)-2]) {
1053
                                        case "SQL" : 
1054
                                                $mime="text/x-sql";
1055
                                        break;
1056
                                        case "XML" :
1057
                                                $mime="text/xml";
1058
                                        break;
1059
                                }
1060
                        }
1061

    
1062
                }
1063

    
1064
                // Now send the file with header() magic
1065
                header("Expires: Mon, 26 Nov 1962 00:00:00 GMT");
1066
                header('Pragma: private'); /// IE BUG + SSL
1067
                //header('Pragma: no-cache'); 
1068
                header('Cache-control: private, must-revalidate'); /// IE BUG + SSL
1069
                header("Content-disposition: filename=\"$filename\"");
1070
                header("Content-type: ".$mime);
1071

    
1072
                $f=fopen($file,"r");
1073

    
1074
                if (!$f){
1075
                        echo "Error opening file $file";
1076
                } else {
1077
                        // Pour que les \x00 ne devienne pas \0
1078
                        $mc=get_magic_quotes_runtime();
1079
                        if ($mc) @set_magic_quotes_runtime(0); 
1080

    
1081
                        echo fread($f, filesize($file));
1082

    
1083
                        if ($mc) @set_magic_quotes_runtime($mc); 
1084
                }
1085
        }
1086
}
1087

    
1088
/**
1089
 * Convert a value in byte, kbyte, megabyte etc...
1090
 *
1091
 * @param $val string: config value (like 10k, 5M)
1092
 * @return $val
1093
 */
1094
function return_bytes_from_ini_vars($val) {
1095
        $val = trim($val);
1096
        $last = strtolower($val{strlen($val)-1});
1097
        switch($last) {
1098
                // Le modifieur 'G' est disponible depuis PHP 5.1.0
1099
                case 'g':
1100
                        $val *= 1024;
1101
                case 'm':
1102
                        $val *= 1024;
1103
                case 'k':
1104
                        $val *= 1024;
1105
        }
1106

    
1107
        return $val;
1108
}
1109

    
1110
/**
1111
 * Header redirection hack
1112
 *
1113
 * @param $dest string: Redirection destination 
1114
 * @return nothing
1115
 */
1116
function glpi_header($dest){
1117
        $toadd='';
1118
        if (!ereg("\?",$dest)){
1119
                $toadd='?tokonq='.getRandomString(5);
1120
        }         
1121
        echo "<script language=javascript>
1122
                NomNav = navigator.appName;
1123
                if (NomNav=='Konqueror'){
1124
                        window.location=\"".$dest.$toadd."\";
1125
                } else {
1126
                        window.location=\"".$dest."\";
1127
                }
1128
        </script>";
1129
        exit();
1130
}
1131

    
1132
/**
1133
 * Call cron
1134
 *
1135
 * @return nothing
1136
 */
1137
function callCron(){
1138
        if (ereg("front",$_SERVER['PHP_SELF'])){
1139
                echo "<div style=\"background-image: url('cron.php');\"></div>";
1140
        } else {
1141
                echo "<div style=\"background-image: url('front/cron.php');\"></div>";
1142
        }
1143
}
1144

    
1145

    
1146
/**
1147
 * Get hour from sql
1148
 *
1149
 * @param $time datetime: time
1150
 * @return  array
1151
 */
1152
function get_hour_from_sql($time){
1153
        $t=explode(" ",$time);
1154
        $p=explode(":",$t[1]);
1155
        return $p[0].":".$p[1];
1156
}
1157

    
1158
/**
1159
 *  Optimize sql table
1160
 *
1161
 * @return nothing
1162
 */
1163
function optimize_tables (){
1164

    
1165
        global $DB;
1166
        $result=$DB->list_tables();
1167
        while ($line = $DB->fetch_array($result))
1168
        {
1169
                if (ereg("glpi_",$line[0])){
1170
                        $table = $line[0];
1171
                        $query = "OPTIMIZE TABLE `".$table."` ;";
1172
                        $DB->query($query);
1173
                }
1174
        }
1175
        $DB->free_result($result);
1176
}
1177

    
1178
/**
1179
* Is a string seems to be UTF-8 one ?
1180
* 
1181
* @param $Str string: string to analyze
1182
* @return  boolean 
1183
**/
1184
function seems_utf8($Str) {
1185
        for ($i=0; $i<strlen($Str); $i++) {
1186
                if (ord($Str[$i]) < 0x80) continue; # 0bbbbbbb
1187
                        elseif ((ord($Str[$i]) & 0xE0) == 0xC0) $n=1; # 110bbbbb
1188
                                elseif ((ord($Str[$i]) & 0xF0) == 0xE0) $n=2; # 1110bbbb
1189
                                elseif ((ord($Str[$i]) & 0xF8) == 0xF0) $n=3; # 11110bbb
1190
                                elseif ((ord($Str[$i]) & 0xFC) == 0xF8) $n=4; # 111110bb
1191
                                elseif ((ord($Str[$i]) & 0xFE) == 0xFC) $n=5; # 1111110b
1192
                else return false; # Does not match any model
1193
                        for ($j=0; $j<$n; $j++) { # n bytes matching 10bbbbbb follow ?
1194
                                if ((++$i == strlen($Str)) || ((ord($Str[$i]) & 0xC0) != 0x80))
1195
                                        return false;
1196
                        }
1197
        }
1198
        return true;
1199
}
1200

    
1201

    
1202

    
1203
/**
1204
 * NOT USED IN CORE - Used for update process - Clean string for knowbase display
1205
 * replace nl2br
1206
 * 
1207
 * @param $pee string: initial string
1208
 * @param $br boolean: make line breaks ?
1209
 * 
1210
 * @return $string
1211
 */
1212
function autop($pee, $br=true) {
1213
        // Thanks  to Matthew Mullenweg
1214

    
1215
        $pee = preg_replace("/(\r\n|\n|\r)/", "\n", $pee); // cross-platform newlines
1216
        $pee = preg_replace("/\n\n+/", "\n\n", $pee); // take care of duplicates
1217
        $pee = preg_replace('/\n?(.+?)(\n\n|\z)/s', "<p>$1</p>\n", $pee); // make paragraphs, including one at the end
1218
        if ($br) {
1219
                $pee = preg_replace('|(?<!</p>)\s*\n|', "<br>\n", $pee); // optionally make line breaks
1220
        }
1221
        return $pee;
1222
}
1223

    
1224

    
1225
/**
1226
 * NOT USED IN CORE - Used for update process - make url clickable
1227
 *
1228
 * @param $chaine string: initial string
1229
 * 
1230
 * @return $string
1231
 */
1232
function clicurl($chaine){
1233
        $text=preg_replace("`((?:https?|ftp)://\S+)(\s|\z)`", '<a href="$1">$1</a>$2', $chaine); 
1234

    
1235
        return $text;
1236
}
1237

    
1238
/**
1239
 * NOT USED IN CORE - Used for update process - Split the message into tokens ($inside contains all text inside $start and $end, and $outside contains all text outside)
1240
 *
1241
 * @param $text string: initial text
1242
 * @param $start integer: where to start
1243
 * @param $end integer: where to stop
1244
 * 
1245
 * @return array 
1246
 */
1247
function split_text($text, $start, $end){
1248

    
1249
        // Adapt�de PunBB 
1250
        //Copyright (C)  Rickard Andersson (rickard@punbb.org)
1251

    
1252
        $tokens = explode($start, $text);
1253

    
1254
        $outside[] = $tokens[0];
1255

    
1256
        $num_tokens = count($tokens);
1257
        for ($i = 1; $i < $num_tokens; ++$i){
1258
                $temp = explode($end, $tokens[$i]);
1259
                $inside[] = $temp[0];
1260
                $outside[] = $temp[1];
1261
        }
1262

    
1263
        return array($inside, $outside);
1264
}
1265

    
1266

    
1267
/**
1268
 * NOT USED IN CORE - Used for update process - Replace bbcode in text by html tag
1269
 *
1270
 * @param $string string: initial string
1271
 * 
1272
 * @return formatted string 
1273
 */
1274
function rembo($string){
1275

    
1276
        // Adapt�de PunBB 
1277
        //Copyright (C)  Rickard Andersson (rickard@punbb.org)
1278

    
1279
        // If the message contains a code tag we have to split it up (text within [code][/code] shouldn't be touched)
1280
        if (strpos($string, '[code]') !== false && strpos($string, '[/code]') !== false)
1281
        {
1282
                list($inside, $outside) = split_text($string, '[code]', '[/code]');
1283
                $outside = array_map('trim', $outside);
1284
                $string = implode('<">', $outside);
1285
        }
1286

    
1287

    
1288
        $pattern = array('#\[b\](.*?)\[/b\]#s',
1289
                        '#\[i\](.*?)\[/i\]#s',
1290
                        '#\[u\](.*?)\[/u\]#s',
1291
                        '#\[s\](.*?)\[/s\]#s',
1292
                        '#\[c\](.*?)\[/c\]#s',
1293
                        '#\[g\](.*?)\[/g\]#s',
1294
                        //'#\[url\](.*?)\[/url\]#e',
1295
                        //'#\[url=(.*?)\](.*?)\[/url\]#e',
1296
                        '#\[email\](.*?)\[/email\]#',
1297
                        '#\[email=(.*?)\](.*?)\[/email\]#',
1298
                        '#\[color=([a-zA-Z]*|\#?[0-9a-fA-F]{6})](.*?)\[/color\]#s');
1299

    
1300

    
1301
        $replace = array('<strong>$1</strong>',
1302
                        '<em>$1</em>',
1303
                        '<span class="souligne">$1</span>',
1304
                        '<span class="barre">$1</span>',
1305
                        '<div align="center">$1</div>',
1306
                        '<big>$1</big>',
1307
                        // 'truncate_url(\'$1\')',
1308
                        //'truncate_url(\'$1\', \'$2\')',
1309
                '<a href="mailto:$1">$1</a>',
1310
                '<a href="mailto:$1">$2</a>',
1311
                '<span style="color: $1">$2</span>');
1312

    
1313
        // This thing takes a while! :)
1314
        $string = preg_replace($pattern, $replace, $string);
1315

    
1316
        $string=clicurl($string);
1317
        $string=autop($string);
1318

    
1319
        // If we split up the message before we have to concatenate it together again (code tags)
1320
        if (isset($inside)){
1321
                        $outside = explode('<">', $string);
1322
                        $string = '';
1323
                        $num_tokens = count($outside);
1324

    
1325
                        for ($i = 0; $i < $num_tokens; ++$i){
1326
                                        $string .= $outside[$i];
1327
                                        if (isset($inside[$i]))
1328
                                                $string .= '<br><br><table  class="code" align="center" cellspacing="4" cellpadding="6"><tr><td class="punquote"><strong>Code:</strong><br><br><pre>'.trim($inside[$i]).'</pre></td></tr></table><br>';
1329
                        }
1330
        }
1331

    
1332
        return $string;
1333
}
1334

    
1335
/**
1336
* Create SQL search condition
1337
* 
1338
* @param $val string: value to search
1339
* @param $not boolean: is a negative search ?
1340
* 
1341
* @return search string 
1342
**/ 
1343
function makeTextSearch($val,$not=false){
1344
        $NOT="";
1345
        if ($not) {
1346
                $NOT= " NOT ";
1347
        }
1348
        // Unclean to permit < and > search
1349
        $val=unclean_cross_side_scripting_deep($val);
1350
        if ($val=="NULL"||$val=="null") {
1351
                $SEARCH=" IS $NOT NULL ";
1352
        } else {
1353
                $begin=0;
1354
                $end=0;
1355
                if (($length=strlen($val))>0){
1356
                        if (($val[0]=='^')){
1357
                                $begin=1;
1358
                        }
1359
                        if ($val[$length-1]=='$'){
1360
                                $end=1;
1361
                        }
1362
                }
1363
                if ($begin||$end) {
1364
                        $val=substr($val,$begin,$length-$end-$begin);
1365
                }
1366

    
1367
                $SEARCH=" $NOT LIKE '".(!$begin?"%":"").$val.(!$end?"%":"")."' ";
1368

    
1369
        }
1370

    
1371
        return $SEARCH;
1372
}
1373

    
1374
/**
1375
 * Get a web page. Use proxy if configured
1376
 * 
1377
 * @param $url string: to retrieve
1378
 * @param $msgerr string: set if problem encountered
1379
 * @param $rec integer: internal use only Must be 0
1380
 * 
1381
 * @return content of the page (or empty)
1382
 */
1383
//Note:  Depuis PHP 5, les valeurs par défaut peuvent être passées par référence.
1384
//function getURLContent ($url, &$msgerr=NULL, $rec=0) {
1385
function getURLContent ($url, &$msgerr, $rec=0) {
1386

    
1387
        global $LANG,$CFG_GLPI;
1388
        
1389
        $content="";
1390

    
1391
        // Connection directe
1392
        if (empty($CFG_GLPI["proxy_name"])){
1393
                $taburl=parse_url($url);
1394
                if ($fp=@fsockopen($taburl["host"], (isset($taburl["port"]) ? $taburl["port"] : 80), $errno, $errstr, 1)){
1395

    
1396
                        if (isset($taburl["path"]) && $taburl["path"]!='/') {
1397
                                // retrieve path + args
1398
                                $request  = "GET ".strstr($url, $taburl["path"])." HTTP/1.1\r\n";
1399
                        } else {
1400
                                $request  = "GET / HTTP/1.1\r\n";
1401
                        }
1402
                        $request .= "Host: ".$taburl["host"]."\r\n";
1403

    
1404
                } else {
1405
                        if (isset($msgerr)) {
1406
                                $msgerr=$LANG["setup"][304] . " ($errstr)"; // failed direct connexion - try proxy
1407
                        }
1408
                        return "";
1409
                }
1410
                
1411
        } else { // Connection using proxy
1412

    
1413
                $fp = fsockopen($CFG_GLPI["proxy_name"], $CFG_GLPI["proxy_port"], $errno, $errstr, 1);
1414
                if ($fp) {
1415
        
1416
                        $request  = "GET $url HTTP/1.1\r\n";
1417
                        $request .= "Host: ".$CFG_GLPI["proxy_name"]."\r\n";
1418
                        if (!empty($CFG_GLPI["proxy_user"])) {
1419
                                $request .= "Proxy-Authorization: Basic " . base64_encode ($CFG_GLPI["proxy_user"].":".$CFG_GLPI["proxy_password"]) . "\r\n";                                
1420
                        }
1421
                        
1422
                } else {
1423
                        if (isset($msgerr)) {
1424
                                $msgerr=$LANG["setup"][311] . " ($errstr)"; // failed proxy connexion
1425
                        }
1426
                        return "";
1427
                }
1428
        }
1429
                 
1430
        $request .= "User-Agent: GLPI/".trim($CFG_GLPI["version"])."\r\n";
1431
        $request .= "Connection: Close\r\n\r\n";
1432
        
1433
        fwrite($fp, $request);
1434
        
1435
        $header=true ;
1436
        $redir=false;
1437
        $errstr="";
1438
        while(!feof($fp)) {
1439
                if ($buf=fgets($fp, 1024)) {
1440
                        if ($header) {
1441
                                if (strlen(trim($buf))==0) {
1442
                                        // Empty line = end of header
1443
                                        $header=false;
1444
                                } else if ($redir && ereg("^Location: (.*)$", $buf, $rep)) {
1445
                                        if ($rec<9) {
1446
                                                return (getURLContent(trim($rep[1]),$errstr,$rec+1));                                                
1447
                                        } else {
1448
                                                $errstr="Too deep";
1449
                                                break;
1450
                                        }
1451
                                } else if (ereg("^HTTP.*200.*OK", $buf)) {
1452
                                        // HTTP 200 = OK
1453
                                } else if (ereg("^HTTP.*302", $buf)) {
1454
                                        // HTTP 302 = Moved Temporarily
1455
                                        $redir=true;
1456
                                } else if (ereg("^HTTP", $buf)) {
1457
                                        // Other HTTP status = error
1458
                                        $errstr=trim($buf);
1459
                                        break;
1460
                                }        
1461
                        }
1462
                        else { 
1463
                                // Body
1464
                                $content .= $buf;        
1465
                        }
1466
                }
1467
        } // eof
1468
        
1469
        fclose($fp);
1470

    
1471
         if (empty($content) && isset($msgerr)) {
1472
                 if (empty($errstr)) {
1473
                         $msgerr=$LANG["setup"][312]; // no data
1474
                 }
1475
                else {
1476
                        $msgerr=$LANG["setup"][310] . " ($errstr)"; // HTTP error        
1477
                }
1478
        }
1479

    
1480
        return $content;        
1481
}
1482

    
1483
/**
1484
* Check if new version is available 
1485
* 
1486
* @param $auto boolean: check done autically ? (if not display result)
1487
* 
1488
* @return string explaining the result 
1489
**/
1490
function checkNewVersionAvailable($auto=true){
1491
        global $DB,$LANG,$CFG_GLPI;
1492

    
1493
        if (!haveRight("check_update","r")) return false;        
1494

    
1495
        if (!$auto) echo "<br>";
1496

    
1497
        $error="";
1498
        $latest_version = getURLContent("http://glpi-project.org/latest_version", $error);
1499

    
1500
        if (strlen(trim($latest_version)) == 0){
1501
                if (!$auto) {
1502
                        echo "<div class='center'> $error </div>";
1503
                } else {
1504
                        return $error;
1505
                }
1506
        } else {                        
1507
                $splitted=split("\.",trim($CFG_GLPI["version"]));
1508

    
1509
                if ($splitted[0]<10) $splitted[0].="0";
1510
                if ($splitted[1]<10) $splitted[1].="0";
1511
                $cur_version = $splitted[0]*10000+$splitted[1]*100;
1512
                if (isset($splitted[2])) {
1513
                        if ($splitted[2]<10) $splitted[2].="0";
1514
                        $cur_version+=$splitted[2];
1515
                }
1516

    
1517
                $splitted=split("\.",trim($latest_version));
1518

    
1519
                if ($splitted[0]<10) $splitted[0].="0";
1520
                if ($splitted[1]<10) $splitted[1].="0";
1521

    
1522
                $lat_version = $splitted[0]*10000+$splitted[1]*100;
1523
                if (isset($splitted[2])) {
1524
                        if ($splitted[2]<10) $splitted[2].="0";
1525
                        $lat_version+=$splitted[2];
1526
                }
1527

    
1528
                if ($cur_version < $lat_version){
1529
                        $config_object=new Config();
1530
                        $input["ID"]=1;
1531
                        $input["founded_new_version"]=$latest_version;
1532
                        $config_object->update($input);
1533
                        if (!$auto) {
1534
                                echo "<div class='center'>".$LANG["setup"][301]." ".$latest_version."</div>";
1535
                                echo "<div class='center'>".$LANG["setup"][302]."</div>";
1536
                        } else {
1537
                                return $LANG["setup"][301]." ".$latest_version;
1538
                        }
1539
                }  else {
1540
                        if (!$auto){
1541
                                echo "<div class='center'>".$LANG["setup"][303]."</div>";
1542
                        } else {
1543
                                return $LANG["setup"][303];
1544
                        }
1545
                }
1546
        } 
1547
        return 1;
1548
}
1549
/**
1550
* Cron job to check if a new version is available
1551
* 
1552
**/
1553
function cron_check_update(){
1554
        global $CFG_GLPI;
1555
        $result=checkNewVersionAvailable(1);
1556
        logInFile("cron",$result."\n");
1557
}
1558

    
1559
/**
1560
* Get date using a begin date and a period in month
1561
* 
1562
* @param $from date: begin date
1563
* @param $addwarranty integer: period in months
1564
* @param $deletenotice integer: period in months of notice
1565
* 
1566
* @return expiration date string
1567
**/
1568
function getWarrantyExpir($from,$addwarranty,$deletenotice=0){
1569
        global $LANG;
1570
        // Life warranty
1571
        if ($addwarranty==-1 && $deletenotice==0){
1572
                return $LANG["setup"][307];
1573
        }
1574
        if ($from==NULL || $from=='0000-00-00')
1575
                return "";
1576
        else {
1577
                return convDate(date("Y-m-d", strtotime("$from+$addwarranty month -$deletenotice month")));
1578
        }
1579

    
1580
}
1581
/**
1582
* Get date using a begin date and a period in month and a notice one
1583
* 
1584
* @param $begin date: begin date
1585
* @param $duration integer: period in months
1586
* @param $notice integer: notice in months 
1587
* 
1588
* @return expiration string 
1589
**/
1590
function getExpir($begin,$duration,$notice="0"){
1591
        global $LANG;
1592
        if ($begin==NULL || $begin=='0000-00-00'){
1593
                return "";
1594
        } else {
1595
                $diff=strtotime("$begin+$duration month -$notice month")-time();
1596
                $diff_days=floor($diff/60/60/24);
1597
                if($diff_days>0){
1598
                        return $diff_days." ".$LANG["stats"][31];
1599
                }else{
1600
                        return "<span class='red'>".$diff_days." ".$LANG["stats"][31]."</span>";
1601
                }
1602
        }
1603
}
1604

    
1605
/**
1606
* Manage login redirection 
1607
* 
1608
* @param $where string: where to redirect ? 
1609
**/
1610
function manageRedirect($where){
1611
        global $CFG_GLPI,$PLUGIN_HOOKS;
1612
        if (!empty($where)){
1613
                $data=split("_",$where);
1614
                if (count($data)>=2&&isset($_SESSION["glpiactiveprofile"]["interface"])&&!empty($_SESSION["glpiactiveprofile"]["interface"])){
1615
                        switch ($_SESSION["glpiactiveprofile"]["interface"]){
1616
                                case "helpdesk" :
1617
                                        switch ($data[0]){
1618
                                                case "plugin":
1619
                                                        if (isset($data[2])&&$data[2]>0&&isset($PLUGIN_HOOKS['redirect_page'][$data[1]])&&!empty($PLUGIN_HOOKS['redirect_page'][$data[1]])){
1620
                                                                glpi_header($CFG_GLPI["root_doc"]."/plugins/".$data[1]."/".$PLUGIN_HOOKS['redirect_page'][$data[1]]."?ID=".$data[2]);
1621
                                                        } else {
1622
                                                                glpi_header($CFG_GLPI["root_doc"]."/front/helpdesk.public.php");
1623
                                                        } 
1624
                                                break;
1625
                                                case "tracking":
1626
                                                        glpi_header($CFG_GLPI["root_doc"]."/front/helpdesk.public.php?show=user&ID=".$data[1]);
1627
                                                break;
1628
                                                case "prefs":
1629
                                                        glpi_header($CFG_GLPI["root_doc"]."/front/user.form.my.php");
1630
                                                break;
1631
                                                default:
1632
                                                        glpi_header($CFG_GLPI["root_doc"]."/front/helpdesk.public.php");
1633
                                                break;
1634

    
1635

    
1636
                                        }
1637
                                break;
1638
                                case "central" :
1639
                                        switch ($data[0]){
1640
                                                case "plugin":
1641
                                                        if (isset($data[2])&&$data[2]>0&&isset($PLUGIN_HOOKS['redirect_page'][$data[1]])&&!empty($PLUGIN_HOOKS['redirect_page'][$data[1]])){
1642
                                                                glpi_header($CFG_GLPI["root_doc"]."/plugins/".$data[1]."/".$PLUGIN_HOOKS['redirect_page'][$data[1]]."?ID=".$data[2]);
1643
                                                        } else {
1644
                                                                glpi_header($CFG_GLPI["root_doc"]."/front/central.php");
1645
                                                        } 
1646
                                                break;
1647
                                                case "prefs":
1648
                                                        glpi_header($CFG_GLPI["root_doc"]."/front/user.form.my.php");
1649
                                                break;
1650
                                                default : 
1651
                                                        if (!empty($data[0])&&$data[1]>0){
1652
                                                                glpi_header($CFG_GLPI["root_doc"]."/front/".$data[0].".form.php?ID=".$data[1]);
1653
                                                        } else {
1654
                                                                glpi_header($CFG_GLPI["root_doc"]."/front/central.php");
1655
                                                        }
1656
                                                break;
1657
                                        }
1658
                                break;
1659
                        }
1660
                }
1661
        }
1662
}
1663
/**
1664
* Clean string for input text field 
1665
* 
1666
* @param $string string: input text
1667
* 
1668
* @return clean string
1669
**/
1670
function cleanInputText($string){
1671
        return preg_replace('/\"/','&quot;',$string);
1672
} 
1673

    
1674
/**
1675
* Get a random string 
1676
* 
1677
* @param $length integer: length of the random string 
1678
* 
1679
* @return random string
1680
**/
1681
function getRandomString($length) {
1682

    
1683
        $alphabet = "1234567890abcdefghijklmnopqrstuvwxyz";
1684
        $rndstring="";
1685
        for ($a = 0; $a <= $length; $a++) {
1686
                $b = rand(0, strlen($alphabet) - 1);
1687
                $rndstring .= $alphabet[$b];
1688
        }
1689
        return $rndstring;
1690
}
1691

    
1692
/**
1693
* Make a good string from the unix timestamp $sec
1694
* 
1695
* @param $sec integer: timestamp
1696
* 
1697
* @param $display_sec boolean: display seconds ? 
1698
* 
1699
* @return string 
1700
**/
1701
function timestampToString($sec,$display_sec=true){
1702
        global $LANG;
1703
        $sec=floor($sec);
1704
        if ($sec<0) $sec=0;
1705

    
1706
        if($sec < MINUTE_TIMESTAMP) {
1707
                return $sec." ".$LANG["stats"][34];
1708

    
1709
        } else if($sec < HOUR_TIMESTAMP) {
1710
                $min = floor($sec/MINUTE_TIMESTAMP);
1711
                $sec = $sec%MINUTE_TIMESTAMP;
1712

    
1713
                $out=$min." ".$LANG["stats"][33];
1714
                if ($display_sec) $out.=" ".$sec." ".$LANG["stats"][34];
1715
                return $out;
1716

    
1717
        } else if($sec <  DAY_TIMESTAMP) {
1718
                $heure = floor($sec/HOUR_TIMESTAMP);
1719
                $min = floor(($sec%HOUR_TIMESTAMP)/(MINUTE_TIMESTAMP));
1720
                $sec = $sec%MINUTE_TIMESTAMP;
1721
                $out=$heure." ".$LANG["job"][21]." ".$min." ".$LANG["stats"][33];
1722
                if ($display_sec) $out.=" ".$sec." ".$LANG["stats"][34];
1723
                return $out;
1724

    
1725
        } else {
1726
                $jour = floor($sec/DAY_TIMESTAMP);
1727
                $heure = floor(($sec%DAY_TIMESTAMP)/(HOUR_TIMESTAMP));
1728
                $min = floor(($sec%HOUR_TIMESTAMP)/(MINUTE_TIMESTAMP));
1729
                $sec = $sec%MINUTE_TIMESTAMP;
1730
                $out=$jour." ".$LANG["stats"][31]." ".$heure." ".$LANG["job"][21]." ".$min." ".$LANG["stats"][33];
1731
                if ($display_sec) $out.=" ".$sec." ".$LANG["stats"][34];
1732
                return $out;
1733

    
1734
        }
1735
}
1736
/**
1737
* Delete a directory and file contains in it
1738
* 
1739
* @param $dir string: directory to delete
1740
**/
1741
function deleteDir($dir) {
1742
        if (file_exists($dir)){
1743
                chmod($dir,0777);
1744
                if (is_dir($dir)){
1745
                        $id_dir = opendir($dir);
1746
                        while($element = readdir($id_dir)){
1747
                                if ($element != "." && $element != ".."){
1748
                                        if (is_dir($element)){
1749
                                                deleteDir($dir."/".$element);
1750
                                        } else {
1751
                                                unlink($dir."/".$element);
1752
                                        }
1753
        
1754
                                }
1755
                        }
1756
                        closedir($id_dir);
1757
                        rmdir($dir);
1758
                } else { // Delete file
1759
                        unlink($dir);
1760
                }
1761
        }
1762
}
1763

    
1764
/**
1765
 * Determine if a login is valid
1766
 * @param $login string: login to check
1767
 * @return boolean 
1768
 */
1769
function isValidLogin($login="")
1770
{
1771
        return preg_match( "/^[[:alnum:]@.\-_]+$/i", $login);
1772
}
1773

    
1774

    
1775
/**
1776
 * Determine if Ldap is usable checking ldap extension existence
1777
 * @return boolean 
1778
 */
1779
function canUseLdap(){
1780
        return extension_loaded('ldap');
1781
}
1782

    
1783
/**
1784
 * Determine if Imap/Pop is usable checking extension existence
1785
 * @return boolean 
1786
 */
1787
function canUseImapPop(){
1788
        return extension_loaded('imap');
1789
}
1790

    
1791

    
1792
/** Converts an array of parameters into a query string to be appended to a URL.
1793
 *
1794
 * @return  string  : Query string to append to a URL.
1795
 * @param   $array  array: parameters to append to the query string.
1796
 * @param   $parent This should be left blank (it is used internally by the function).
1797
 */
1798
function append_params($array, $parent=''){
1799
        $params = array();
1800
        foreach ($array as $k => $v){
1801
                if (is_array($v))
1802
                $params[] = append_params($v, (empty($parent) ? rawurlencode($k) : $parent . '[' . rawurlencode($k) . ']'));
1803
                else
1804
                $params[] = (!empty($parent) ? $parent . '[' . rawurlencode($k) . ']' : rawurlencode($k)) . '=' . rawurlencode($v);
1805
        }
1806
        
1807
        return implode('&', $params);
1808
}
1809

    
1810
/** Format a size passing a size in octet
1811
 *
1812
 * @param   $size integer: Size in octet
1813
 * @return  formatted size
1814
 */
1815
function getSize($size) {
1816
        $bytes = array('B','KB','MB','GB','TB');
1817
        foreach($bytes as $val) {
1818
                if($size > 1024){
1819
                        $size = $size / 1024;
1820
                }else{
1821
                        break;
1822
                }
1823
        }
1824
        return round($size, 2)." ".$val;
1825
}
1826
?>
Redmine Appliance - Powered by TurnKey Linux