PluginProbe
Media Cloud Sync / 1.4.2
Media Cloud Sync v1.4.2
1.4.2 1.4.1 1.4.0 1.3.12 1.3.11 1.3.10 trunk 1.0.0 1.0.1 1.0.2 1.0.3 1.1.0 1.1.1 1.2.0 1.2.10 1.2.11 1.2.12 1.2.13 1.2.2 1.2.3 1.2.4 1.2.5 1.2.6 1.2.7 1.2.8 All 36 releases
media-cloud-sync / includes / sdk / google / ramsey / uuid / src / Provider / Node / SystemNodeProvider.php

SystemNodeProvider.php in Media Cloud Sync 1.4.2, at includes/sdk/google/ramsey/uuid/src/Provider/Node/SystemNodeProvider.php

148 lines 4.7 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 /**
4 * This file is part of the ramsey/uuid library
5 *
6 * For the full copyright and license information, please view the LICENSE
7 * file that was distributed with this source code.
8 *
9 * @copyright Copyright (c) Ben Ramsey <[email protected]>
10 * @license http://opensource.org/licenses/MIT MIT
11 */
12 declare (strict_types=1);
13 namespace Dudlewebs\WPMCS\GCP\Ramsey\Uuid\Provider\Node;
14
15 use Dudlewebs\WPMCS\GCP\Ramsey\Uuid\Exception\NodeException;
16 use Dudlewebs\WPMCS\GCP\Ramsey\Uuid\Provider\NodeProviderInterface;
17 use Dudlewebs\WPMCS\GCP\Ramsey\Uuid\Type\Hexadecimal;
18 use function array_filter;
19 use function array_map;
20 use function array_walk;
21 use function count;
22 use function ob_get_clean;
23 use function ob_start;
24 use function preg_match;
25 use function preg_match_all;
26 use function reset;
27 use function str_contains;
28 use function str_replace;
29 use function strtolower;
30 use function strtoupper;
31 use function substr;
32 use const GLOB_NOSORT;
33 use const PREG_PATTERN_ORDER;
34 /**
35 * SystemNodeProvider retrieves the system node ID, if possible
36 *
37 * The system node ID, or host ID, is often the same as the MAC address for a network interface on the host.
38 */
39 class SystemNodeProvider implements NodeProviderInterface
40 {
41 /**
42 * Pattern to match nodes in `ifconfig` and `ipconfig` output.
43 */
44 private const IFCONFIG_PATTERN = '/[^:]([0-9a-f]{2}([:-])[0-9a-f]{2}(\\2[0-9a-f]{2}){4})[^:]/i';
45 /**
46 * Pattern to match nodes in sysfs stream output.
47 */
48 private const SYSFS_PATTERN = '/^([0-9a-f]{2}:){5}[0-9a-f]{2}$/i';
49 public function getNode() : Hexadecimal
50 {
51 $node = $this->getNodeFromSystem();
52 if ($node === '') {
53 throw new NodeException('Unable to fetch a node for this system');
54 }
55 return new Hexadecimal($node);
56 }
57 /**
58 * Returns the system node if found
59 */
60 protected function getNodeFromSystem() : string
61 {
62 /** @var string | null $node */
63 static $node = null;
64 if ($node !== null) {
65 return $node;
66 }
67 // First, try a Linux-specific approach.
68 $node = $this->getSysfs();
69 if ($node === '') {
70 // Search ifconfig output for MAC addresses & return the first one.
71 $node = $this->getIfconfig();
72 }
73 $node = str_replace([':', '-'], '', $node);
74 return $node;
75 }
76 /**
77 * Returns the network interface configuration for the system
78 *
79 * @codeCoverageIgnore
80 */
81 protected function getIfconfig() : string
82 {
83 if (str_contains(strtolower((string) \ini_get('disable_functions')), 'passthru')) {
84 return '';
85 }
86 /** @var string $phpOs */
87 $phpOs = \constant('PHP_OS');
88 ob_start();
89 switch (strtoupper(substr($phpOs, 0, 3))) {
90 case 'WIN':
91 \passthru('ipconfig /all 2>&1');
92 break;
93 case 'DAR':
94 \passthru('ifconfig 2>&1');
95 break;
96 case 'FRE':
97 \passthru('netstat -i -f link 2>&1');
98 break;
99 case 'LIN':
100 default:
101 \passthru('netstat -ie 2>&1');
102 break;
103 }
104 $ifconfig = (string) ob_get_clean();
105 if (preg_match_all(self::IFCONFIG_PATTERN, $ifconfig, $matches, PREG_PATTERN_ORDER)) {
106 foreach ($matches[1] as $iface) {
107 if ($iface !== '00:00:00:00:00:00' && $iface !== '00-00-00-00-00-00') {
108 return $iface;
109 }
110 }
111 }
112 return '';
113 }
114 /**
115 * Returns MAC address from the first system interface via the sysfs interface
116 */
117 protected function getSysfs() : string
118 {
119 /** @var string $phpOs */
120 $phpOs = \constant('PHP_OS');
121 if (strtoupper($phpOs) !== 'LINUX') {
122 return '';
123 }
124 $addressPaths = \glob('/sys/class/net/*/address', GLOB_NOSORT);
125 if ($addressPaths === \false || count($addressPaths) === 0) {
126 return '';
127 }
128 /** @var array<array-key, string> $macs */
129 $macs = [];
130 array_walk($addressPaths, function (string $addressPath) use(&$macs) : void {
131 if (\is_readable($addressPath)) {
132 $macs[] = \file_get_contents($addressPath);
133 }
134 });
135 /** @var callable $trim */
136 $trim = 'trim';
137 $macs = array_map($trim, $macs);
138 // Remove invalid entries.
139 $macs = array_filter($macs, function (mixed $address) : bool {
140 \assert(\is_string($address));
141 return $address !== '00:00:00:00:00:00' && preg_match(self::SYSFS_PATTERN, $address);
142 });
143 /** @var bool | string $mac */
144 $mac = reset($macs);
145 return (string) $mac;
146 }
147 }
148