PageRenderTime 51ms CodeModel.GetById 14ms RepoModel.GetById 1ms app.codeStats 0ms

/lib/functions.display.php

https://bitbucket.org/rmarefaty/linfo
PHP | 1141 lines | 911 code | 108 blank | 122 comment | 164 complexity | 50279e4dfe6c57411b71ae2dbfd0121f MD5 | raw file
Possible License(s): GPL-3.0
  1. <?php
  2. /**
  3. * This file is part of Linfo (c) 2010 Joseph Gillotti.
  4. *
  5. * Linfo is free software: you can redistribute it and/or modify
  6. * it under the terms of the GNU General Public License as published by
  7. * the Free Software Foundation, either version 3 of the License, or
  8. * (at your option) any later version.
  9. *
  10. * Linfo is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU General Public License
  16. * along with Linfo. If not, see <http://www.gnu.org/licenses/>.
  17. *
  18. */
  19. /**
  20. * Keep out hackers...
  21. */
  22. defined('IN_INFO') or exit;
  23. /**
  24. * Show it all... in very minimal HTML
  25. * @param array $info the system information
  26. * @param array $settings linfo settings
  27. */
  28. function showInfoHTML($info, $settings) {
  29. // Gain access to language array
  30. global $lang;
  31. // Fun icons
  32. $show_icons = array_key_exists('icons', $settings) ? !empty($settings['icons']) : true;
  33. $os_icon = defined('IS_WINDOWS') ? 'windows' : strtolower(str_replace(' ', '', current(explode('(', $info['OS']))));
  34. $distro_icon = $info['OS'] == 'Linux' && is_array($info['Distro']) && $info['Distro']['name'] ? strtolower(str_replace(' ', '', $info['Distro']['name'])) : false;
  35. // Start compressed output buffering
  36. if (!isset($settings['compress_content']) || $settings['compress_content'])
  37. ob_start('ob_gzhandler');
  38. // Proceed to letting it all out
  39. echo '<!DOCTYPE html>
  40. <html>
  41. <head>
  42. <meta charset="UTF-8" />
  43. <title>'.AppName.' - '.$info['HostName'].'</title>
  44. <link href="'.WEB_PATH.'layout/favicon.ico" type="image/x-icon" rel="shortcut icon" />
  45. <link href="'.WEB_PATH.'layout/styles.css" rel="stylesheet" />'.( $show_icons ? '
  46. <link href="'.WEB_PATH.'layout/icons.css" rel="stylesheet" />' : ''
  47. ).'
  48. <script src="'.WEB_PATH.'layout/scripts.min.js"></script>
  49. <meta name="generator" content="'.AppName.' ('.VERSION.')" />
  50. <meta name="author" content="Joseph Gillotti &amp; friends" />
  51. <!--[if lt IE 8]>
  52. <link href="'.WEB_PATH.'layout/old_ie.css" type="text/css" rel="stylesheet" />
  53. <![endif]-->
  54. </head>
  55. <body id="info">
  56. <div id="header">
  57. <h1>'.$info['HostName'].'</h1>
  58. <div class="subtitle">'.$lang['header'].'</div>
  59. </div>
  60. <div class="col2">
  61. <div class="col">
  62. <div class="infoTable">
  63. <h2>'.$lang['core'].'</h2>
  64. <table>';
  65. // Linfo Core. Decide what to show.
  66. $core = array();
  67. // OS? (with icon, if we have it)
  68. if (!empty($settings['show']['os']))
  69. $core[] = array($lang['os'], ($show_icons && (file_exists(LOCAL_PATH . 'layout/icons/os_'.$os_icon.'.gif') || file_exists(LOCAL_PATH . 'layout/icons/os_'.$os_icon.'.png')) ? '<span class="icon icon_os_'.$os_icon.'"></span>' : '') . $info['OS']);
  70. // Distribution? (with icon, if we have it)
  71. if (!empty($settings['show']['distro']) && array_key_exists('Distro', $info) && is_array($info['Distro']))
  72. $core[] = array($lang['distro'], ($show_icons && $distro_icon && (file_exists(LOCAL_PATH . 'layout/icons/distro_'.$distro_icon.'.gif') || file_exists(LOCAL_PATH . 'layout/icons/distro_'.$distro_icon.'.png')) ? '<span class="icon icon_distro_'.$distro_icon.'"></span>' : '') . $info['Distro']['name'] . ($info['Distro']['version'] ? ' - '.$info['Distro']['version'] : ''));
  73. // Kernel
  74. if (!empty($settings['show']['kernel']))
  75. $core[] = array($lang['kernel'], $info['Kernel']);
  76. // Model?
  77. if (!empty($settings['show']['model']) && array_key_exists('Model', $info) && !empty($info['Model']))
  78. $core[] = array($lang['model'], $info['Model']);
  79. // IP
  80. $core[] = array($lang['accessed_ip'], isset($_SERVER['SERVER_ADDR']) ? $_SERVER['SERVER_ADDR'] : 'Unknown');
  81. // Uptime
  82. if (!empty($settings['show']['uptime']))
  83. $core[] = array($lang['uptime'], $info['UpTime']);
  84. // Hostname
  85. if (!empty($settings['show']['hostname']))
  86. $core[] = array($lang['hostname'], $info['HostName']);
  87. // The CPUs
  88. if (!empty($settings['show']['cpu'])) {
  89. $cpus = '';
  90. foreach ((array) $info['CPU'] as $cpu)
  91. $cpus .=
  92. (array_key_exists('Vendor', $cpu) ? $cpu['Vendor'] . ' - ' : '') .
  93. $cpu['Model'] .
  94. (array_key_exists('MHz', $cpu) ?
  95. ($cpu['MHz'] < 1000 ? ' ('.$cpu['MHz'].' MHz)' : ' ('.round($cpu['MHz'] / 1000, 3).' GHz)') : '') .
  96. '<br />';
  97. $core[] = array('CPUs ('.count($info['CPU']).')', $cpus);
  98. }
  99. // CPU architecture. Permissions goes hand in hand with normal CPU
  100. if (!empty($settings['show']['cpu']) && array_key_exists('CPUArchitecture', $info))
  101. $core[] = array($lang['cpu_arch'], $info['CPUArchitecture']);
  102. // System Load
  103. if (!empty($settings['show']['load']))
  104. $core[] = array($lang['load'], implode(' ', (array) $info['Load']));
  105. // We very well may not have process stats
  106. if (!empty($settings['show']['process_stats']) && $info['processStats']['exists']) {
  107. // Different os' have different keys of shit
  108. $proc_stats = array();
  109. // Load the keys
  110. if (array_key_exists('totals', $info['processStats']) && is_array($info['processStats']['totals']))
  111. foreach ($info['processStats']['totals'] as $k => $v)
  112. $proc_stats[] = $k . ': ' . number_format($v);
  113. // Total as well
  114. $proc_stats[] = 'total: ' . number_format($info['processStats']['proc_total']);
  115. // Show them
  116. $core[] = array($lang['processes'], implode('; ', $proc_stats));
  117. // We might not have threads
  118. if ($info['processStats']['threads'] !== false)
  119. $core[] = array($lang['threads'], number_format($info['processStats']['threads']));
  120. }
  121. // Users with active shells
  122. if (!empty($settings['show']['numLoggedIn']) && array_key_exists('numLoggedIn', $info))
  123. $core[] = array($lang['numLoggedIn'], $info['numLoggedIn']);
  124. // Show
  125. for ($i = 0, $core_num = count($core); $i < $core_num; $i++) {
  126. echo '
  127. <tr>
  128. <th>'.$core[$i][0].'</th>
  129. <td>'.$core[$i][1].'</td>
  130. </tr>
  131. ';
  132. }
  133. echo '
  134. </table>
  135. </div>';
  136. // Show memory?
  137. if (!empty($settings['show']['ram'])) {
  138. echo '
  139. <div class="infoTable">
  140. <h2>'.$lang['memory'].'</h2>
  141. <table>
  142. <colgroup>
  143. <col style="width: 10%;" />
  144. <col style="width: 30%;" />
  145. <col style="width: 30%;" />
  146. <col style="width: 30%;" />
  147. </colgroup>
  148. <tr>
  149. <th>'.$lang['type'].'</th>
  150. <th>'.$lang['free'].'</th>
  151. <th>'.$lang['used'].'</th>
  152. <th>'.$lang['size'].'</th>
  153. </tr>
  154. <tr>
  155. <td>'.$info['RAM']['type'].'</td>
  156. <td>'.byte_convert($info['RAM']['free']).'</td>
  157. <td>'.byte_convert($info['RAM']['total'] - $info['RAM']['free']).'</td>
  158. <td>'.byte_convert($info['RAM']['total']).'</td>
  159. </tr>';
  160. $have_swap = (isset($info['RAM']['swapFree']) || isset($info['RAM']['swapTotal']));
  161. if ($have_swap) {
  162. // Show detailed swap info?
  163. $show_detailed_swap = is_array($info['RAM']['swapInfo']) && count($info['RAM']['swapInfo']) > 0;
  164. echo'
  165. <tr>
  166. <td'.($show_detailed_swap ? ' rowspan="2"' : '').'>Swap</td>
  167. <td>'.byte_convert(@$info['RAM']['swapFree']).'</td>
  168. <td>'.byte_convert(@$info['RAM']['swapTotal'] - $info['RAM']['swapFree']).'</td>
  169. <td>'.byte_convert(@$info['RAM']['swapTotal']).'</td>
  170. </tr>';
  171. // As in we have at least one swap device present. Show them.
  172. if ($show_detailed_swap) {
  173. echo '
  174. <tr>
  175. <td colspan="3">
  176. <table class="mini center">
  177. <colgroup>
  178. <col style="width: 25%;" />
  179. <col style="width: 25%;" />
  180. <col style="width: 25%;" />
  181. <col style="width: 25%;" />
  182. </colgroup>
  183. <tr>
  184. <th>'.$lang['device'].'</th>
  185. <th>'.$lang['type'].'</th>
  186. <th>'.$lang['size'].'</th>
  187. <th>'.$lang['used'].'</th>
  188. </tr>';
  189. foreach($info['RAM']['swapInfo'] as $swap)
  190. echo '
  191. <tr>
  192. <td>'.$swap['device'].'</td>
  193. <td>'.ucfirst($swap['type']).'</td>
  194. <td>'.byte_convert($swap['size']).'</td>
  195. <td>'.byte_convert($swap['used']).'</td>
  196. </tr>
  197. ';
  198. echo '
  199. </table>
  200. </td>
  201. </tr>';
  202. }
  203. }
  204. echo '
  205. </table>
  206. </div>';
  207. }
  208. // Network Devices?
  209. if (!empty($settings['show']['network'])) {
  210. $show_type = array_key_exists('nic_type', $info['contains']) ? ($info['contains']['nic_type'] === false ? false : true) : true;
  211. echo '
  212. <div class="infoTable">
  213. <h2>'.$lang['network_devices'].'</h2>
  214. <table>
  215. <tr>
  216. <th>'.$lang['device_name'].'</th>',$show_type ? '
  217. <th>'.$lang['type'].'</th>' : '','
  218. <th>'.$lang['amount_sent'].'</th>
  219. <th>'.$lang['amount_received'].'</th>
  220. <th>'.$lang['state'].'</th>
  221. </tr>';
  222. if (count($info['Network Devices']) > 0)
  223. foreach($info['Network Devices'] as $device => $stats)
  224. echo '
  225. <tr>
  226. <td>'.$device.'</td>', $show_type ? '
  227. <td>'.$stats['type'].'</td>' : '','
  228. <td>'.byte_convert($stats['sent']['bytes']).'</td>
  229. <td>'.byte_convert($stats['recieved']['bytes']).'</td>
  230. <td class="net_'.$stats['state'].'">'.ucfirst($stats['state']).'</td>
  231. </tr>';
  232. else
  233. echo '<tr><td colspan="5" class="none">'.$lang['none_found'].'</td></tr>';
  234. echo '
  235. </table>
  236. </div>';
  237. }
  238. // Show temps?
  239. if (!empty($settings['show']['temps']) && count($info['Temps']) > 0) {
  240. echo '
  241. <div class="infoTable">
  242. <h2>'.$lang['temps_voltages'].'</h2>
  243. <table>
  244. <tr><th>'.$lang['path'].'</th><th>'.$lang['device'].'</th><th>'.$lang['value'].'</th></tr>
  245. ';
  246. $num_temps = count($info['Temps']);
  247. if ($num_temps > 0) {
  248. for($i = 0; $i < $num_temps; $i++) {
  249. $stat = $info['Temps'][$i];
  250. echo '
  251. <tr>
  252. <td>'.$stat['path'].'</td>
  253. <td>'.$stat['name'].'</td>
  254. <td>'.(
  255. array_key_exists('bar', $stat) && $stat['bar'] && $stat['unit'] == '%' ?
  256. '<div class="bar_chart">
  257. <div class="bar_inner" style="width: '.$stat['temp'].'%;">
  258. <div class="bar_text">
  259. '.($stat['temp'] > -1 ? $stat['temp']: '?').'%
  260. </div>
  261. </div>
  262. </div>
  263. ':
  264. $stat['temp'].' '.$stat['unit']).'</td>
  265. </tr>
  266. ';
  267. }
  268. }
  269. else
  270. echo '<tr><td colspan="3" class="none">'.$lang['none_found'].'</td></tr>';
  271. echo '
  272. </table>
  273. </div>';
  274. }
  275. // Show battery?
  276. if (!empty($settings['show']['battery']) && count($info['Battery']) > 0) {
  277. echo '
  278. <div class="infoTable">
  279. <h2>'.$lang['batteries'].'</h2>
  280. <table>
  281. <tr><th>'.$lang['device'].'</th><th>'.$lang['state'].'</th><th>'.$lang['charge'].' %</th></tr>
  282. ';
  283. foreach ($info['Battery'] as $bat)
  284. echo '
  285. <tr>
  286. <td>'.$bat['device'].'</td>
  287. <td>'.$bat['state'].'</td>
  288. <td>
  289. <div class="bar_chart">
  290. <div class="bar_inner" style="width: '.(int) $bat['percentage'].'%;">
  291. <div class="bar_text">
  292. '.($bat['percentage'] > -1 ? $bat['percentage']: '?').'
  293. </div>
  294. </div>
  295. </div>
  296. </td>
  297. </tr>
  298. ';
  299. echo '
  300. </table>
  301. </div>';
  302. }
  303. // Show services?
  304. if (!empty($settings['show']['services']) && count($info['services']) > 0) {
  305. echo '
  306. <div class="infoTable">
  307. <h2>'.$lang['services'].'</h2>
  308. <table>
  309. <tr>
  310. <th>'.$lang['service'].'</th><th>'.$lang['state'].'</th><th>'.$lang['pid'].'</th><th>Threads</th><th>'.$lang['memory_usage'].'</th>
  311. </tr>
  312. ';
  313. // Show them
  314. foreach ($info['services'] as $service => $state) {
  315. $state_parts = explode(' ', $state['state'], 2);
  316. echo '
  317. <tr>
  318. <td>'.$service.'</td>
  319. <td>
  320. <span class="service_'.strtolower($state_parts[0]).'">'.$state_parts[0].'</span>
  321. '.(array_key_exists(1, $state_parts) ? '<span class="faded">'.$state_parts[1].'</span>' : '').'</td>
  322. <td>'.$state['pid'].'</td>
  323. <td>',$state['threads'] ? $state['threads'] : '?','</td>
  324. <td>',$state['memory_usage'] ? byte_convert($state['memory_usage']) : '?','</td>
  325. </tr>
  326. ';
  327. }
  328. echo '
  329. </table>
  330. </div>';
  331. }
  332. echo '
  333. </div>
  334. <div class="col">';
  335. // Show hardware?
  336. if (!empty($settings['show']['devices'])) {
  337. // Don't show vendor?
  338. $show_vendor = array_key_exists('hw_vendor', $info['contains']) ? ($info['contains']['hw_vendor'] === false ? false : true) : true;
  339. echo '
  340. <div class="infoTable">
  341. <h2>'.$lang['hardware'].'</h2>
  342. <table>
  343. <tr>
  344. <th>'.$lang['type'].'</th>
  345. ',($show_vendor ? '<th>'.$lang['vendor'].'</th>' : ''),'
  346. <th>'.$lang['device'].'</th>
  347. </tr>
  348. ';
  349. $num_devs = count($info['Devices']);
  350. if ($num_devs > 0) {
  351. for ($i = 0; $i < $num_devs; $i++) {
  352. echo '
  353. <tr>
  354. <td class="center">'.$info['Devices'][$i]['type'].'</td>
  355. ',$show_vendor ? '<td>'.($info['Devices'][$i]['vendor'] ? $info['Devices'][$i]['vendor'] : 'Unknown').'</td>' : '','
  356. <td>'.$info['Devices'][$i]['device'].'</td>
  357. </tr>';
  358. }
  359. }
  360. else
  361. echo '<tr><td colspan="3" class="none">'.$lang['none_found'].'</td></tr>';
  362. echo '
  363. </table>
  364. </div>';
  365. }
  366. // Show drives?
  367. if (!empty($settings['show']['hd'])) {
  368. // Should we not show the Reads and Writes columns?
  369. $show_stats = array_key_exists('drives_rw_stats', $info['contains']) ? ($info['contains']['drives_rw_stats'] === false ? false : true) : true;
  370. // Or vendor columns?
  371. $show_vendor = array_key_exists('drives_vendor', $info['contains']) ? ($info['contains']['drives_vendor'] === false ? false : true) : true;
  372. echo '
  373. <div class="infoTable">
  374. <h2>Drives</h2>
  375. <table>
  376. <tr>
  377. <th>'.$lang['path'].'</th>
  378. ',$show_vendor ? '<th>'.$lang['vendor'] : '','</th>
  379. <th>'.$lang['name'].'</th>
  380. ',$show_stats ? '<th>'.$lang['reads'].'</th>
  381. <th>'.$lang['writes'].'</th>' : '','
  382. <th>'.$lang['size'].'</th>
  383. </tr>';
  384. if (count($info['HD']) > 0)
  385. foreach($info['HD'] as $drive) {
  386. echo '
  387. <tr>
  388. <td>'.$drive['device'].'</td>
  389. ',$show_vendor ? '<td>'.($drive['vendor'] ? $drive['vendor'] : $lang['unknown']).'</td>' : '','
  390. <td>',$drive['name'] ? $drive['name'] : $lang['unknown'],'</td>
  391. ', $show_stats ? '<td>'.($drive['reads'] !== false ? number_format($drive['reads']) : $lang['unknown']).'</td>
  392. <td>'.($drive['writes'] !== false ? number_format($drive['writes']) : $lang['unknown']).'</td>' : '','
  393. <td>',$drive['size'] ? byte_convert($drive['size']) : $lang['unknown'],'</td>
  394. </tr>';
  395. // If we've got partitions for this drive, show them too
  396. if (array_key_exists('partitions', $drive) && is_array($drive['partitions']) && count($drive['partitions']) > 0) {
  397. echo '
  398. <tr>
  399. <td colspan="6">';
  400. // Each
  401. foreach ($drive['partitions'] as $partition)
  402. echo '
  403. &#9492; '. (isset($partition['number']) ? $drive['device'].$partition['number'] : $partition['name']) .' - '.byte_convert($partition['size']).'<br />';
  404. echo '
  405. </td>
  406. </tr>
  407. ';
  408. }
  409. }
  410. else
  411. echo '<tr><td colspan="6" class="none">'.$lang['none_found'].'</td></tr>';
  412. echo '
  413. </table>
  414. </div>';
  415. }
  416. // Show sound card stuff?
  417. if (!empty($settings['show']['sound']) && count($info['SoundCards']) > 0) {
  418. echo '
  419. <div class="infoTable">
  420. <h2>'.$lang['sound_cards'].'</h2>
  421. <table>
  422. <tr>
  423. <th>'.$lang['number'].'</th>
  424. <th>'.$lang['vendor'].'</th>
  425. <th>'.$lang['card'].'</th>
  426. </tr>';
  427. foreach ($info['SoundCards'] as $card) {
  428. if (empty($card['vendor']))
  429. $card['vendor'] = 'Unknown';
  430. echo '
  431. <tr>
  432. <td>'.$card['number'].'</td>
  433. <td>'.$card['vendor'].'</td>
  434. <td>'.$card['card'].'</td>
  435. </tr>';
  436. }
  437. echo '
  438. </table>
  439. </div>
  440. ';
  441. }
  442. echo '
  443. </div>
  444. </div>';
  445. // Show file system mounts?
  446. if (!empty($settings['show']['mounts'])) {
  447. $has_devices = false;
  448. $has_labels = false;
  449. $has_types = false;
  450. foreach($info['Mounts'] as $mount) {
  451. if (!empty($mount['device'])) {
  452. $has_devices = true;
  453. }
  454. if (!empty($mount['label'])) {
  455. $has_labels = true;
  456. }
  457. if (!empty($mount['devtype'])) {
  458. $has_types = true;
  459. }
  460. }
  461. $addcolumns = 0;
  462. if ($settings['show']['mounts_options'])
  463. $addcolumns++;
  464. if ($has_devices)
  465. $addcolumns++;
  466. if ($has_labels)
  467. $addcolumns++;
  468. if ($has_types)
  469. $addcolumns++;
  470. echo '
  471. <div class="infoTable">
  472. <h2>'.$lang['filesystem_mounts'].'</h2>
  473. <table>
  474. <tr>';
  475. if ($has_types) {
  476. echo '<th>'.$lang['type'].'</th>';
  477. }
  478. if ($has_devices) {
  479. echo '<th>'.$lang['device'].'</th>';
  480. }
  481. echo '<th>'.$lang['mount_point'].'</th>';
  482. if ($has_labels) {
  483. echo '<th>'.$lang['label'].'</th>';
  484. }
  485. echo'
  486. <th>'.$lang['filesystem'].'</th>',$settings['show']['mounts_options'] ? '
  487. <th>'.$lang['mount_options'].'</th>' : '','
  488. <th>'.$lang['size'].'</th>
  489. <th>'.$lang['used'].'</th>
  490. <th>'.$lang['free'].'</th>
  491. <th style="width: 12%;">'.$lang['percent_used'].'</th>
  492. </tr>
  493. ';
  494. // Calc totals
  495. $total_size = 0;
  496. $total_used = 0;
  497. $total_free = 0;
  498. // Don't add totals for duplicates. (same filesystem mount twice in different places)
  499. $done_devices = array();
  500. // Are there any?
  501. if (count($info['Mounts']) > 0)
  502. // Go through each
  503. foreach($info['Mounts'] as $mount) {
  504. // Only add totals for this device if we haven't already
  505. if (!in_array($mount['device'], $done_devices)) {
  506. $total_size += $mount['size'];
  507. $total_used += $mount['used'];
  508. $total_free += $mount['free'];
  509. if (!empty($mount['device']))
  510. $done_devices[] = $mount['device'];
  511. }
  512. // Possibly don't show this twice
  513. else if (array_key_exists('duplicate_mounts', $settings['show']) && empty($settings['show']['duplicate_mounts']))
  514. continue;
  515. // If it's an NFS mount it's likely in the form of server:path (without a trailing slash),
  516. // but if the path is just / it likely just shows up as server:,
  517. // which is vague. If there isn't a /, add one
  518. if (preg_match('/^.+:$/', $mount['device']) == 1)
  519. $mount['device'] .= DIRECTORY_SEPARATOR;
  520. echo '<tr>';
  521. if ($has_types) {
  522. echo '<td>'.$mount['devtype'].'</td>';
  523. }
  524. if ($has_devices) {
  525. echo '<td>'.$mount['device'].'</td>';
  526. }
  527. echo '<td>'.$mount['mount'].'</td>';
  528. if ($has_labels) {
  529. echo '<td>'.$mount['label'].'</td>';
  530. }
  531. echo'
  532. <td>'.$mount['type'].'</td>', $settings['show']['mounts_options'] ? '
  533. <td>'.(empty($mount['options']) ? '<em>unknown</em>' : '<ul><li>'.implode('</li><li>', $mount['options']).'</li></ul>').'</td>' : '','
  534. <td>'.byte_convert($mount['size']).'</td>
  535. <td>'.byte_convert($mount['used']).
  536. ' <span class="perc">('.($mount['used_percent'] !== false ? $mount['used_percent'] : 'N/A').'%)</span></td>
  537. <td>'.byte_convert($mount['free']).
  538. ' <span class="perc">('.($mount['free_percent'] !== false ? $mount['free_percent'] : 'N/A').'%)</span></td>
  539. <td>
  540. <div class="bar_chart">
  541. <div class="bar_inner" style="width: '.(int) $mount['used_percent'].'%;">
  542. <div class="bar_text">
  543. '.($mount['used_percent'] ? $mount['used_percent'].'%' : 'N/A').'
  544. </div>
  545. </div>
  546. </div>
  547. </td>
  548. </tr>';
  549. }
  550. else {
  551. echo '<tr><td colspan="',6 + $addcolumns,'" class="none">None found</td></tr>';
  552. }
  553. // Show totals and finish table
  554. $total_used_perc = $total_size > 0 && $total_used > 0 ? round($total_used / $total_size, 2) * 100 : 0;
  555. echo '
  556. <tr class="alt">
  557. <td colspan="',2 + $addcolumns,'">Totals: </td>
  558. <td>'.byte_convert($total_size).'</td>
  559. <td>'.byte_convert($total_used).'</td>
  560. <td>'.byte_convert($total_free).'</td>
  561. <td>
  562. <div class="bar_chart">
  563. <div class="bar_inner" style="width: '.$total_used_perc.'%;">
  564. <div class="bar_text">
  565. '.$total_used_perc.'%
  566. </div>
  567. </div>
  568. </div>
  569. </td>
  570. </tr>
  571. </table>
  572. </div>';
  573. }
  574. // Show RAID Arrays?
  575. if (!empty($settings['show']['raid']) && count($info['Raid']) > 0) {
  576. echo '
  577. <div class="infoTable">
  578. <h2>'.$lang['raid_arrays'].'</h2>
  579. <table>
  580. <colgroup>
  581. <col style="width: 10%;" />
  582. <col style="width: 30%;" />
  583. <col style="width: 10%;" />
  584. <col style="width: 10%;" />
  585. <col style="width: 30%;" />
  586. <col style="width: 10%;" />
  587. </colgroup>
  588. <tr>
  589. <th>'.$lang['name'].'</th>
  590. <th>'.$lang['level'].'</th>
  591. <th>'.$lang['status'].'</th>
  592. <th>'.$lang['size'].'</th>
  593. <th>'.$lang['devices'].'</th>
  594. <th>'.$lang['active'].'</th>
  595. </tr>
  596. ';
  597. if (count($info['Raid']) > 0)
  598. foreach ($info['Raid'] as $raid) {
  599. $active = explode('/', $raid['count']);
  600. // http://en.wikipedia.org/wiki/Standard_RAID_levels
  601. switch ($raid['level']) {
  602. case 0:
  603. $type = 'Stripe';
  604. break;
  605. case 1:
  606. $type = 'Mirror';
  607. break;
  608. case 5:
  609. case 6:
  610. $type = 'Distributed Parity Block-Level Striping';
  611. break;
  612. default:
  613. $type = false;
  614. break;
  615. }
  616. echo '
  617. <tr>
  618. <td>'.$raid['device'].'</td>
  619. <td>'.$raid['level'].($type ? ' <span class="caption">('.$type.')</span>' : '').'</td>
  620. <td>'.ucfirst($raid['status']).'</td>
  621. <td>'.$raid['size'].'</td>
  622. <td><table class="mini center margin_auto"><tr><th>'.$lang['device'].'</th><th>'.$lang['state'].'</th></tr>';
  623. foreach ($raid['drives'] as $drive)
  624. echo '<tr><td>'.$drive['drive'].'</td><td class="raid_'.$drive['state'].'">'.ucfirst($drive['state']).'</td></tr>';
  625. echo '</table></td>
  626. <td>'.$active[1].'/'.$active[0].'</td>
  627. </tr>
  628. ';
  629. }
  630. else
  631. echo '<tr><td colspan="6" class="none">'.$lang['none_found'].'</td></tr>';
  632. echo '
  633. </table>
  634. </div>';
  635. }
  636. // Feel like showing errors? Are there any even?
  637. if (!empty($settings['show_errors']) && LinfoError::Fledging()->num() > 0) {
  638. echo '
  639. <div id="errorList" class="infoTable">
  640. <h2>'.$lang['error_head'].'</h2>
  641. <table>
  642. <tr>
  643. <th>'.$lang['from_where'].'</th>
  644. <th>'.$lang['message'].'</th>
  645. </tr>';
  646. foreach (LinfoError::Fledging()->show() as $error) {
  647. echo '
  648. <tr>
  649. <td>'.$error[0].'</td>
  650. <td>'.$error[1].'</td>
  651. </tr>
  652. ';
  653. }
  654. echo '
  655. </table>
  656. </div>
  657. ';
  658. }
  659. // Additional extensions
  660. if (count($info['extensions']) > 0) {
  661. foreach ($info['extensions'] as $ext)
  662. if (is_array($ext) && count($ext) > 0) {
  663. // Decide how to show something extra
  664. switch (array_key_exists('extra_type', $ext) && !empty($ext['extra_vals']) ? $ext['extra_type'] : false) {
  665. // Table with a key->value table to the right of it
  666. // Useful for stats or other stuff pertaining to
  667. // the main info to the left
  668. case 'k->v':
  669. echo '
  670. <div class="col2_side">
  671. <div class="col2_side_left">
  672. '.create_table($ext).'
  673. </div>
  674. <div class="col2_side_right">
  675. <div class="infoTable">
  676. <h2>'.$ext['extra_vals']['title'].'</h2>
  677. <table>';
  678. // Give each value
  679. foreach(array_filter($ext['extra_vals']['values']) as $v)
  680. echo '
  681. <tr>
  682. <th>'.$v[0].'</th>
  683. <td>'.$v[1].'</td>
  684. </tr>';
  685. echo'
  686. </table>
  687. </div>
  688. </div>
  689. </div>
  690. ';
  691. break;
  692. // Nothing extra; just the table
  693. default:
  694. echo create_table($ext);
  695. break;
  696. }
  697. }
  698. }
  699. // Feel like showing timed results?
  700. if (!empty($settings['timer'])) {
  701. echo '
  702. <div id="timerList" class="infoTable">
  703. <h2>'.$lang['timer'].'</h2>
  704. <table>
  705. <tr>
  706. <th>'.$lang['area'].'</th>
  707. <th>'.$lang['time_taken'].'</th>
  708. </tr>';
  709. foreach (LinfoTimer::Fledging()->getResults() as $result) {
  710. echo '
  711. <tr>
  712. <td>'.$result[0].'</td>
  713. <td>'.round($result[1], 3).' '.$lang['seconds'].'</td>
  714. </tr>
  715. ';
  716. }
  717. echo '
  718. </table>
  719. </div>
  720. ';
  721. }
  722. echo '
  723. <div id="foot">
  724. '.sprintf($lang['footer_app'], '<a href="http://linfo.sf.net"><em>'.AppName.' ('.VERSION.')</em></a>', round(microtime(true) - TIME_START,2)).'<br>
  725. <em>'.AppName.'</em> &copy; 2010 &ndash; 2011 Joseph Gillotti &amp; friends. Source code licensed under GPL.
  726. </div>
  727. <div id="foot_time">
  728. <br />
  729. Generated on '.date('m/d/y h:i A').'
  730. </div>
  731. <script>Linfo.init()</script>
  732. </body>
  733. </html>';
  734. // End output buffering
  735. if (!isset($settings['compress_content']) || $settings['compress_content']) {
  736. ob_end_flush();
  737. }
  738. }
  739. /**
  740. * Show it all... in simplexml
  741. * @param array $info the system information
  742. * @param array $settings linfo settings
  743. */
  744. function showInfoSimpleXML($info, $settings) {
  745. global $lang;
  746. try {
  747. // Start it up
  748. $xml = new SimpleXMLElement('<?xml version="1.0"?><linfo></linfo>');
  749. // Deal with core stuff
  750. $core_elem = $xml->addChild('core');
  751. $core = array();
  752. if (!empty($settings['show']['os']))
  753. $core[] = array('os', $info['OS']);
  754. if (!empty($settings['show']['distro']) && is_array($info['Distro']))
  755. $core[] = array($lang['distro'], $info['Distro']['name'] . ($info['Distro']['version'] ? ' - '.$info['Distro']['version'] : ''));
  756. if (!empty($settings['show']['kernel']))
  757. $core[] = array('kernel', $info['Kernel']);
  758. $core[] = array('accessed_ip', (isset($_SERVER['SERVER_ADDR']) ? $_SERVER['SERVER_ADDR'] : 'Unknown'));
  759. if (!empty($settings['show']['uptime']))
  760. $core[] = array('uptime', $info['UpTime']);
  761. if (!empty($settings['show']['hostname']))
  762. $core[] = array('hostname', $info['HostName']);
  763. if (!empty($settings['show']['cpu'])) {
  764. $cpus = '';
  765. foreach ((array) $info['CPU'] as $cpu)
  766. $cpus .=
  767. (array_key_exists('Vendor', $cpu) ? $cpu['Vendor'] . ' - ' : '') .
  768. $cpu['Model'] .
  769. (array_key_exists('MHz', $cpu) ?
  770. ($cpu['MHz'] < 1000 ? ' ('.$cpu['MHz'].' MHz)' : ' ('.round($cpu['MHz'] / 1000, 3).' GHz)') : '') .
  771. '<br />';
  772. $core[] = array('CPU', $cpus);
  773. }
  774. if (!empty($settings['show']['model']) && array_key_exists('Model', $info) && !empty($info['Model']))
  775. $core[] = array($lang['model'], $info['Model']);
  776. if (!empty($settings['show']['load']))
  777. $core[] = array('load', implode(' ', (array) $info['Load']));
  778. if (!empty($settings['show']['process_stats']) && $info['processStats']['exists']) {
  779. $proc_stats = array();
  780. if (array_key_exists('totals', $info['processStats']) && is_array($info['processStats']['totals']))
  781. foreach ($info['processStats']['totals'] as $k => $v)
  782. $proc_stats[] = $k . ': ' . number_format($v);
  783. $proc_stats[] = 'total: ' . number_format($info['processStats']['proc_total']);
  784. $core[] = array('processes', implode('; ', $proc_stats));
  785. if ($info['processStats']['threads'] !== false)
  786. $core[] = array('threads', number_format($info['processStats']['threads']));
  787. }
  788. for ($i = 0, $core_num = count($core); $i < $core_num; $i++)
  789. $core_elem->addChild($core[$i][0], $core[$i][1]);
  790. // RAM
  791. if (!empty($settings['show']['ram'])) {
  792. $mem = $xml->addChild('memory');
  793. $core_mem = $mem->addChild($info['RAM']['type']);
  794. $core_mem->addChild('free', $info['RAM']['free']);
  795. $core_mem->addChild('total', $info['RAM']['total']);
  796. $core_mem->addChild('used', $info['RAM']['total'] - $info['RAM']['free']);
  797. if (isset($info['RAM']['swapFree']) || isset($info['RAM']['swapTotal'])){
  798. $swap = $mem->addChild('swap');
  799. $swap_core = $swap->addChild('core');
  800. $swap_core->addChild('free', $info['RAM']['swapFree']);
  801. $swap_core->addChild('total', $info['RAM']['swapTotal']);
  802. $swap_core->addChild('used', $info['RAM']['swapTotal'] - $info['RAM']['swapFree']);
  803. if (is_array($info['RAM']['swapInfo']) && count($info['RAM']['swapInfo']) > 0) {
  804. $swap_devices = $swap->addChild('devices');
  805. foreach($info['RAM']['swapInfo'] as $swap_dev) {
  806. $swap_dev_elem = $swap_devices->addChild('device');
  807. $swap_dev_elem->addAttribute('device', $swap_dev['device']);
  808. $swap_dev_elem->addAttribute('type', $swap_dev['type']);
  809. $swap_dev_elem->addAttribute('size', $swap_dev['size']);
  810. $swap_dev_elem->addAttribute('used', $swap_dev['used']);
  811. }
  812. }
  813. }
  814. }
  815. // NET
  816. if (!empty($settings['show']['network'])) {
  817. $net = $xml->addChild('net');
  818. foreach ($info['Network Devices'] as $device => $stats) {
  819. $nic = $net->addChild('interface');
  820. $nic->addAttribute('device', $device);
  821. $nic->addAttribute('type', $stats['type']);
  822. $nic->addAttribute('sent', $stats['sent']['bytes']);
  823. $nic->addAttribute('recieved', $stats['recieved']['bytes']);
  824. }
  825. }
  826. // TEMPS
  827. if (!empty($settings['show']['temps']) && count($info['Temps']) > 0) {
  828. $temps = $xml->addChild('temps');
  829. for($i = 0, $num_temps = count($info['Temps']); $i < $num_temps; $i++) {
  830. $temp = $temps->addChild('temp');
  831. $temp->addAttribute('path', $info['Temps'][$i]['path']);
  832. $temp->addAttribute('name', $info['Temps'][$i]['name']);
  833. $temp->addAttribute('temp', $info['Temps'][$i]['temp'].' '.$info['Temps'][$i]['unit']);
  834. }
  835. }
  836. // Batteries
  837. if (!empty($settings['show']['battery']) && count($info['Battery']) > 0) {
  838. $bats = $xml->addChild('batteries');
  839. foreach ($info['Battery'] as $bat) {
  840. $bat = $bats->addChild('battery');
  841. $bat->addAttribute('device', $bat['device']);
  842. $bat->addAttribute('state', $bat['state']);
  843. $bat->addAttribute('percentage', $bat['percentage']);
  844. }
  845. }
  846. // SERVICES
  847. if (!empty($settings['show']['services']) && count($info['services']) > 0) {
  848. $services = $xml->addChild('services');
  849. foreach ($info['services'] as $service => $state) {
  850. $state_parts = explode(' ', $state['state'], 2);
  851. $service_elem = $services->addChild('service');
  852. $service_elem->addAttribute('name', $service);
  853. $service_elem->addAttribute('state', $state_parts[0] . (array_key_exists(1, $state_parts) ? ' '.$state_parts[1] : ''));
  854. $service_elem->addAttribute('pid', $state['pid']);
  855. $service_elem->addAttribute('threads', $state['threads'] ? $state['threads'] : '?');
  856. $service_elem->addAttribute('mem_usage', $state['memory_usage'] ? $state['memory_usage'] : '?');
  857. }
  858. }
  859. // DEVICES
  860. if (!empty($settings['show']['devices'])) {
  861. $show_vendor = array_key_exists('hw_vendor', $info['contains']) ? ($info['contains']['hw_vendor'] === false ? false : true) : true;
  862. $devices = $xml->addChild('devices');
  863. for ($i = 0, $num_devs = count($info['Devices']); $i < $num_devs; $i++) {
  864. $device = $devices->addChild('device');
  865. $device->addAttribute('type', $info['Devices'][$i]['type']);
  866. if ($show_vendor)
  867. $device->addAttribute('vendor', $info['Devices'][$i]['vendor']);
  868. $device->addAttribute('name', $info['Devices'][$i]['device']);
  869. }
  870. }
  871. // DRIVES
  872. if (!empty($settings['show']['hd'])) {
  873. $show_stats = array_key_exists('drives_rw_stats', $info['contains']) ? ($info['contains']['drives_rw_stats'] === false ? false : true) : true;
  874. $drives = $xml->addChild('drives');
  875. foreach($info['HD'] as $drive) {
  876. $drive_elem = $drives->addChild('drive');
  877. $drive_elem->addAttribute('device', $drive['device']);
  878. $drive_elem->addAttribute('vendor', $drive['vendor'] ? $drive['vendor'] : $lang['unknown']);
  879. $drive_elem->addAttribute('name', $drive['name']);
  880. if ($show_stats) {
  881. $drive_elem->addAttribute('reads', $drive['reads'] ? $drive['reads'] : 'unknown');
  882. $drive_elem->addAttribute('writes', $drive['writes'] ? $drive['writes'] : 'unknown');
  883. }
  884. $drive_elem->addAttribute('size', $drive['size'] ? $drive['size'] : 'unknown');
  885. if (is_array($drive['partitions']) && count($drive['partitions']) > 0) {
  886. $partitions = $drive_elem->addChild('partitions');
  887. foreach ($drive['partitions'] as $partition) {
  888. $partition_elem = $partitions->addChild('partition');
  889. $partition_elem->addAttribute('name', isset($partition['number']) ? $drive['device'].$partition['number'] : $partition['name']);
  890. $partition_elem->addAttribute('size', $partition['size']);
  891. }
  892. }
  893. }
  894. }
  895. // Sound cards? lol
  896. if (!empty($settings['show']['sound']) && count($info['SoundCards']) > 0) {
  897. $cards = $xml->addChild('soundcards');
  898. foreach ($info['SoundCards'] as $card) {
  899. $card_elem = $cards->addChild('card');
  900. $card_elem->addAttribute('number', $card['number']);
  901. $card_elem->addAttribute('vendor', empty($card['vendor']) ? 'unknown' : $card['vendor']);
  902. $card_elem->addAttribute('card', $card['card']);
  903. }
  904. }
  905. // File system mounts
  906. if (!empty($settings['show']['mounts'])) {
  907. $has_devices = false;
  908. $has_labels = false;
  909. $has_types = false;
  910. foreach($info['Mounts'] as $mount) {
  911. if (!empty($mount['device'])) {
  912. $has_devices = true;
  913. }
  914. if (!empty($mount['label'])) {
  915. $has_labels = true;
  916. }
  917. if (!empty($mount['devtype'])) {
  918. $has_types = true;
  919. }
  920. }
  921. $mounts = $xml->addChild('mounts');
  922. foreach ($info['Mounts'] as $mount) {
  923. $mount_elem = $mounts->addChild('mount');
  924. if (preg_match('/^.+:$/', $mount['device']) == 1)
  925. $mount['device'] .= DIRECTORY_SEPARATOR;
  926. if ($has_types)
  927. $mount_elem->addAttribute('type', $mount['devtype']);
  928. if ($has_devices)
  929. $mount_elem->addAttribute('device', $mount['device']);
  930. $mount_elem->addAttribute('mountpoint', $mount['mount']);
  931. if ($has_labels)
  932. $mount_elem->addAttribute('label', $mount['label']);
  933. $mount_elem->addAttribute('fstype', $mount['type']);
  934. if ($settings['show']['mounts_options'] && !empty($mount['options'])) {
  935. $options_elem = $mount_elem->addChild('mount_options');
  936. foreach ($mount['options'] as $option)
  937. $options_elem->addChild($option);
  938. }
  939. $mount_elem->addAttribute('size', $mount['size']);
  940. $mount_elem->addAttribute('used', $mount['used']);
  941. $mount_elem->addAttribute('free', $mount['free']);
  942. }
  943. }
  944. // RAID arrays
  945. if (!empty($settings['show']['raid']) && count($info['Raid']) > 0) {
  946. $raid_elem = $xml->addChild('raid');
  947. foreach ($info['Raid'] as $raid) {
  948. $array = $raid_elem->addChild('array');
  949. $active = explode('/', $raid['count']);
  950. $array->addAttribute('device', $raid['device']);
  951. $array->addAttribute('level', $raid['level']);
  952. $array->addAttribute('status', $raid['status']);
  953. $array->addAttribute('size', $raid['size']);
  954. $array->addAttribute('active', $active[1].'/'.$active[0]);
  955. $drives = $array->addChild('drives');
  956. foreach ($raid['drives'] as $drive) {
  957. $drive_elem = $drives->addChild('drive');
  958. $drive_elem->addAttribute('drive', $drive['drive']);
  959. $drive_elem->addAttribute('state', $drive['state']);
  960. }
  961. }
  962. }
  963. // Timestamp
  964. $xml->addChild('timestamp', $info['timestamp']);
  965. // Extensions
  966. if (count($info['extensions']) > 0) {
  967. $extensions = $xml->addChild('extensions');
  968. foreach ($info['extensions'] as $ext) {
  969. $header = false;
  970. if (is_array($ext) && count($ext) > 0) {
  971. $this_ext = $extensions->addChild(string_xml_tag_unfuck($ext['root_title']));
  972. foreach ((array) $ext['rows'] as $i => $row) {
  973. if ($row['type'] == 'header') {
  974. $header = $i;
  975. }
  976. elseif ($row['type'] == 'values') {
  977. $this_row = $this_ext->addChild('row');
  978. if ($header !== false && array_key_exists($header, $ext['rows'])) {
  979. foreach ($ext['rows'][$header]['columns'] as $ri => $rc) {
  980. $this_row->addChild(
  981. string_xml_tag_unfuck($rc),
  982. $ext['rows'][$i]['columns'][$ri]
  983. );
  984. }
  985. }
  986. }
  987. }
  988. }
  989. }
  990. }
  991. // Out it
  992. header('Content-type: text/xml');
  993. echo $xml->asXML();
  994. // Comment which has stats and generator
  995. echo '<!-- Generated in '.round(microtime(true) - TIME_START,2).' seconds by '.AppName.' ('.VERSION.')-->';
  996. }
  997. catch (Exception $e) {
  998. exit('Creation of XML error: '.$e->getMessage());
  999. }
  1000. }
  1001. /**
  1002. * Show it all... in XMLWriter
  1003. * @param array $info the system information
  1004. * @param array $settings linfo settings
  1005. */
  1006. function showInfoXMLWriter($info, $settings) {
  1007. exit ('So far only php\'s simple xml library is supported for XML output. Sorry!');
  1008. }
  1009. /**
  1010. * Show it all... in JSON
  1011. * @param array $info the system information
  1012. * @param array $settings linfo settings
  1013. */
  1014. function showInfoJSON($info, $settings) {
  1015. // Make sure we have JSON
  1016. if (!function_exists('json_encode')) {
  1017. exit('{error:\'JSON extension not loaded\'}');
  1018. return;
  1019. }
  1020. header("Content-Type: application/json");
  1021. // Output buffering, along with compression (if supported)
  1022. if (!isset($settings['compress_content']) || $settings['compress_content']) {
  1023. ob_start('ob_gzhandler');
  1024. }
  1025. // Give it
  1026. echo json_encode($info);
  1027. // Send it all out
  1028. if (!isset($settings['compress_content']) || $settings['compress_content']) {
  1029. ob_end_flush();
  1030. }
  1031. }