diff options
author | Simon Rettberg | 2021-10-18 16:09:03 +0200 |
---|---|---|
committer | Simon Rettberg | 2021-10-18 16:09:03 +0200 |
commit | d2edc57cda4da452013631beeb10c758df12ee9c (patch) | |
tree | ba9baceaaba13b96d027ac1495febee0847a7472 | |
parent | [statistics] lang (diff) | |
download | slx-admin-d2edc57cda4da452013631beeb10c758df12ee9c.tar.gz slx-admin-d2edc57cda4da452013631beeb10c758df12ee9c.tar.xz slx-admin-d2edc57cda4da452013631beeb10c758df12ee9c.zip |
[statistica] Query support etc.
12 files changed, 142 insertions, 122 deletions
diff --git a/modules-available/passthrough/page.inc.php b/modules-available/passthrough/page.inc.php index 3ab0696e..7dcc8215 100644 --- a/modules-available/passthrough/page.inc.php +++ b/modules-available/passthrough/page.inc.php @@ -68,6 +68,7 @@ class Page_Passthrough extends Page $q = new HardwareQuery(HardwareInfo::PCI_DEVICE, null, false); $q->addGlobalColumn('vendor'); $q->addGlobalColumn('device'); + $q->addGlobalColumn('rev'); $q->addGlobalColumn('class'); $q->addGlobalColumn('@PASSTHROUGH'); $rows = []; @@ -110,10 +111,11 @@ class Page_Passthrough extends Page $missing[$row['vendor'] . ':' . $row['device']] = true; } } - Render::addTemplate('hardware-list', [ - 'list' => $finalRows, - 'missing_ids' => json_encode(array_keys($missing)), - ]); + Render::addTemplate('hardware-list', ['list' => $finalRows]); + if (!empty($missing)) { + Render::addTemplate('js-pciquery', + ['missing_ids' => json_encode(array_keys($missing))], 'statistics'); + } } /* diff --git a/modules-available/passthrough/templates/hardware-list.html b/modules-available/passthrough/templates/hardware-list.html index d331acb5..4bff0a39 100644 --- a/modules-available/passthrough/templates/hardware-list.html +++ b/modules-available/passthrough/templates/hardware-list.html @@ -18,7 +18,7 @@ </td> {{/class_name}} {{^class_name}} - <td>{{vendor}}:{{device}}</td> + <td>{{vendor}}:{{device}} [{{rev}}]</td> <td> <table class="slx-ellipsis"> <tr> @@ -101,25 +101,5 @@ $(this).append($('<option>').attr('value', gid).text(gid + ' (' + title + ')')); }); }); - var missing = {{{missing_ids}}}; - var doQuery = function() { - if (missing && missing.length > 0) { - $.ajax({ - url: '?do=statistics', dataType: "json", method: "POST", data: { - token: TOKEN, - action: 'json-lookup', - list: missing.splice(0, 10) // Query 10 at a time max - } - }).done(function (data) { - if (!data) - return; - for (var k in data) { - $('.query-' + k.replace(':', '-')).text(data[k]); - } - doQuery(); - }); - } - } - doQuery(); }); </script>
\ No newline at end of file diff --git a/modules-available/serversetup-bwlp-ipxe/inc/localboot.inc.php b/modules-available/serversetup-bwlp-ipxe/inc/localboot.inc.php index d4dd9516..2ce098e9 100644 --- a/modules-available/serversetup-bwlp-ipxe/inc/localboot.inc.php +++ b/modules-available/serversetup-bwlp-ipxe/inc/localboot.inc.php @@ -17,30 +17,38 @@ chain -ar /tftp/sl-bios/lpxelinux.0', 'EFI' => [ 'EXIT' => 'set slx_exit 1 || exit 1', + 'SANBOOT' => 'imgfree || +console || +set filename \EFI\Boot\bootx64.efi || +set i:int32 0 || +:blubber +sanboot --no-describe --drive ${i} --filename ${filename} || +inc i +iseq ${i} 10 || goto blubber', 'COMBOOT' => 'set netX/209:string localboot.cfg || set netX/210:string http://${serverip}/tftp/sl-efi64/ || chain -ar /tftp/sl-efi64/syslinux.efi', ], ]; - public static function getDefault() + public static function getDefault(): array { - $ret = explode(',', Property::get(self::PROPERTY_KEY, 'SANBOOT,EXIT')); + $ret = explode(',', Property::get(self::PROPERTY_KEY, 'SANBOOT,SANBOOT')); if (empty($ret)) { - $ret = ['SANBOOT', 'EXIT']; + $ret = ['SANBOOT', 'SANBOOT']; } elseif (count($ret) < 2) { - $ret[] = 'EXIT'; + $ret[] = 'SANBOOT'; } - if (null === self::BOOT_METHODS['PCBIOS'][$ret[0]]) { + if (!isset(self::BOOT_METHODS['PCBIOS'][$ret[0]])) { $ret[0] = 'SANBOOT'; } - if (null === self::BOOT_METHODS['EFI'][$ret[1]]) { - $ret[1] = 'EXIT'; + if (!isset(self::BOOT_METHODS['EFI'][$ret[1]])) { + $ret[1] = 'SANBOOT'; } return ['PCBIOS' => $ret[0], 'EFI' => $ret[1]]; } - public static function setDefault($pcbios, $efi) + public static function setDefault(string $pcbios, string $efi) { Property::set(self::PROPERTY_KEY, "$pcbios,$efi"); } diff --git a/modules-available/statistics/inc/hardwareinfo.inc.php b/modules-available/statistics/inc/hardwareinfo.inc.php index 6a6c74cd..586b8124 100644 --- a/modules-available/statistics/inc/hardwareinfo.inc.php +++ b/modules-available/statistics/inc/hardwareinfo.inc.php @@ -54,7 +54,7 @@ class HardwareInfo $gvt = true; } else { $passthrough[$row['vendor'] . ':' . $row['device']] = 1; - error_log('Passthouorgh: ' . $row['vendor'] . ':' . $row['device']); + //error_log('Passthouorgh: ' . $row['vendor'] . ':' . $row['device']); $slots[preg_replace('/\.[0-9]+$/', '', $row['slot'])] = 1; } } @@ -64,14 +64,14 @@ class HardwareInfo } if (!empty($passthrough)) { foreach (array_keys($slots) as $slot) { - error_log('Querying slot ' . $slot); + //error_log('Querying slot ' . $slot); $hw = new HardwareQuery(self::PCI_DEVICE, $best['machineuuid'], true); $hw->addWhere(false, 'slot', 'LIKE', $slot . '.%'); $hw->addGlobalColumn('vendor'); $hw->addGlobalColumn('device'); foreach ($hw->query() as $row) { $passthrough[$row['vendor'] . ':' . $row['device']] = 1; - error_log('Extra PT: ' . $row['vendor'] . ':' . $row['device']); + //error_log('Extra PT: ' . $row['vendor'] . ':' . $row['device']); } } $kcl .= ' vfio-pci.ids=' . implode(',', array_keys($passthrough)); diff --git a/modules-available/statistics/inc/hardwareparserlegacy.inc.php b/modules-available/statistics/inc/hardwareparserlegacy.inc.php index 4d8a8502..277f6d4a 100644 --- a/modules-available/statistics/inc/hardwareparserlegacy.inc.php +++ b/modules-available/statistics/inc/hardwareparserlegacy.inc.php @@ -134,47 +134,10 @@ class HardwareParserLegacy $row['hdds'] = &$hdds; } - public static function parsePci(&$pci1, &$pci2, $data) + public static function parsePci(string $data): array { - preg_match_all('/[a-f0-9:.]{7}\s+"(Class\s*)?(?<class>[a-f0-9]{4})"\s+"(?<ven>[a-f0-9]{4})"\s+"(?<dev>[a-f0-9]{4})"/is', $data, $out, PREG_SET_ORDER); - $pci = array(); - foreach ($out as $entry) { - if (!isset($pci[$entry['class']])) { - $class = 'c.' . $entry['class']; - $res = PciId::getPciId('CLASS', $class); - if ($res === false) { - $pci[$entry['class']]['lookupClass'] = 'do-lookup'; - $pci[$entry['class']]['class'] = $class; - } else { - $pci[$entry['class']]['class'] = $res; - } - } - $new = array( - 'ven' => $entry['ven'], - 'dev' => $entry['ven'] . ':' . $entry['dev'], - ); - $res = PciId::getPciId('VENDOR', $new['ven']); - if ($res === false) { - $new['lookupVen'] = 'do-lookup'; - } else { - $new['ven'] = $res; - } - $res = PciId::getPciId('DEVICE', $new['dev']); - if ($res === false) { - $new['lookupDev'] = 'do-lookup'; - } else { - $new['dev'] = $res . ' (' . $new['dev'] . ')'; - } - $pci[$entry['class']]['entries'][] = $new; - } - ksort($pci); - foreach ($pci as $class => $entry) { - if ($class === '0300' || $class === '0200' || $class === '0403') { - $pci1[] = $entry; - } else { - $pci2[] = $entry; - } - } + preg_match_all('/[a-f0-9:.]{7}\s+"(Class\s*)?(?<class>[a-f0-9]{4})"\s+"(?<vendor>[a-f0-9]{4})"\s+"(?<device>[a-f0-9]{4})"/is', $data, $out, PREG_SET_ORDER); + return $out; } public static function parseSmartctl(&$hdds, $data) diff --git a/modules-available/statistics/inc/pciid.inc.php b/modules-available/statistics/inc/pciid.inc.php index 65edf570..38a2c56d 100644 --- a/modules-available/statistics/inc/pciid.inc.php +++ b/modules-available/statistics/inc/pciid.inc.php @@ -17,20 +17,36 @@ class PciId public static function getPciId(string $cat, string $id, bool $dnsQuery = false) { static $cache = []; - if ($cat === self::DEVCLASS && $id[1] !== '.') { - $id = 'c.' . $id; + if ($cat === self::DEVCLASS && $id[1] === '.') { + $id = substr($id, 2); } if ($cat === self::AUTO) { - if (preg_match('/^([a-f0-9]{4}):([a-f0-9]{4})$/', $id, $out)) { + if (preg_match('/^([a-f0-9]{4})[:._-]?([a-f0-9]{4})$/', $id, $out)) { $cat = 'DEVICE'; - } elseif (preg_match('/^([a-f0-9]{4})$/', $id, $out)) { + $host = $out[2] . '.' . $out[1]; + $id = $out[1] . ':' . $out[2]; + } elseif (preg_match('/^[a-f0-9]{4}$/', $id)) { $cat = 'VENDOR'; - } elseif (preg_match('/^c\.([a-f0-9]{2})([a-f0-9]{2})$/', $id, $out)) { + $host = $id; + } elseif (preg_match('/^c[.-]([a-f0-9]{2})([a-f0-9]{2})$/', $id)) { $cat = 'CLASS'; + $host = $out[2] . '.' . $out[1] . '.c'; + $id = substr($id, 2); } else { error_log('Invalid PCIID lookup format: ' . $id); return false; } + } elseif ($cat === self::DEVICE && preg_match('/^([a-f0-9]{4})[:._-]?([a-f0-9]{4})$/', $id, $out)) { + $host = $out[2] . '.' . $out[1]; + $id = $out[1] . ':' . $out[2]; + } elseif ($cat === self::VENDOR && preg_match('/^([a-f0-9]{4})$/', $id)) { + $host = $id; + } elseif ($cat === self::DEVCLASS && preg_match('/^(?:c[.-])?([a-f0-9]{2})([a-f0-9]{2})$/', $id, $out)) { + $host = $out[2] . '.' . $out[1] . '.c'; + $id = 'c.' . $out[1] . $out[2]; + } else { + error_log("getPciId called with unknown format: ($cat) ($id)"); + return false; } $key = $cat . '-' . $id; if (isset($cache[$key])) @@ -43,16 +59,6 @@ class PciId if (!$dnsQuery) return false; // Unknown, query - if ($cat === self::DEVICE && preg_match('/^([a-f0-9]{4}):([a-f0-9]{4})$/', $id, $out)) { - $host = $out[2] . '.' . $out[1]; - } elseif ($cat === self::VENDOR && preg_match('/^([a-f0-9]{4})$/', $id, $out)) { - $host = $out[1]; - } elseif ($cat === self::DEVCLASS && preg_match('/^c\.([a-f0-9]{2})([a-f0-9]{2})$/', $id, $out)) { - $host = $out[2] . '.' . $out[1] . '.c'; - } else { - error_log("getPciId called with unknown format: ($cat) ($id)"); - return false; - } $res = dns_get_record($host . '.pci.id.ucw.cz', DNS_TXT); if (!is_array($res)) return false; diff --git a/modules-available/statistics/lang/de/template-tags.json b/modules-available/statistics/lang/de/template-tags.json index b9b3a563..d7013da6 100644 --- a/modules-available/statistics/lang/de/template-tags.json +++ b/modules-available/statistics/lang/de/template-tags.json @@ -24,6 +24,7 @@ "lang_eventType": "Typ", "lang_firstSeen": "Erste Aktivit\u00e4t", "lang_free": "frei", + "lang_fullInfo": "Alle Werte", "lang_gbRam": "RAM", "lang_hardwareSummary": "Hardware", "lang_hasNotes": "Zu diesem Rechner wurden Notizen hinterlegt", diff --git a/modules-available/statistics/lang/en/template-tags.json b/modules-available/statistics/lang/en/template-tags.json index 3fcbc049..43b6aeea 100644 --- a/modules-available/statistics/lang/en/template-tags.json +++ b/modules-available/statistics/lang/en/template-tags.json @@ -24,6 +24,7 @@ "lang_eventType": "Type", "lang_firstSeen": "First seen", "lang_free": "free", + "lang_fullInfo": "All values", "lang_gbRam": "RAM", "lang_hardwareSummary": "Hardware", "lang_hasNotes": "Notes have been added to this client", diff --git a/modules-available/statistics/pages/machine.inc.php b/modules-available/statistics/pages/machine.inc.php index fdb04023..62abc8d2 100644 --- a/modules-available/statistics/pages/machine.inc.php +++ b/modules-available/statistics/pages/machine.inc.php @@ -61,33 +61,64 @@ class SubPage Message::addError('unknown-machine', $uuid); return; } + if (Module::isAvailable('locations') && !Location::isLeaf($client['locationid'])) { + $client['hasroomplan'] = false; + } + User::assertPermission('machine.view-details', (int)$client['locationid']); + // Hack: Get raw collected data + if (Request::get('raw', false)) { + Header('Content-Type: text/plain; charset=utf-8'); + die($client['data']); + } // Parse data $hdds = array(); if ($client['data'][0] === '{') { $json = json_decode($client['data'], true); if (is_array($json)) { $client += self::parseJson($uuid, $json); - $hdds['hdds'] = self::parseJsonHdd($uuid); + $hdds['hdds'] = self::queryHddData($uuid); } } else { self::parseLegacy($client, $hdds); } unset($client['data']); // Get rid of configured speed, if equal to maximum speed - foreach ($client['ram'] as &$ram) { - if (isset($ram['Configured Memory Speed']) && $ram['Configured Memory Speed'] === $ram['Speed']) { - unset($ram['Configured Memory Speed']); + foreach ($client['ram'] as &$item) { + if (isset($item['Configured Memory Speed']) && $item['Configured Memory Speed'] === $item['Speed']) { + unset($item['Configured Memory Speed']); } } - if (Module::isAvailable('locations') && !Location::isLeaf($client['locationid'])) { - $client['hasroomplan'] = false; - } - User::assertPermission('machine.view-details', (int)$client['locationid']); - // Hack: Get raw collected data - if (Request::get('raw', false)) { - Header('Content-Type: text/plain; charset=utf-8'); - die($client['data']); + unset($item); + $client['lspci1'] = $client['lspci2'] = []; + foreach ($client['lspci'] as $item) { + $item['vendor_s'] = PciId::getPciId(PciId::VENDOR, $item['vendor']); + $item['device_s'] = PciId::getPciId(PciId::DEVICE, $item['vendor'] . $item['device']); + if ($item['vendor_s'] === false) { + $pciLookup[$item['vendor']] = true; + } + if ($item['device_s'] === false) { + $pciLookup[$item['vendor'] . ':' . $item['device']] = true; + } + $class = $item['class']; + if ($class === '0300' || $class === '0200' || $class === '0403') { + $dst =& $client['lspci1']; + } else { + $dst =& $client['lspci2']; + } + if (!isset($dst[$class])) { + $dst[$class] = [ + 'class' => $class, + 'class_s' => PciId::getPciId(PciId::DEVCLASS, $class, true), + 'entries' => [], + ]; + } + $dst[$class]['entries'][] = $item; } + unset($dst, $client['lspci']); + ksort($client['lspci1']); + ksort($client['lspci2']); + $client['lspci1'] = array_values($client['lspci1']); + $client['lspci2'] = array_values($client['lspci2']); // Runmode if (Module::isAvailable('runmode')) { $data = RunMode::getRunMode($uuid, RunMode::DATA_STRINGS); @@ -211,6 +242,10 @@ class SubPage Permission::addGlobalTags($client['perms'], null, ['hardware.projectors.edit', 'hardware.projectors.view']); // Throw output at user Render::addTemplate('machine-main', $client); + if (!empty($pciLookup)) { + Render::addTemplate('js-pciquery', + ['missing_ids' => json_encode(array_keys($pciLookup))]); + } // Sessions $NOW = time(); $cutoff = $NOW - 86400 * 7; @@ -366,8 +401,7 @@ class SubPage HardwareParserLegacy::parseHdd($hdds, $section[2]); } if ($section[1] === 'PCI ID') { - $client['lspci1'] = $client['lspci2'] = array(); - HardwareParserLegacy::parsePci($client['lspci1'], $client['lspci2'], $section[2]); + $client['lspci'] = HardwareParserLegacy::parsePci($section[2]); } if (isset($hdds['hdds']) && $section[1] === 'smartctl') { // This currently requires that the partition table section comes first... @@ -381,6 +415,7 @@ class SubPage { $return = [ 'cpu' => $json['cpu'] ?? [], + 'lspci' => $json['lspci'] ?? [], 'ram' => array_map(function($item) { return HardwareParser::prepareDmiProperties($item); }, HardwareParser::getDmiHandles($json, 17)), @@ -407,7 +442,7 @@ class SubPage return $return; } - private static function parseJsonHdd(string $uuid): array + private static function queryHddData(string $uuid): array { $hdds = []; $ret = Database::simpleQuery("SELECT mp.`machinehwid`, mp.`prop`, mp.`value`, mp.`numeric` diff --git a/modules-available/statistics/templates/hints-ram-underclocked.html b/modules-available/statistics/templates/hints-ram-underclocked.html index e1f19c4f..fffd3322 100644 --- a/modules-available/statistics/templates/hints-ram-underclocked.html +++ b/modules-available/statistics/templates/hints-ram-underclocked.html @@ -10,7 +10,7 @@ <th>{lang_speedCurrent}}</th> <th>{{lang_speedDesign}}</th> <th>{{lang_manufacturer}}</th> - <th>{{lang_serialNumber}}</th> + <th>{{lang_serialNo}}</th> </tr> </thead> <tbody> diff --git a/modules-available/statistics/templates/js-pciquery.html b/modules-available/statistics/templates/js-pciquery.html new file mode 100644 index 00000000..5d4df867 --- /dev/null +++ b/modules-available/statistics/templates/js-pciquery.html @@ -0,0 +1,24 @@ +<script> + document.addEventListener('DOMContentLoaded', function() { + var missing = {{{missing_ids}}}; + var doQuery = function() { + if (missing && missing.length > 0) { + $.ajax({ + url: '?do=statistics', dataType: "json", method: "POST", data: { + token: TOKEN, + action: 'json-lookup', + list: missing.splice(0, 10) // Query 10 at a time max + } + }).done(function (data) { + if (!data) + return; + for (var k in data) { + $('.query-' + k.replace(':', '-')).text(data[k]); + } + doQuery(); + }); + } + } + doQuery(); + }); +</script>
\ No newline at end of file diff --git a/modules-available/statistics/templates/machine-main.html b/modules-available/statistics/templates/machine-main.html index 0509a646..71df723d 100644 --- a/modules-available/statistics/templates/machine-main.html +++ b/modules-available/statistics/templates/machine-main.html @@ -297,7 +297,7 @@ <td>{{lang_slot}}</td> <td></td> <td>{{lang_speed}}</td> - <td>{{lang_vendor}}</td> + <td>{{lang_manufacturer}}</td> <td>{{lang_serialNo}}</td> </tr> </thead> @@ -392,16 +392,26 @@ </table> <h4>{{lang_devices}}</h4> {{#lspci1}} - <div><span class="{{lookupClass}}">{{class}}</span></div> + <div><span>{{class_s}}</span></div> {{#entries}} - <div class="small"> └ <span class="{{lookupVen}}">{{ven}}</span> <span class="{{lookupDev}}">{{dev}}</span></div> + <div class="small"> +  └ + <span{{^vendor_s}} class="query-{{vendor}}"{{/vendor_s}}>{{vendor_s}}</span> + <span{{^device_s}} class="query-{{vendor}}-{{device}}"{{/device_s}}>{{device_s}}</span> + <span>[{{vendor}}:{{device}}]</span> + </div> {{/entries}} {{/lspci1}} <div id="lspci" class="collapse"> {{#lspci2}} - <div><span class="{{lookupClass}}">{{class}}</span></div> + <div><span>{{class_s}}</span></div> {{#entries}} - <div class="small"> └ <span class="{{lookupVen}}">{{ven}}</span> <span class="{{lookupDev}}">{{dev}}</span></div> + <div class="small"> +  └ + <span{{^vendor_s}} class="query-{{vendor}}"{{/vendor_s}}>{{vendor_s}}</span> + <span{{^device_s}} class="query-{{vendor}}-{{device}}"{{/device_s}}>{{device_s}}</span> + <span>[{{vendor}}:{{device}}]</span> + </div> {{/entries}} {{/lspci2}} </div> @@ -410,13 +420,3 @@ </div> </div> </div> -<script type="application/javascript"><!-- -document.addEventListener("DOMContentLoaded", function () { - $('span.do-lookup').each(function () { - $(this).load('?do=statistics&lookup=' + $(this).text()); - }); - {{#biosurl}} - $('#bios-panel').load('{{{biosurl}}}'); - {{/biosurl}} -}, false); -// --></script> |