2018-08-10 08:59:46 +02:00
|
|
|
#!/usr/bin/env python
|
2017-06-20 16:38:38 +02:00
|
|
|
# This Module collects the vendor- and device ids for USB- and PCI(e)-devices and currently loaded kernel modules.
|
|
|
|
DOCUMENTATION = '''
|
2017-06-20 16:19:08 +02:00
|
|
|
---
|
|
|
|
module: hardware_facts
|
|
|
|
short_description: collects facts for kernel modules, usb and pci devices
|
|
|
|
description:
|
|
|
|
- This Module collects the vendor- and device ids for USB- and PCI(e)-devices and
|
|
|
|
currently loaded kernel modules.
|
|
|
|
options:
|
|
|
|
usb:
|
|
|
|
required: False
|
|
|
|
default: True
|
|
|
|
description:
|
|
|
|
- return a list of vendor- and device ids for usb devices in '04x:04x' notation
|
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
pci:
|
|
|
|
required: False
|
|
|
|
default: True
|
|
|
|
description:
|
|
|
|
- return a list of vendor- and device ids for pci devices in '04x:04x' notation
|
|
|
|
|
|
|
|
modules:
|
|
|
|
required: False
|
|
|
|
default: True
|
|
|
|
description:
|
|
|
|
- return a list of currently loaded kernel modules
|
|
|
|
|
|
|
|
gpus:
|
|
|
|
required: False
|
|
|
|
default: True
|
|
|
|
description:
|
|
|
|
- return a list of devices of the pci gpu class (0x030000)
|
2017-11-20 09:20:30 +01:00
|
|
|
|
|
|
|
acpi_power_modes:
|
|
|
|
required: False
|
|
|
|
default: True
|
|
|
|
description:
|
|
|
|
- return a list of supported acpi power saving modes
|
2017-06-20 16:38:38 +02:00
|
|
|
notes:
|
|
|
|
- requres python-pyusb and python-kmodpy
|
|
|
|
requirements: [ ]
|
|
|
|
author: "Alexander Grothe <seahawk1986@gmx.de>"
|
|
|
|
'''
|
|
|
|
|
|
|
|
EXAMPLES = '''
|
|
|
|
- name: get information about usb and pci hardware and loaded kernel modules
|
|
|
|
hardware_facts:
|
|
|
|
usb: True
|
|
|
|
pci: True
|
|
|
|
modules: True
|
2017-11-20 09:20:30 +01:00
|
|
|
acpi_power_modes: True
|
2017-06-20 16:38:38 +02:00
|
|
|
- debug:
|
|
|
|
var: usb
|
2017-11-21 11:30:03 +01:00
|
|
|
- debug:
|
2017-06-20 16:38:38 +02:00
|
|
|
var: pci
|
2017-11-21 11:30:03 +01:00
|
|
|
- debug:
|
2017-06-20 16:38:38 +02:00
|
|
|
var: modules
|
2017-11-21 11:30:03 +01:00
|
|
|
- debug:
|
2017-06-20 16:38:38 +02:00
|
|
|
var: gpus
|
|
|
|
'''
|
|
|
|
|
|
|
|
import glob
|
|
|
|
import json
|
|
|
|
import os
|
|
|
|
import sys
|
|
|
|
import usb.core
|
|
|
|
from collections import namedtuple
|
2018-04-20 11:47:18 +02:00
|
|
|
from itertools import chain
|
2017-06-20 16:38:38 +02:00
|
|
|
|
|
|
|
import kmodpy
|
|
|
|
from ansible.module_utils.basic import *
|
|
|
|
|
|
|
|
|
|
|
|
PCIDevice = namedtuple("PCIDevice", 'idVendor idProduct idClass pciPath')
|
|
|
|
|
2017-07-16 08:03:50 +02:00
|
|
|
vendor_dict = {
|
|
|
|
0x10de: 'nvidia',
|
|
|
|
0x8086: 'intel',
|
|
|
|
0x1002: 'amd',
|
|
|
|
0x80ee: 'virtualbox',
|
|
|
|
}
|
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
def get_pci_devices():
|
2018-04-20 11:47:18 +02:00
|
|
|
for device in chain(glob.glob('/sys/devices/pci*/*:*:*/'), glob.glob('/sys/devices/pci*/*:*:*/*:*:*/')):
|
2017-07-16 08:03:50 +02:00
|
|
|
try:
|
|
|
|
with open(os.path.join(device, 'device')) as d:
|
|
|
|
product_id = int(d.read().strip(), 16)
|
|
|
|
with open(os.path.join(device, 'vendor')) as d:
|
|
|
|
vendor_id = int(d.read().strip(), 16)
|
|
|
|
with open(os.path.join(device, 'class')) as d:
|
|
|
|
class_id = int(d.read().strip(), 16)
|
|
|
|
yield PCIDevice(idVendor=vendor_id, idProduct=product_id, idClass=class_id, pciPath=device)
|
|
|
|
except IOError:
|
|
|
|
pass
|
2017-06-20 16:38:38 +02:00
|
|
|
|
|
|
|
def format_device_list(iterator):
|
|
|
|
return ["{:04x}:{:04x}".format(d.idVendor, d.idProduct) for d in iterator]
|
|
|
|
|
|
|
|
def format_gpu_device_list(iterator):
|
|
|
|
def get_entries(iterator):
|
|
|
|
for d in iterator:
|
|
|
|
if d.idClass == 0x030000:
|
2017-07-16 08:16:55 +02:00
|
|
|
yield {"VendorName": vendor_dict.get(d.idVendor, "unknown"),
|
|
|
|
"VendorID": d.idVendor, "ProductID": d.idProduct}
|
2017-06-20 16:38:38 +02:00
|
|
|
return [entry for entry in get_entries(iterator)]
|
|
|
|
|
2017-11-20 09:20:30 +01:00
|
|
|
def list_acpi_power_modes():
|
|
|
|
acpi_power_modes = []
|
|
|
|
try:
|
|
|
|
with open('/sys/power/state') as f:
|
|
|
|
acpi_power_modes = [l for l in f.readline().split()]
|
|
|
|
except IOError:
|
|
|
|
pass
|
|
|
|
return acpi_power_modes
|
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
arg_specs = {
|
|
|
|
'usb': dict(default=True, type='bool', required=False),
|
|
|
|
'pci': dict(default=True, type='bool', required=False),
|
|
|
|
'modules': dict(default=True, type='bool', required=False),
|
|
|
|
'gpus': dict(default=True, type='bool', required=False),
|
2017-11-20 09:20:30 +01:00
|
|
|
'acpi_power_modes': dict(default=True, type='bool', required=False),
|
2017-06-20 16:38:38 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
def main():
|
|
|
|
module = AnsibleModule(argument_spec=arg_specs, supports_check_mode=True,)
|
|
|
|
collect_usb = module.params['usb']
|
|
|
|
collect_pci = module.params['pci']
|
|
|
|
collect_modules = module.params['modules']
|
|
|
|
collect_gpus = module.params['gpus']
|
2017-11-20 09:20:30 +01:00
|
|
|
collect_acpi_power_modes = module.params['acpi_power_modes']
|
|
|
|
|
|
|
|
usb_devices = []
|
|
|
|
pci_devices = []
|
|
|
|
modules = []
|
|
|
|
gpus = []
|
2017-11-22 09:24:33 +01:00
|
|
|
nvidia_detected = False
|
|
|
|
intel_detected = False
|
|
|
|
amd_detected = False
|
|
|
|
virtualbox_detected = False
|
2017-11-20 09:20:30 +01:00
|
|
|
acpi_power_modes = []
|
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
if collect_usb:
|
|
|
|
usb_devices = format_device_list(usb.core.find(find_all=True))
|
2017-11-20 09:20:30 +01:00
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
if collect_pci:
|
|
|
|
pci_devices = format_device_list(get_pci_devices())
|
2017-11-20 09:20:30 +01:00
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
if collect_modules:
|
|
|
|
k = kmodpy.Kmod()
|
|
|
|
modules = [m[0] for m in k.loaded()]
|
2017-11-20 09:20:30 +01:00
|
|
|
|
2017-06-20 16:38:38 +02:00
|
|
|
if collect_gpus:
|
|
|
|
gpus = format_gpu_device_list(get_pci_devices())
|
2017-11-22 09:26:32 +01:00
|
|
|
nvidia_detected = any((True for gpu in gpus if gpu['VendorName'] == 'nvidia'))
|
|
|
|
intel_detected = any((True for gpu in gpus if gpu['VendorName'] == 'intel'))
|
|
|
|
amd_detected = any((True for gpu in gpus if gpu['VendorName'] == 'amd'))
|
|
|
|
virtualbox_detected = any((True for gpu in gpus if gpu['VendorName'] == 'virtualbox'))
|
2017-11-20 09:20:30 +01:00
|
|
|
|
|
|
|
if collect_acpi_power_modes:
|
|
|
|
acpi_power_modes = list_acpi_power_modes()
|
|
|
|
|
|
|
|
data = {'usb': usb_devices, 'pci': pci_devices, 'modules': modules, 'gpus': gpus,
|
2017-11-22 09:24:33 +01:00
|
|
|
'acpi_power_modes': acpi_power_modes, 'nvidia_detected': nvidia_detected,
|
|
|
|
'intel_detected': intel_detected, 'amd_detected': amd_detected,
|
|
|
|
'virtualbox_detected': virtualbox_detected}
|
2017-06-20 16:38:38 +02:00
|
|
|
module.exit_json(changed=False, ansible_facts=data, msg=data)
|
|
|
|
|
|
|
|
|
|
|
|
if __name__ == '__main__':
|
|
|
|
main()
|