Updated PEAR and PEAR packages.
[timetracker.git] / WEB-INF / lib / pear / OS / Guess.php
1 <?php
2 /**
3  * The OS_Guess class
4  *
5  * PHP versions 4 and 5
6  *
7  * @category   pear
8  * @package    PEAR
9  * @author     Stig Bakken <ssb@php.net>
10  * @author     Gregory Beaver <cellog@php.net>
11  * @copyright  1997-2009 The Authors
12  * @license    http://opensource.org/licenses/bsd-license.php New BSD License
13  * @link       http://pear.php.net/package/PEAR
14  * @since      File available since PEAR 0.1
15  */
16
17 // {{{ uname examples
18
19 // php_uname() without args returns the same as 'uname -a', or a PHP-custom
20 // string for Windows.
21 // PHP versions prior to 4.3 return the uname of the host where PHP was built,
22 // as of 4.3 it returns the uname of the host running the PHP code.
23 //
24 // PC RedHat Linux 7.1:
25 // Linux host.example.com 2.4.2-2 #1 Sun Apr 8 20:41:30 EDT 2001 i686 unknown
26 //
27 // PC Debian Potato:
28 // Linux host 2.4.17 #2 SMP Tue Feb 12 15:10:04 CET 2002 i686 unknown
29 //
30 // PC FreeBSD 3.3:
31 // FreeBSD host.example.com 3.3-STABLE FreeBSD 3.3-STABLE #0: Mon Feb 21 00:42:31 CET 2000     root@example.com:/usr/src/sys/compile/CONFIG  i386
32 //
33 // PC FreeBSD 4.3:
34 // FreeBSD host.example.com 4.3-RELEASE FreeBSD 4.3-RELEASE #1: Mon Jun 25 11:19:43 EDT 2001     root@example.com:/usr/src/sys/compile/CONFIG  i386
35 //
36 // PC FreeBSD 4.5:
37 // FreeBSD host.example.com 4.5-STABLE FreeBSD 4.5-STABLE #0: Wed Feb  6 23:59:23 CET 2002     root@example.com:/usr/src/sys/compile/CONFIG  i386
38 //
39 // PC FreeBSD 4.5 w/uname from GNU shellutils:
40 // FreeBSD host.example.com 4.5-STABLE FreeBSD 4.5-STABLE #0: Wed Feb  i386 unknown
41 //
42 // HP 9000/712 HP-UX 10:
43 // HP-UX iq B.10.10 A 9000/712 2008429113 two-user license
44 //
45 // HP 9000/712 HP-UX 10 w/uname from GNU shellutils:
46 // HP-UX host B.10.10 A 9000/712 unknown
47 //
48 // IBM RS6000/550 AIX 4.3:
49 // AIX host 3 4 000003531C00
50 //
51 // AIX 4.3 w/uname from GNU shellutils:
52 // AIX host 3 4 000003531C00 unknown
53 //
54 // SGI Onyx IRIX 6.5 w/uname from GNU shellutils:
55 // IRIX64 host 6.5 01091820 IP19 mips
56 //
57 // SGI Onyx IRIX 6.5:
58 // IRIX64 host 6.5 01091820 IP19
59 //
60 // SparcStation 20 Solaris 8 w/uname from GNU shellutils:
61 // SunOS host.example.com 5.8 Generic_108528-12 sun4m sparc
62 //
63 // SparcStation 20 Solaris 8:
64 // SunOS host.example.com 5.8 Generic_108528-12 sun4m sparc SUNW,SPARCstation-20
65 //
66 // Mac OS X (Darwin)
67 // Darwin home-eden.local 7.5.0 Darwin Kernel Version 7.5.0: Thu Aug  5 19:26:16 PDT 2004; root:xnu/xnu-517.7.21.obj~3/RELEASE_PPC  Power Macintosh
68 //
69 // Mac OS X early versions
70 //
71
72 // }}}
73
74 /* TODO:
75  * - define endianness, to allow matchSignature("bigend") etc.
76  */
77
78 /**
79  * Retrieves information about the current operating system
80  *
81  * This class uses php_uname() to grok information about the current OS
82  *
83  * @category   pear
84  * @package    PEAR
85  * @author     Stig Bakken <ssb@php.net>
86  * @author     Gregory Beaver <cellog@php.net>
87  * @copyright  1997-2009 The Authors
88  * @license    http://opensource.org/licenses/bsd-license.php New BSD License
89  * @version    Release: 1.10.1
90  * @link       http://pear.php.net/package/PEAR
91  * @since      Class available since Release 0.1
92  */
93 class OS_Guess
94 {
95     var $sysname;
96     var $nodename;
97     var $cpu;
98     var $release;
99     var $extra;
100
101     function __construct($uname = null)
102     {
103         list($this->sysname,
104              $this->release,
105              $this->cpu,
106              $this->extra,
107              $this->nodename) = $this->parseSignature($uname);
108     }
109
110     function parseSignature($uname = null)
111     {
112         static $sysmap = array(
113             'HP-UX' => 'hpux',
114             'IRIX64' => 'irix',
115         );
116         static $cpumap = array(
117             'i586' => 'i386',
118             'i686' => 'i386',
119             'ppc' => 'powerpc',
120         );
121         if ($uname === null) {
122             $uname = php_uname();
123         }
124         $parts = preg_split('/\s+/', trim($uname));
125         $n = count($parts);
126
127         $release  = $machine = $cpu = '';
128         $sysname  = $parts[0];
129         $nodename = $parts[1];
130         $cpu      = $parts[$n-1];
131         $extra = '';
132         if ($cpu == 'unknown') {
133             $cpu = $parts[$n - 2];
134         }
135
136         switch ($sysname) {
137             case 'AIX' :
138                 $release = "$parts[3].$parts[2]";
139                 break;
140             case 'Windows' :
141                 switch ($parts[1]) {
142                     case '95/98':
143                         $release = '9x';
144                         break;
145                     default:
146                         $release = $parts[1];
147                         break;
148                 }
149                 $cpu = 'i386';
150                 break;
151             case 'Linux' :
152                 $extra = $this->_detectGlibcVersion();
153                 // use only the first two digits from the kernel version
154                 $release = preg_replace('/^([0-9]+\.[0-9]+).*/', '\1', $parts[2]);
155                 break;
156             case 'Mac' :
157                 $sysname = 'darwin';
158                 $nodename = $parts[2];
159                 $release = $parts[3];
160                 if ($cpu == 'Macintosh') {
161                     if ($parts[$n - 2] == 'Power') {
162                         $cpu = 'powerpc';
163                     }
164                 }
165                 break;
166             case 'Darwin' :
167                 if ($cpu == 'Macintosh') {
168                     if ($parts[$n - 2] == 'Power') {
169                         $cpu = 'powerpc';
170                     }
171                 }
172                 $release = preg_replace('/^([0-9]+\.[0-9]+).*/', '\1', $parts[2]);
173                 break;
174             default:
175                 $release = preg_replace('/-.*/', '', $parts[2]);
176                 break;
177         }
178
179         if (isset($sysmap[$sysname])) {
180             $sysname = $sysmap[$sysname];
181         } else {
182             $sysname = strtolower($sysname);
183         }
184         if (isset($cpumap[$cpu])) {
185             $cpu = $cpumap[$cpu];
186         }
187         return array($sysname, $release, $cpu, $extra, $nodename);
188     }
189
190     function _detectGlibcVersion()
191     {
192         static $glibc = false;
193         if ($glibc !== false) {
194             return $glibc; // no need to run this multiple times
195         }
196         $major = $minor = 0;
197         include_once "System.php";
198         // Use glibc's <features.h> header file to
199         // get major and minor version number:
200         if (@file_exists('/usr/include/features.h') &&
201               @is_readable('/usr/include/features.h')) {
202             if (!@file_exists('/usr/bin/cpp') || !@is_executable('/usr/bin/cpp')) {
203                 $features_file = fopen('/usr/include/features.h', 'rb');
204                 while (!feof($features_file)) {
205                     $line = fgets($features_file, 8192);
206                     if (!$line || (strpos($line, '#define') === false)) {
207                         continue;
208                     }
209                     if (strpos($line, '__GLIBC__')) {
210                         // major version number #define __GLIBC__ version
211                         $line = preg_split('/\s+/', $line);
212                         $glibc_major = trim($line[2]);
213                         if (isset($glibc_minor)) {
214                             break;
215                         }
216                         continue;
217                     }
218
219                     if (strpos($line, '__GLIBC_MINOR__'))  {
220                         // got the minor version number
221                         // #define __GLIBC_MINOR__ version
222                         $line = preg_split('/\s+/', $line);
223                         $glibc_minor = trim($line[2]);
224                         if (isset($glibc_major)) {
225                             break;
226                         }
227                         continue;
228                     }
229                 }
230                 fclose($features_file);
231                 if (!isset($glibc_major) || !isset($glibc_minor)) {
232                     return $glibc = '';
233                 }
234                 return $glibc = 'glibc' . trim($glibc_major) . "." . trim($glibc_minor) ;
235             } // no cpp
236
237             $tmpfile = System::mktemp("glibctest");
238             $fp = fopen($tmpfile, "w");
239             fwrite($fp, "#include <features.h>\n__GLIBC__ __GLIBC_MINOR__\n");
240             fclose($fp);
241             $cpp = popen("/usr/bin/cpp $tmpfile", "r");
242             while ($line = fgets($cpp, 1024)) {
243                 if ($line{0} == '#' || trim($line) == '') {
244                     continue;
245                 }
246
247                 if (list($major, $minor) = explode(' ', trim($line))) {
248                     break;
249                 }
250             }
251             pclose($cpp);
252             unlink($tmpfile);
253         } // features.h
254
255         if (!($major && $minor) && @is_link('/lib/libc.so.6')) {
256             // Let's try reading the libc.so.6 symlink
257             if (preg_match('/^libc-(.*)\.so$/', basename(readlink('/lib/libc.so.6')), $matches)) {
258                 list($major, $minor) = explode('.', $matches[1]);
259             }
260         }
261
262         if (!($major && $minor)) {
263             return $glibc = '';
264         }
265
266         return $glibc = "glibc{$major}.{$minor}";
267     }
268
269     function getSignature()
270     {
271         if (empty($this->extra)) {
272             return "{$this->sysname}-{$this->release}-{$this->cpu}";
273         }
274         return "{$this->sysname}-{$this->release}-{$this->cpu}-{$this->extra}";
275     }
276
277     function getSysname()
278     {
279         return $this->sysname;
280     }
281
282     function getNodename()
283     {
284         return $this->nodename;
285     }
286
287     function getCpu()
288     {
289         return $this->cpu;
290     }
291
292     function getRelease()
293     {
294         return $this->release;
295     }
296
297     function getExtra()
298     {
299         return $this->extra;
300     }
301
302     function matchSignature($match)
303     {
304         $fragments = is_array($match) ? $match : explode('-', $match);
305         $n = count($fragments);
306         $matches = 0;
307         if ($n > 0) {
308             $matches += $this->_matchFragment($fragments[0], $this->sysname);
309         }
310         if ($n > 1) {
311             $matches += $this->_matchFragment($fragments[1], $this->release);
312         }
313         if ($n > 2) {
314             $matches += $this->_matchFragment($fragments[2], $this->cpu);
315         }
316         if ($n > 3) {
317             $matches += $this->_matchFragment($fragments[3], $this->extra);
318         }
319         return ($matches == $n);
320     }
321
322     function _matchFragment($fragment, $value)
323     {
324         if (strcspn($fragment, '*?') < strlen($fragment)) {
325             $reg = '/^' . str_replace(array('*', '?', '/'), array('.*', '.', '\\/'), $fragment) . '\\z/';
326             return preg_match($reg, $value);
327         }
328         return ($fragment == '*' || !strcasecmp($fragment, $value));
329     }
330
331 }
332 /*
333  * Local Variables:
334  * indent-tabs-mode: nil
335  * c-basic-offset: 4
336  * End:
337  */