Skip to content
258 changes: 258 additions & 0 deletions lib/OperatingSystems/FreeBSD.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,258 @@
<?php

declare(strict_types=1);
/**
* @author Matthew Wener <[email protected]>
*
* @license AGPL-3.0
*
* This code is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License, version 3,
* as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License, version 3,
* along with this program. If not, see <http://www.gnu.org/licenses/>
*
*/

namespace OCA\ServerInfo\OperatingSystems;

/**
* Class FreeBSD
*
* @package OCA\ServerInfo\OperatingSystems
*/
class FreeBSD {

/**
* @return bool
*/
public function supported(): bool {
return false;
}

/**
* Get memory will return a list key => value where all values are in bytes.
* [MemTotal => 0, MemFree => 0, MemAvailable => 0, SwapTotal => 0, SwapFree => 0].
*
* @return array
*/
public function getMemory(): array {
$data = ['MemTotal' => -1, 'MemFree' => -1, 'MemAvailable' => -1, 'SwapTotal' => -1, 'SwapFree' => -1];

try {
$swapinfo = $this->executeCommand('/usr/sbin/swapinfo');
$line = preg_split("/[\s]+/", $swapinfo);

if (count($line) > 3) {
$data['SwapTotal'] = (int)$line[3];
$data['SwapFree'] = $data['SwapTotal'] - (int)$line[2];
}

$meminfo = $this->executeCommand('/sbin/sysctl -n hw.physmem hw.pagesize vm.stats.vm.v_inactive_count vm.stats.vm.v_cache_count vm.stats.vm.v_free_count');

$line = preg_split('/\s+/', trim($meminfo));
if (count($line) > 4) {
$data['MemTotal'] = (int)$line[0];
$data['MemAvailable'] = (int)$line[1] * ((int)$line[2] + (int)$line[3] + (int)$line[4]);
}
} catch (\RuntimeException $e) {
return $data;
}

return $data;
}

/**
* Get name of the processor
*
* @return string
*/
public function getCPUName(): string {
$data = 'Unknown Processor';

try {
$data = $this->executeCommand('/sbin/sysctl -n hw.model');
} catch (\RuntimeException $e) {
return $data;
}
return $data;
}

/**
* @return string
*/
public function getTime() {
$time = '';

try {
$time = $this->executeCommand('date');
} catch (\RuntimeException $e) {
return $time;
}
return $time;
}

/**
* Get the total number of seconds the system has been up or -1 on failure.
*
* @return int
*/
public function getUptime(): int {
$uptime = -1;

try {
$shell_boot = $this->executeCommand('/sbin/sysctl -n kern.boottime');
preg_match("/[\d]+/", $shell_boot, $boottime);
$time = $this->executeCommand('date +%s');
$uptime = (int)$time - (int)$boottime[0];
} catch (\RuntimeException $e) {
return $uptime;
}
return $uptime;
}

/**
* @return string
*/
public function getTimeServers() {
$servers = " ";

try {
$servers = $this->executeCommand('cat /etc/ntp.conf 2>/dev/null');
preg_match_all("/(?<=^pool ).\S*/m", $servers, $matches);
$allservers = implode(' ', $matches[0]);
} catch (\RuntimeException $e) {
return $servers;
}
return $allservers;
}

/**
* @return string
*/
public function getNetworkInfo() {
$result = [];
$result['hostname'] = \gethostname();

try {
$dns = $this->executeCommand('cat /etc/resolv.conf 2>/dev/null');
preg_match_all("/(?<=^nameserver ).\S*/m", $dns, $matches);
$alldns = implode(' ', $matches[0]);
$result['dns'] = $alldns;
$netstat = $this->executeCommand('netstat -rn');
preg_match("/(?<=^default).*\b\d/m", $netstat, $gw);
$result['gateway'] = $gw[0];
} catch (\RuntimeException $e) {
return $result;
}
return $result;
}

/**
* @return string
*/
public function getNetworkInterfaces() {
$result = [];

$ifconfig = $this->executeCommand('/sbin/ifconfig -a');
preg_match_all("/^(?<=(?!\t)).*(?=:)/m", $ifconfig, $interfaces);

foreach ($interfaces[0] as $interface) {
$iface = [];
$iface['interface'] = $interface;
$intface = $this->executeCommand('/sbin/ifconfig ' . $iface['interface']);
preg_match_all("/(?<=inet ).\S*/m", $intface, $ipv4);
preg_match_all("/(?<=inet6 )((.*(?=%))|(.\S*))/m", $intface, $ipv6);
$iface['ipv4'] = implode(' ', $ipv4[0]);
$iface['ipv6'] = implode(' ', $ipv6[0]);

if ($iface['interface'] !== 'lo0') {
preg_match_all("/(?<=ether ).*/m", $intface, $mac);
preg_match("/(?<=status: ).*/m", $intface, $status);
preg_match("/(?<=\().*(?=b)/m", $intface, $speed);
preg_match("/(?<=\<).*(?=-)/m", $intface, $duplex);

$iface['mac'] = implode(' ', $mac[0]);
$iface['status'] = $status[0];
$iface['speed'] = $speed[0];

if ($iface['speed'] !== '') {
$iface['speed'] = $iface['speed'];
} else {
$iface['speed'] = 'unknown';
}

if ($duplex[0] !== '') {
$iface['duplex'] = 'Duplex: ' . $duplex[0];
} else {
$iface['duplex'] = '';
}
} else {
$iface['status'] = 'active';
$iface['speed'] = 'unknown';
$iface['duplex'] = '';
}
$result[] = $iface;
}

return $result;
}

/**
* Get diskInfo will return a list of disks. Used and Available in bytes.
*
* [
* [device => /dev/mapper/homestead--vg-root, fs => ext4, used => 6205468, available => 47321220, percent => 12%, mount => /]
* ]
*
* @return array
*/
public function getDiskInfo(): array {
$data = [];

try {
$disks = $this->executeCommand('df -TP');
} catch (\RuntimeException $e) {
return $data;
}

$matches = [];
$pattern = '/^(?<Filesystem>[\w\/-]+)\s*(?<Type>\w+)\s*(?<Blocks>\d+)\s*(?<Used>\d+)\s*(?<Available>\d+)\s*(?<Capacity>\d+%)\s*(?<Mounted>[\w\/-]+)$/m';

$result = preg_match_all($pattern, $disks, $matches);
if ($result === 0 || $result === false) {
return $data;
}

foreach ($matches['Filesystem'] as $i => $filesystem) {
if (in_array($matches['Type'][$i], ['tmpfs', 'devtmpfs'], false)) {
continue;
}

$data[] = [
'device' => $filesystem,
'fs' => $matches['Type'][$i],
'used' => (int)$matches['Used'][$i] * 1024,
'available' => (int)$matches['Available'][$i] * 1024,
'percent' => $matches['Capacity'][$i],
'mount' => $matches['Mounted'][$i],
];
}

return $data;
}

protected function executeCommand(string $command): string {
$output = @shell_exec(escapeshellcmd($command));
if ($output === null || $output === '') {
throw new \RuntimeException('No output for command: "' . $command . '"');
}
return $output;
}
}
7 changes: 6 additions & 1 deletion lib/Os.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@

use bantu\IniGetWrapper\IniGetWrapper;
use OCA\ServerInfo\OperatingSystems\DefaultOs;
use OCA\ServerInfo\OperatingSystems\FreeBSD;
use OCP\Http\Client\IClientService;
use OCP\IConfig;
use OCP\IDBConnection;
Expand Down Expand Up @@ -66,7 +67,11 @@ public function __construct(IClientService $clientService,
$this->connection = $connection;
$this->phpIni = $phpIni;
$this->l = $l;
$this->backend = new DefaultOs();
if (PHP_OS === 'FreeBSD') {
$this->backend = new FreeBSD();
} else {
$this->backend = new DefaultOs();
}
}

/**
Expand Down