%PDF- %PDF-
Direktori : /usr/share/hplip/installer/ |
Current File : //usr/share/hplip/installer/core_install.py |
# -*- coding: utf-8 -*- # # (c) Copyright 2003-2015 HP Development Company, L.P. # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # 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 General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Author: Don Welch # # Std Lib import sys import os import os.path import re import time import grp import pwd import tarfile import stat import glob try: import hashlib # new in 2.5 def get_checksum(s): return hashlib.sha1(s).hexdigest() except ImportError: import sha # deprecated in 2.6/3.0 def get_checksum(s): return sha.new(s).hexdigest() # Local from base.g import * from base.codes import * from base import utils, tui, password, services, os_utils from .dcheck import * DISTRO_UNKNOWN = 0 DISTRO_VER_UNKNOWN = '0.0' MODE_INSTALLER = 0 # hplip-install/hp-setup MODE_CHECK = 1 # hp-check MODE_CREATE_DOCS = 2 # create_docs TYPE_STRING = 1 TYPE_LIST = 2 TYPE_BOOL = 3 TYPE_INT = 4 DEPENDENCY_RUN_TIME = 1 DEPENDENCY_COMPILE_TIME = 2 DEPENDENCY_RUN_AND_COMPILE_TIME = 3 DEPENDENCY_REQUIRED_INDEX = 0 DEPENDENCY_DISPLAY_INDEX = 2 # Mapping from patterns to probability contribution of pattern # Example code from David Mertz' Text Processing in Python. # Released in the Public Domain. err_pats = {r'(?is)<TITLE>.*?(404|403).*?ERROR.*?</TITLE>': 0.95, r'(?is)<TITLE>.*?ERROR.*?(404|403).*?</TITLE>': 0.95, r'(?is)<TITLE>ERROR</TITLE>': 0.30, r'(?is)<TITLE>.*?ERROR.*?</TITLE>': 0.10, r'(?is)<META .*?(404|403).*?ERROR.*?>': 0.80, r'(?is)<META .*?ERROR.*?(404|403).*?>': 0.80, r'(?is)<TITLE>.*?File Not Found.*?</TITLE>': 0.80, r'(?is)<TITLE>.*?Not Found.*?</TITLE>': 0.40, r'(?is)<BODY.*(404|403).*</BODY>': 0.10, r'(?is)<H1>.*?(404|403).*?</H1>': 0.15, r'(?is)<BODY.*not found.*</BODY>': 0.10, r'(?is)<H1>.*?not found.*?</H1>': 0.15, r'(?is)<BODY.*the requested URL.*</BODY>': 0.10, r'(?is)<BODY.*the page you requested.*</BODY>': 0.10, r'(?is)<BODY.*page.{1,50}unavailable.*</BODY>': 0.10, r'(?is)<BODY.*request.{1,50}unavailable.*</BODY>': 0.10, r'(?i)does not exist': 0.10, } # Note:- If new utility is added, add same utility here to uninstall properly. BINS_LIST = ['hpijs', 'hp-align', 'hp-colorcal', 'hp-faxsetup', 'hp-linefeedcal', 'hp-pkservice', 'hp-printsettings', 'hp-sendfax', 'hp-timedate', 'hp-check', 'hp-devicesettings', 'hp-firmware', 'hp-makecopies', 'hp-plugin', 'hp-probe', 'hp-setup', 'hp-toolbox', 'hp-check-plugin', 'hp-diagnose_plugin', 'hp-info', 'hp-makeuri', 'hp-pqdiag', 'hp-query', 'hp-systray', 'hp-unload', 'hp-clean', 'hp-fab', 'hp-levels', 'hp-print', 'hp-scan', 'hp-testpage', 'hp-wificonfig', 'hp-upgrade', 'hplip-info', 'hp-check-upgrade', 'hp-config_usb_printer', 'hp-diagnose_queues', 'hp-devicesetup', 'hp-doctor', 'hp-logcapture'] LIBS_LIST = ['libhpmud.*', 'libhpip.*', 'sane/libsane-hpaio.*', 'cups/backend/hp', 'cups/backend/hpfax', 'cups/filter/hpcac','sane/libsane-hp2000S1*', 'libjpeg*', 'cups/filter/hpps', 'cups/filter/pstotiff', 'cups/filter/hpcups', 'cups/filter/hpcupsfax', 'cups/filter/hplipjs'] HPLIP_EXT_LIST = ['cupsext.so', 'cupsext.la', 'scanext.so', 'scanext.la', 'hpmudext.so', 'hpmudext.la', 'pcardext.so', 'pcardext.la'] FILES_LIST = ['/usr/share/cups/drv/hp/', '/usr/local/share/ppd/HP/', '/usr/local/share/cups/drv/hp/', '/usr/share/applications/hplip.desktop', '/usr/share/applications/hp-uiscan.desktop', '/etc/xdg/autostart/hplip-systray.desktop', '/etc/hp/hplip.conf', '/usr/share/doc/hplip-*', '/usr/lib/systemd/system/hplip-printer*.service'] RULES_LIST = ['56-hpmud.rules', '56-hpmud_sysfs.rules', '40-hplip.rules', '56-hpmud_support.rules', '56-hpmud_support_sysfs.rules', '55-hpmud.rules','S99-2000S1.rules', '55-hpmud_sysfs.rules', '56-hpmud_add_printer.rules', '56-hpmud_add_printer_sysfs.rules', '86-hpmud-hp_*.rules', '86-hpmud_plugin.rules', '86-hpmud_plugin_sysfs.rules'] HPLIP_LIST = ['*.py', '*.pyc', 'base', 'copier', 'data', 'installer', 'pcard', 'ui4', 'ui', 'fax/*.py', 'fax/*.pyc', 'fax/pstotiff.convs', 'fax/pstotiff.types', 'fax/pstotiff', 'prnt/*.py', 'prnt/*.pyc', 'scan/*.py', 'scan/*.pyc'] PLUGIN_LIST = ['fax/plugins/', 'prnt/plugins/', 'scan/plugins/'] PLUGIN_STATE = ['/var/lib/hp/hplip.state'] # end OK_PROCESS_LIST = ['adept-notifier', 'adept_notifier', 'yum-updatesd', ] CONFIGURE_ERRORS = {1: "General/unknown error", 2: "libusb not found", 3: "cups-devel not found", 4: "libnetsnmp not found", 5: "netsnmp-devel not found", 6: "python-devel not found", 7: "pthread-devel not found", 8: "ppdev-devel not found", 9: "libcups not found", 10: "libm not found", 11: "libusb-devel not found", 12: "sane-backends-devel not found", 13: "libdbus not found", 14: "dbus-devel not found", 15: "fax requires dbus support", 102: "libjpeg not found", 103: "jpeg-devel not found", 104: "libdi not found", } EXTERNALDEP = 1 GENERALDEP = 2 COMPILEDEP = 3 PYEXT = 4 SCANCONF = 5 JPEG_STR = "libjpeg - JPEG library" LIBTOOL_STR = "libtool - Library building support services" CUPS_STR = "CUPS - Common Unix Printing System" CUPS_DEV_STR = "CUPS devel- Common Unix Printing System development files" CUPS_IMG_STR = "CUPS image - CUPS image development files" GCC_STR = "gcc - GNU Project C and C++ Compiler" MAKE_STR = "make - GNU make utility to maintain groups of programs" THREAD_STR = "libpthread - POSIX threads library" GS_STR = "GhostScript - PostScript and PDF language interpreter and previewer" USB_STR = "libusb - USB library" CUPS_DDK_STR = "CUPS DDK - CUPS driver development kit" SANE_STR = "SANE - Scanning library" SANE_DEV_STR = "SANE - Scanning library development files" XSANE_STR = "xsane - Graphical scanner frontend for SANE" SCANIMAGE_STR = "scanimage - Shell scanning program" DBUS_STR = "DBus - Message bus system" POLKIT_STR = "PolicyKit - Administrative policy framework" SNMP_DEV_STR = "libnetsnmp-devel - SNMP networking library development files" CRYPTO_STR = "libcrypto - OpenSSL cryptographic library" NETWORK_STR = "network -wget" AVAHI_STR = "avahi-utils" PYTHON_STR = "Python 2.2 or greater - Python programming language" PYNTF_STR = "Python libnotify - Python bindings for the libnotify Desktop notifications" QT4DBUS_STR = "PyQt 4 DBus - DBus Support for PyQt4" QT4_STR = "PyQt 4- Qt interface for Python (for Qt version 4.x)" QT5DBUS_STR = "PyQt 5 DBus - DBus Support for PyQt5" QT5_STR = "PyQt 5- Qt interface for Python (for Qt version 4.x)" PYDBUS_STR = "Python DBus - Python bindings for DBus" PYXML_STR = "Python XML libraries" PY_DEV_STR = "Python devel - Python development files" PIL_STR = "PIL - Python Imaging Library (required for commandline scanning with hp-scan)" PIP_STR = "PIP - preferred installer program" TESS_STR = "Tesseract - Tesseract library for python" TESSEROCR_STR = "Tesserocr - Optical-character-recognition tesseract library for python" IMUTILS_STR = "Imutils - A series of basic image processing functions" OPENCV_STR = "Opencv - opencv library for python" ZBAR_STR = "ZBAR -zbar library for python" LEPTO_STR = "leptonica - leptonica library for python" #SETUPTOOLS_STR = "setuptools - library designed to facilitate packaging Python projects" PYPDF2_STR = "pypdf2 - pdf library for python" REPORTLAB_STR = "Reportlab - PDF library for Python" CUPSEXT_STR = 'CUPS-Extension' HPMUDEXT_STR = 'IO-Extension' HPAIO_STR = 'HPLIP-SANE-Backend' SCANEXT_STR = 'Scan-SANE-Extension' QT_STR = "Python-Qt" EPM_STR = "Build Debian Package" AUTOMAKE_STR = "Build Driver" LIB_AVAHI="libavahi-dev" APPARMOR_DIR = "/etc/apparmor.d" SELINUX_DIR = "/etc/selinux/targeted/policy/policy*" SEC_DICT = {"AppArmor": (APPARMOR_DIR, ["/etc/apparmor.d/usr.share.hplip", "/etc/apparmor.d/abstractions/hplip"]), "SELinux": (SELINUX_DIR, ["/etc/selinux/targeted/modules/active/modules/hplip.pp"]) } try: from functools import update_wrapper except ImportError: # using Python version < 2.5 def trace(f): def newf(*args, **kw): log.debug("TRACE: func=%s(), args=%s, kwargs=%s" % (f.__name__, args, kw)) return f(*args, **kw) newf.__name__ = f.__name__ newf.__dict__.update(f.__dict__) newf.__doc__ = f.__doc__ newf.__module__ = f.__module__ return newf else: # using Python 2.5+ def trace(f): def newf(*args, **kw): log.debug("TRACE: func=%s(), args=%s, kwargs=%s" % (f.__name__, args, kw)) return f(*args, **kw) return update_wrapper(newf, f) class CoreInstall(object): def __init__(self, mode=MODE_INSTALLER, ui_mode=INTERACTIVE_MODE, ui_toolkit='qt4'): os.umask(0o022) self.mode = mode self.ui_mode = ui_mode self.passwordObj = password.Password(ui_mode) self.version_description, self.version_public, self.version_internal = '', '', '' self.bitness = 32 self.endian = utils.LITTLE_ENDIAN self.distro, self.distro_name, self.distro_version = DISTRO_UNKNOWN, '', DISTRO_VER_UNKNOWN self.distro_version_supported = False self.install_location = '/usr' self.hplip_present = False self.have_dependencies = {} self.native_cups = True self.ppd_dir = None self.drv_dir = None self.distros = {} self.ui_toolkit = ui_toolkit self.enable = None self.disable = None self.reload_dbus = False self.security_package = "" self.FIELD_TYPES = { 'distros': TYPE_LIST, 'index': TYPE_INT, 'versions': TYPE_LIST, 'display_name': TYPE_STRING, 'alt_names': TYPE_LIST, 'display': TYPE_BOOL, 'notes': TYPE_STRING, 'package_mgrs': TYPE_LIST, 'package_mgr_cmd': TYPE_STRING, 'pre_install_cmd': TYPE_LIST, 'pre_depend_cmd': TYPE_LIST, 'post_depend_cmd': TYPE_LIST, 'scanjet_depend_cmd': TYPE_LIST, 'scanjet_py3_depend_cmd': TYPE_LIST, 'hpoj_remove_cmd': TYPE_STRING, 'hplip_remove_cmd': TYPE_STRING, 'su_sudo': TYPE_STRING, 'ppd_install': TYPE_STRING, 'udev_mode_fix': TYPE_BOOL, 'ppd_dir': TYPE_STRING, 'drv_dir': TYPE_STRING, 'fix_ppd_symlink': TYPE_BOOL, 'code_name': TYPE_STRING, 'supported': TYPE_BOOL, # Supported by installer 'release_date': TYPE_STRING, 'packages': TYPE_LIST, 'commands': TYPE_LIST, 'same_as_version': TYPE_STRING, 'scan_supported': TYPE_BOOL, 'fax_supported': TYPE_BOOL, 'pcard_supported': TYPE_BOOL, 'network_supported': TYPE_BOOL, 'parallel_supported': TYPE_BOOL, 'usb_supported': TYPE_BOOL, 'packaged_version': TYPE_STRING, # Version of HPLIP pre-packaged in distro 'cups_path_with_bitness': TYPE_BOOL, 'ui_toolkit': TYPE_STRING, # qt3 or qt4 [or gtk] or none 'policykit': TYPE_BOOL, 'libusb01': TYPE_BOOL, 'udev_sysfs_rule': TYPE_BOOL, 'native_cups': TYPE_BOOL, 'package_available': TYPE_BOOL, 'package_arch': TYPE_LIST, 'open_mdns_port': TYPE_LIST, # command to use to open mdns multicast port 5353 'libdir_path': TYPE_STRING, 'hp_libs_remove_cmd': TYPE_STRING, } # components # 'name': ('description', [<option list>]) self.components = { 'hplip': ("HP Linux Imaging and Printing System", ['prnt', 'base', 'network', 'gui_qt4', 'gui_qt5', 'fax', 'scan', 'docs']), } self.selected_component = 'hplip' # options # name: (<required>, "<display_name>", [<dependency list>]), ... self.options = { # HPLIP 'prnt': (True, 'Print Component ', []), 'base': (True, 'Required HPLIP base components (including hpcups)', []), 'network': (False, 'Network/JetDirect I/O', []), 'gui_qt4': (False, 'Graphical User Interfaces (Qt4)', []), 'gui_qt5': (False, 'Graphical User Interfaces (Qt5)', []), 'gui_qt': (False, 'Graphical User Interfaces (Qt)', []), 'fax': (False, 'PC Send Fax support', []), 'scan': (False, 'Scanning support', []), 'docs': (False, 'HPLIP documentation (HTML)', []), 'policykit': (False, 'Administrative policy framework', []), 'libusb01': (False, 'libusb-1.0', []), 'udev_sysfs_rule': (False, 'udev_sysfs_rule', []), } # holds whether the user has selected (turned on each option) # initial values are defaults (for GUI only) self.selected_options = { 'prnt': False, 'base': True, 'network': True, 'gui_qt4': False, 'gui_qt5': False, 'gui_qt': False, 'fax': True, 'scan': True, 'docs': True, 'policykit': False, 'libusb01': False, 'udev_sysfs_rule': False, 'native_cups': False, 'class-driver': False, } # dependencies # 'name': (<required or option>, [<option list>], <display_name>, <check_func>, <runtime/compiletime>), ... # Note: any change to the list of dependencies must be reflected in # base/distros.py self.dependencies = { # Required base packages 'epm': (False, ['prnt'], EPM_STR, self.check_epm, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', None, GENERALDEP), 'automake': (True, ['prnt'], AUTOMAKE_STR, self.check_automake, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', None, GENERALDEP), 'libjpeg': (True, ['base', 'prnt'], JPEG_STR, self.check_libjpeg, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', None, GENERALDEP), 'libtool': (True, ['base', 'prnt'], LIBTOOL_STR, self.check_libtool, DEPENDENCY_COMPILE_TIME, '-', 'libtool --version', COMPILEDEP), 'cups': (True, ['base', 'prnt'], CUPS_STR, self.check_cups, DEPENDENCY_RUN_TIME, '1.1', 'lpstat -r', EXTERNALDEP), 'cups-devel': (True, ['base', 'prnt'], CUPS_DEV_STR, self.check_cups_devel, DEPENDENCY_COMPILE_TIME, '-', 'lpstat -r', GENERALDEP), 'cups-image': (True, ['base', 'prnt'], CUPS_IMG_STR, self.check_cups_image, DEPENDENCY_COMPILE_TIME, '-', 'lpstat -r', GENERALDEP), 'gcc': (True, ['base', 'prnt'], GCC_STR, self.check_gcc, DEPENDENCY_COMPILE_TIME, '-', 'gcc --version', COMPILEDEP), 'make': (True, ['base', 'prnt'], MAKE_STR, self.check_make, DEPENDENCY_COMPILE_TIME, '3.0', 'make --version', COMPILEDEP), 'libpthread': (True, ['base', 'prnt'], THREAD_STR, self.check_libpthread, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#get_libpthread_version', GENERALDEP), 'gs': (True, ['base', 'prnt'], GS_STR, self.check_gs, DEPENDENCY_RUN_TIME, '7.05', 'gs --version', EXTERNALDEP), 'libusb': (True, ['base'], USB_STR, self.check_libusb, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#get_libusb_version', GENERALDEP), #'pkgconf': (True, ['base', 'prnt'], PKG_CONF, self.check_pkgconf, DEPENDENCY_COMPILE_TIME, '-', None, GENERALDEP), # Optional base packages # req. for .drv PPD installs 'cups-ddk': (False, ['base', 'prnt'], CUPS_DDK_STR, self.check_cupsddk, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), # Required scan packages 'sane': (True, ['scan'], SANE_STR, self.check_sane, DEPENDENCY_RUN_TIME, '-', 'sane-config --version', GENERALDEP), 'sane-devel': (True, ['scan'], SANE_DEV_STR, self.check_sane_devel, DEPENDENCY_COMPILE_TIME, '-', 'sane-config --version', GENERALDEP), 'libavahi-dev': (True, ['scan'], LIB_AVAHI, self.check_libavahi_dev, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#check_libavahi_dev', GENERALDEP), #'tesseract': (True, ['scan'], TESS_STR, self.check_tesseract, DEPENDENCY_RUN_TIME, '-', 'tesseract --version', GENERALDEP), #'zbar': (True, ['scan'], ZBAR_STR, self.check_zbar, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'libleptonica': (True, ['scan'], LEPTO_STR, self.check_libleptonica, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), # Optional scan packages 'xsane': (False, ['scan'], XSANE_STR, self.check_xsane, DEPENDENCY_RUN_TIME, '0.9', 'FUNC#get_xsane_version', EXTERNALDEP), 'scanimage': (False, ['scan'], SCANIMAGE_STR, self.check_scanimage, DEPENDENCY_RUN_TIME, '1.0', 'scanimage --version', EXTERNALDEP), # Required fax packages 'dbus': (True, ['fax'], DBUS_STR, self.check_dbus, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'dbus-daemon --version', EXTERNALDEP), # Required and optional qt4 GUI packages # optional for non-sudo behavior of plugins (only optional for Qt4 # option) 'policykit': (False, ['gui_qt4', 'gui_qt5'], POLKIT_STR, self.check_policykit, DEPENDENCY_RUN_TIME, '-', 'pkexec --version', EXTERNALDEP), # Required network I/O packages 'libnetsnmp-devel': (True, ['network'], SNMP_DEV_STR, self.check_libnetsnmp, DEPENDENCY_RUN_AND_COMPILE_TIME, '5.0.9', 'net-snmp-config --version', GENERALDEP), 'libcrypto': (True, ['network'], CRYPTO_STR, self.check_libcrypto, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'openssl version', GENERALDEP), 'network': (False, ['network'], NETWORK_STR, self.check_wget, DEPENDENCY_RUN_TIME, '-', 'wget --version', EXTERNALDEP), 'avahi-utils': (False, ['network'], AVAHI_STR, self.check_avahi_utils, DEPENDENCY_RUN_TIME, '-', 'avahi-browse --version', EXTERNALDEP), } python2_dep = { 'python2X': (True, ['base'], PYTHON_STR, self.check_python, DEPENDENCY_RUN_AND_COMPILE_TIME, '2.2', 'python --version', GENERALDEP), #'setuptools': (False, ['scan'], SETUPTOOLS_STR, self.check_setuptools, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'pip': (True, ['scan'], PIP_STR, self.check_pip, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'pypdf2': (True, ['scan'], PYPDF2_STR, self.check_pypdf2, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'opencv': (True, ['scan'], OPENCV_STR, self.check_opencv, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'zbar': (True, ['scan'], ZBAR_STR, self.check_zbar, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), # Optional for libnotify style popups from hp-systray 'python-notify': (False, ['gui_qt5', 'gui_qt4'], PYNTF_STR, self.check_pynotify, DEPENDENCY_RUN_TIME, '-', 'python-notify --version', GENERALDEP), 'pyqt4-dbus': (True, ['gui_qt4'], QT4DBUS_STR, self.check_pyqt4_dbus, DEPENDENCY_RUN_TIME, '4.0', 'FUNC#get_pyQt4_version', GENERALDEP), # PyQt 4.x ) 'pyqt4': (True, ['gui_qt4'], QT4_STR, self.check_pyqt4, DEPENDENCY_RUN_TIME, '4.0', 'FUNC#get_pyQt4_version', GENERALDEP), 'pyqt5-dbus': (False, ['gui_qt5'], QT5DBUS_STR, self.check_pyqt5_dbus, DEPENDENCY_RUN_TIME, '5.0', 'FUNC#get_pyQt5_version', GENERALDEP), # PyQt 5.x ) 'pyqt5': (True, ['gui_qt5'], QT5_STR, self.check_pyqt5, DEPENDENCY_RUN_TIME, '5.0', 'FUNC#get_pyQt5_version', GENERALDEP), 'python-dbus': (True, ['fax'], PYDBUS_STR, self.check_python_dbus, DEPENDENCY_RUN_TIME, '0.80.0', 'FUNC#get_python_dbus_ver', GENERALDEP), 'python-xml': (True, ['base'], PYXML_STR, self.check_python_xml, DEPENDENCY_RUN_TIME, '-', 'FUNC#get_python_xml_version', GENERALDEP), 'python-devel': (True, ['base'], PY_DEV_STR, self.check_python_devel, DEPENDENCY_COMPILE_TIME, '2.2', 'python --version', GENERALDEP), 'pil': (False, ['scan'], PIL_STR, self.check_pil, DEPENDENCY_RUN_TIME, '-', 'FUNC#get_pil_version', GENERALDEP), #'imutils': (True, ['scan'], IMUTILS_STR, self.check_imutils, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), # Optional fax packages 'reportlab': (False, ['fax'], REPORTLAB_STR, self.check_reportlab, DEPENDENCY_RUN_TIME, '2.0', 'FUNC#get_reportlab_version', GENERALDEP), #'tesserocr': (True, ['scan'], TESSEROCR_STR, self.check_tesserocr, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), } python3_dep = { 'python3X': (True, ['base'], PYTHON_STR, self.check_python, DEPENDENCY_RUN_AND_COMPILE_TIME, '2.2', 'python3 --version', GENERALDEP), # Optional for libnotify style popups from hp-systray #'py3_setuptools': (False, ['scan'], SETUPTOOLS_STR, self.check_setuptools, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'python3-pip': (True, ['scan'], PIP_STR, self.check_pip3, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'pypdf2': (True, ['scan'], PYPDF2_STR, self.check_pypdf2, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), #'opencv': (True, ['scan'], OPENCV_STR, self.check_opencv, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), 'python3-notify2': (False, ['gui_qt5', 'gui_qt4'], PYNTF_STR, self.check_pynotify, DEPENDENCY_RUN_TIME, '-', 'python-notify --version', GENERALDEP), 'python3-pyqt4-dbus': (False, ['gui_qt4'], QT4DBUS_STR, self.check_pyqt4_dbus, DEPENDENCY_RUN_TIME, '4.0', 'FUNC#get_pyQt4_version', GENERALDEP), # PyQt 4.x ) 'python3-pyqt4': (True, ['gui_qt4'], QT4_STR, self.check_pyqt4, DEPENDENCY_RUN_TIME, '4.0', 'FUNC#get_pyQt4_version', GENERALDEP), 'python3-pyqt5-dbus': (False, ['gui_qt5'], QT5DBUS_STR, self.check_pyqt5_dbus, DEPENDENCY_RUN_TIME, '5.0', 'FUNC#get_pyQt5_version', GENERALDEP), # PyQt 5.x ) 'python3-pyqt5': (True, ['gui_qt5'], QT5_STR, self.check_pyqt5, DEPENDENCY_RUN_TIME, '5.0', 'FUNC#get_pyQt5_version', GENERALDEP), 'python3-dbus': (True, ['fax'], PYDBUS_STR, self.check_python_dbus, DEPENDENCY_RUN_TIME, '0.80.0', 'FUNC#get_python_dbus_ver', GENERALDEP), 'python3-xml': (True, ['base'], PYXML_STR, self.check_python_xml, DEPENDENCY_RUN_TIME, '-', 'FUNC#get_python_xml_version', GENERALDEP), 'python3-devel': (True, ['base'], PY_DEV_STR, self.check_python_devel, DEPENDENCY_COMPILE_TIME, '2.2', 'python3 --version', GENERALDEP), 'python3-pil': (False, ['scan'], PIL_STR, self.check_pil, DEPENDENCY_RUN_TIME, '-', 'FUNC#get_pil_version', GENERALDEP), #'imutils': (True, ['scan'], IMUTILS_STR, self.check_imutils, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), # Optional fax packages 'python3-reportlab': (False, ['fax'], REPORTLAB_STR, self.check_reportlab, DEPENDENCY_RUN_TIME, '2.0', 'FUNC#get_reportlab_version', GENERALDEP), #'tesserocr': (True, ['scan'], TESSEROCR_STR, self.check_tesserocr, DEPENDENCY_RUN_TIME, '-', None, GENERALDEP), } from base.sixext import PY3 if PY3: self.dependencies.update(python3_dep) else: self.dependencies.update(python2_dep) self.hplip_dependencies = { 'cupsext': (True, ['base'], CUPSEXT_STR, self.check_cupsext, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#get_HPLIP_version', PYEXT), 'hpmudext': (True, ['base'], HPMUDEXT_STR, self.check_hpmudext, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#get_HPLIP_version', PYEXT), 'hpaio': (True, ['scan'], HPAIO_STR, self.check_hpaio, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#get_HPLIP_version', SCANCONF), 'scanext': (True, ['scan'], SCANEXT_STR, self.check_scanext, DEPENDENCY_RUN_AND_COMPILE_TIME, '-', 'FUNC#get_HPLIP_version', SCANCONF), 'pyqt': (True, ['gui_qt'], QT_STR, self.check_pyqt, DEPENDENCY_RUN_AND_COMPILE_TIME, '2.3', 'FUNC#get_pyQt_version', GENERALDEP), } self.version_func = { 'FUNC#get_python_dbus_ver': get_python_dbus_ver, 'FUNC#get_pyQt5_version': get_pyQt5_version, 'FUNC#get_pyQt4_version': get_pyQt4_version, 'FUNC#get_pyQt_version': get_pyQt_version, 'FUNC#get_reportlab_version': get_reportlab_version, 'FUNC#get_xsane_version': get_xsane_version, 'FUNC#get_pil_version': get_pil_version, 'FUNC#get_libpthread_version': get_libpthread_version, 'FUNC#get_python_xml_version': get_python_xml_version, 'FUNC#get_HPLIP_version': get_HPLIP_version, 'FUNC#get_libusb_version': get_libusb_version, } for opt in self.options: update_spinner() for d in self.dependencies: if opt in self.dependencies[d][1]: self.options[opt][2].append(d) self.load_distros() self.distros_index = {} for d in self.distros: self.distros_index[self.distros[d]['index']] = d def init(self, callback=None): if callback is not None: callback("Init...\n") update_spinner() # Package manager names self.package_mgrs = [] for d in self.distros: update_spinner() for a in self.distros[d].get('package_mgrs', []): if a and a not in self.package_mgrs: self.package_mgrs.append(a) self.version_description, self.version_public, self.version_internal = self.get_hplip_version() log.debug("HPLIP Description=%s Public version=%s Internal version = %s" % (self.version_description, self.version_public, self.version_internal)) # have_dependencies # is each dependency satisfied? # start with each one 'No' for d in self.dependencies: update_spinner() self.have_dependencies[d] = False self.get_distro() self.distro_name = self.distros_index[self.distro] self.distro_changed() if callback is not None: callback("Distro: %s\n" % self.distro) self.check_dependencies(callback) for d in self.dependencies: update_spinner() log.debug("have %s = %s" % (d, self.have_dependencies[d])) if callback is not None: callback("Result: %s = %s\n" % (d, self.have_dependencies[d])) pid, cmdline = utils.check_pkg_mgr(self.package_mgrs) if pid: log.debug("Running package manager: %s (%s)" % (cmdline, pid)) self.bitness = utils.getBitness() log.debug("Bitness = %d" % self.bitness) update_spinner() self.endian = utils.getEndian() log.debug("Endian = %d" % self.endian) update_spinner() self.distro_version_supported = self.get_distro_ver_data( 'supported', False) log.debug("Distro = %s Distro Name = %s Display Name= %s Version = %s Supported = %s" % (self.distro, self.distro_name, self.distros[self.distro_name]['display_name'], self.distro_version, self.distro_version_supported)) update_spinner() self.hplip_present = self.check_hplip() log.debug("HPLIP (prev install) = %s" % self.hplip_present) status, output = utils.run('cups-config --version', self.passwordObj) self.cups_ver = output.strip() log.debug("CUPS version = %s" % self.cups_ver) if self.distro_name == "ubuntu": self.reload_dbus = True log.debug("DBUS configuration reload possible? %s" % self.reload_dbus) status, self.sys_uname_info = utils.run('uname -a', self.passwordObj) self.sys_uname_info = self.sys_uname_info.replace('\n', '') log.debug(self.sys_uname_info) # Record the installation time/date and version. # Also has the effect of making the .hplip.conf file user r/w # on the 1st run so that running hp-setup as root doesn't lock # the user out of owning the file user_conf.set('installation', 'date_time', time.strftime("%x %H:%M:%S", time.localtime())) user_conf.set('installation', 'version', self.version_public) if callback is not None: callback("Done") def init_for_docs(self, distro_name, version, bitness=32): self.distro_name = distro_name self.distro_version = version try: self.distro = self.distros[distro_name]['index'] except KeyError: log.error("Invalid distro name: %s" % distro_name) sys.exit(1) self.bitness = bitness for d in self.dependencies: self.have_dependencies[d] = True self.enable_ppds = self.get_distro_ver_data( 'ppd_install', 'ppd') == 'ppd' self.ppd_dir = self.get_distro_ver_data('ppd_dir') self.drv_dir = self.get_distro_ver_data('drv_dir') self.distro_version_supported = True # for manual installs def check_dependencies(self, callback=None): update_ld_output() for d in self.dependencies: update_spinner() log.debug("Checking for dependency '%s'...\n" % d) if callback is not None: callback("Checking: %s\n" % d) self.have_dependencies[d] = self.dependencies[d][3]() log.debug("have %s = %s" % (d, self.have_dependencies[d])) cleanup_spinner() def password_func(self): if self.password: return self.password elif self.ui_mode == INTERACTIVE_MODE: import getpass return getpass.getpass("Enter password: ") else: return '' def get_distro(self): log.debug("Determining distro...") name, ver = '', '0.0' found = False import distro ld = distro.linux_distribution(full_distribution_name=False) name = ld[0] ver = ld[1] found = True # Updating the distro name and version. if found: name = name.lower().strip() log.debug("Distro name=%s" % name) if name.find("redhatenterprise") > -1 or name.find("redhat") > -1: name = "rhel" log.debug("Distro version=%s" % ver) if name == "rhel" and ver[0] == "5" and ver[1] == ".": ver = "5.0" elif name == "rhel" and ver[0] == "6" and ver[1] == ".": ver = "6.0" if 'MX' in name: ver = name[3:5] name = "mxlinux" if 'manjaro' in name.lower(): version = ver.split('.') ver = version[0] +'.'+version[1] found_in_list = False for d in self.distros: if name.find(d) > -1: self.distro = self.distros[d]['index'] found_in_list = True else: for x in self.distros[d].get('alt_names', ''): if x and name.find(x) > -1: self.distro = self.distros[d]['index'] found_in_list = True break if found_in_list: break self.distro_version = ver self.distro_name = name else: log.warn("Failed to get the distro information.") self.distro, self.distro_version = DISTRO_UNKNOWN, '0.0' log.debug("distro=%d, distro_version=%s" % (self.distro, self.distro_version)) def distro_changed(self): ppd_install = self.get_distro_ver_data('ppd_install', 'ppd') if ppd_install not in ('ppd', 'drv'): log.warning("Invalid ppd_install value: %s" % ppd_install) self.enable_ppds = (ppd_install == 'ppd') log.debug("Enable PPD install: %s (False=drv)" % self.enable_ppds) self.ppd_dir = self.get_distro_ver_data('ppd_dir') self.drv_dir = self.get_distro_ver_data('drv_dir') if not self.enable_ppds and not self.drv_dir: log.warning("Invalid drv_dir value: %s" % self.drv_dir) self.distro_version_supported = self.get_distro_ver_data( 'supported', False) self.selected_options['fax'] = self.get_distro_ver_data( 'fax_supported', True) self.selected_options['network'] = self.get_distro_ver_data( 'network_supported', True) self.selected_options['scan'] = self.get_distro_ver_data( 'scan_supported', True) self.selected_options['policykit'] = self.get_distro_ver_data( 'policykit', False) self.selected_options[ 'libusb01'] = self.get_distro_ver_data('libusb01', False) self.selected_options['udev_sysfs_rule'] = self.get_distro_ver_data( 'udev_sysfs_rule', False) self.native_cups = self.get_distro_ver_data('native_cups', False) # Adjust required flag based on the distro ver ui_toolkit value ui_toolkit = self.get_distro_ver_data('ui_toolkit', 'qt4').lower() if ui_toolkit == 'qt4': log.debug("Default UI toolkit: Qt4") self.ui_toolkit = 'qt4' self.selected_options['gui_qt4'] = True elif ui_toolkit == 'qt5': log.debug("Default UI toolkit: Qt5") self.ui_toolkit = 'qt5' self.selected_options['gui_qt5'] = True # todo: gtk # Override with --qt4 command args if self.enable is not None: if 'qt4' in self.enable: log.debug("User selected UI toolkit: Qt4") self.ui_toolkit = 'qt4' self.selected_options['gui_qt4'] = True elif 'qt5' in self.enable: log.debug("User selected UI toolkit: Qt5") self.ui_toolkit = 'qt5' self.selected_options['gui_qt5'] = True if self.disable is not None: if 'qt4' in self.disable: log.debug("User deselected UI toolkit: Qt4") self.selected_options['gui_qt4'] = False elif 'qt5' in self.disable: log.debug("User deselected UI toolkit: Qt5") self.selected_options['gui_qt5'] = False def __fixup_data(self, key, data): field_type = self.FIELD_TYPES.get(key, TYPE_STRING) #log.debug("%s (%s) %d" % (key, data, field_type)) if field_type == TYPE_BOOL: return utils.to_bool(data) elif field_type == TYPE_STRING: if type('') == type(data): return data.strip() else: return data elif field_type == TYPE_INT: try: return int(data) except ValueError: return 0 elif field_type == TYPE_LIST: return [x for x in data.split(',') if x] def load_distros(self): distros_dat_file = '/usr/share/hplip/installer/distros.dat' distros_dat = ConfigBase(distros_dat_file) distros_list = self.__fixup_data( 'distros', distros_dat.get('distros', 'distros')) log.debug(distros_list) for distro in distros_list: update_spinner() d = {} if not distros_dat.has_section(distro): log.debug( "Missing distro section in distros.dat: [%s]" % distro) continue for key in distros_dat.keys(distro): d[key] = self.__fixup_data(key, distros_dat.get(distro, key)) self.distros[distro] = d versions = self.__fixup_data( "versions", distros_dat.get(distro, 'versions')) self.distros[distro]['versions'] = {} self.distros[distro]['versions_list'] = versions for ver in versions: same_as_version, supported = False, True v = {} ver_section = "%s:%s" % (distro, ver) if not distros_dat.has_section(ver_section): log.error( "Missing version section in distros.dat: [%s:%s]" % (distro, ver)) continue if 'same_as_version' in distros_dat.keys(ver_section): same_as_version = True supported = self.__fixup_data( 'supported', distros_dat.get(ver_section, 'supported')) for key in distros_dat.keys(ver_section): v[key] = self.__fixup_data( key, distros_dat.get(ver_section, key)) self.distros[distro]['versions'][ver] = v self.distros[distro]['versions'][ver]['dependency_cmds'] = {} if same_as_version: # or not supported: continue for dep in self.dependencies: dd = {} dep_section = "%s:%s:%s" % (distro, ver, dep) if not distros_dat.has_section(dep_section) and not same_as_version: continue # if same_as_version: # continue for key in distros_dat.keys(dep_section): dd[key] = self.__fixup_data( key, distros_dat.get(dep_section, key)) self.distros[distro]['versions'][ ver]['dependency_cmds'][dep] = dd versions = self.distros[distro]['versions'] for ver in versions: ver_section = "%s:%s" % (distro, ver) if 'same_as_version' in distros_dat.keys(ver_section): v = self.__fixup_data("same_as_version", distros_dat.get( ver_section, 'same_as_version')) try: import copy vv = copy.deepcopy(self.distros[distro]['versions'][v]) #vv = self.distros[distro]['versions'][v].copy() vv['same_as_version'] = v self.distros[distro]['versions'][ver] = vv for key in distros_dat.keys(ver_section): vv[key] = self.__fixup_data( key, distros_dat.get(ver_section, key)) dd = {} for dep in self.dependencies: dep_section = "%s:%s:%s" % (distro, ver, dep) if not distros_dat.has_section(dep_section): continue for key in distros_dat.keys(dep_section): dd[key] = self.__fixup_data( key, distros_dat.get(dep_section, key)) self.distros[distro]['versions'][ ver]['dependency_cmds'][dep] = dd except KeyError: log.debug( "Missing 'same_as_version=' version in distros.dat for section [%s:%s]." % (distro, v)) continue #import pprint # pprint.pprint(self.distros) def pre_install(self): pass def pre_depend(self): pass def check_python(self): py_ver = sys.version_info py_major_ver, py_minor_ver = py_ver[:2] log.debug("Python ver=%d.%d" % (py_major_ver, py_minor_ver)) return py_major_ver >= 2 def check_gcc(self): return check_tool('gcc --version', 0) and check_tool('g++ --version', 0) def check_make(self): return check_tool('make --version', 3.0) #def check_pkgconf(self): #return check_tool('pkgconf --version', 0) def check_libusb(self): Is_libusb01_enabled = self.get_distro_ver_data('libusb01', False) if Is_libusb01_enabled == True: if not check_lib('libusb'): return False if self.distro_name != "rhel": return len(locate_file_contains("usb.h", '/usr/include', 'usb_init')) else: return True else: if not check_lib('libusb-1.0'): return False if self.distro_name != "rhel": return len(locate_file_contains("libusb.h", '/usr/include/libusb-1.0', 'libusb_init')) else: return True def check_epm(self): return check_tool('epm --version') def check_automake(self): return check_tool('automake --version') def check_libjpeg(self): return check_lib("libjpeg") and check_file("jpeglib.h") def check_libcrypto(self): return check_lib("libcrypto") and check_file("crypto.h") def check_libpthread(self): return check_lib("libpthread") and check_file("pthread.h") def check_libnetsnmp(self): return check_lib("libnetsnmp") and check_file("net-snmp-config.h") def check_reportlab(self): try: log.debug("Trying to import 'reportlab'...") import reportlab ver = str(reportlab.Version) log.debug("Version: %.1s" % ver) if ver >= "2.0": log.debug("Success.") return True else: return False except ImportError: log.debug("Failed.") return False def check_python23(self): py_ver = sys.version_info py_major_ver, py_minor_ver = py_ver[:2] log.debug("Python ver=%d.%d" % (py_major_ver, py_minor_ver)) return py_major_ver >= 2 and py_minor_ver >= 3 def check_python_xml(self): try: import xml.parsers.expat except ImportError: return False else: return True def check_sane(self): return check_lib('libsane') def check_sane_devel(self): return len(locate_file_contains("sane.h", '/usr/include', 'extern SANE_Status sane_init')) def check_xsane(self): if os.getenv('DISPLAY'): # will fail if X not running... return check_version(get_xsane_version(), '0.9') # return check_tool('xsane --version', 0.9) # will fail if X not # running... else: # ...so just see if it installed somewhere return bool(utils.which("xsane")) def check_scanimage(self): return check_tool('scanimage --version', 1.0) def check_gs(self): return check_tool('gs -v', 7.05) def check_pyqt4(self): if self.ui_toolkit == 'qt4': try: import PyQt4 except ImportError: return False else: return True else: return False def check_pyqt5(self): if self.ui_toolkit == 'qt5': try: import PyQt5 except ImportError: return False else: return True else: return False def check_pyqt4_dbus(self): if self.ui_toolkit == 'qt4': try: from dbus.mainloop.qt import DBusQtMainLoop except ImportError: return False else: return True else: return False def check_pyqt5_dbus(self): if self.ui_toolkit == 'qt5': try: from dbus.mainloop.pyqt5 import DBusQtMainLoop except ImportError: return False else: return True else: return False def check_pyqt(self): if self.ui_toolkit == 'qt3': try: import qt except ImportError: return False else: return True else: return False def check_python_devel(self): dir_list = glob.glob('/usr/include/python%d*' % sys.version_info[0]) Found = False for p in dir_list: if check_file('Python.h', dir=p): Found = True break return Found def check_pynotify(self): try: import notify2 except (ImportError, RuntimeError): try: import pynotify except (ImportError, RuntimeError): return False return True def check_python_dbus(self): log.debug("Checking for python-dbus (>= 0.80)...") try: import dbus try: ver = dbus.version log.debug("Version: %s" % '.'.join( [str(x) for x in dbus.version])) return ver >= (0, 80, 0) except AttributeError: try: ver = dbus.__version__ log.debug("Version: %s" % dbus.__version__) log.debug("HPLIP requires dbus version > 0.80.") return False except AttributeError: log.debug( "Unknown version. HPLIP requires dbus version > 0.80.") return False except ImportError: return False def check_python_ctypes(self): try: import ctypes return True except ImportError: return False def check_dbus(self): log.debug("Checking for dbus running and header files present (dbus-devel)...") if (self.distro_name.lower()=='fedora') and (self.distro_version>='30'): return True else: return check_ps(['dbus-daemon']) and \ len(locate_file_contains("dbus-message.h", '/usr/include', 'dbus_message_new_signal')) def check_cups_devel(self): return check_file('cups.h') and bool(utils.which('lpr')) def check_cups(self): status, output = utils.run('lpstat -r', self.passwordObj) if status > 0 or 'not running' in output: log.debug("CUPS is not running. %s" % output) return False else: log.debug("CUPS is running. %s " % output) return True def check_cups_image(self): return check_file("raster.h", "/usr/include/cups") def check_hplip(self): log.debug("Checking for HPLIP...") return locate_files('hplip.conf', '/etc/hp') def check_libtool(self): log.debug("Checking for libtool...") return check_tool('libtool --version') '''def check_pip(self): return check_tool('pip2 --version') def check_pip3(self): return check_tool('pip3 --version') def check_tesseract(self): return check_tool('tesseract --version') def check_opencv(self): try: import cv2 return True except ImportError: return False def check_tesserocr(self): try: import tesserocr return True except ImportError: return False def check_imutils(self): try: import imutils return True except ImportError: return False def check_zbar(self): return check_file("zbar.h", "/usr/include/") def check_libleptonica(self): return check_file("allheaders.h", "/usr/include/leptonica") def check_setuptools(self): try: import setuptools return True except ImportError: return False def check_pypdf2(self): try: import PyPDF2 return True except ImportError: return False ''' def check_pil(self): log.debug("Checking for PIL...") try: from PIL import Image return True except ImportError: return False def check_cupsddk(self): log.debug("Checking for cups-ddk...") # TODO: Compute these paths some way or another... return check_file('media.defs', "/usr/share/cups/ppdc/") def check_libavahi_dev(self): log.debug("Checking for libavahi-dev") # TODO: Compute these paths some way or another... return check_file('client.h', "/usr/include/avahi-client") def check_policykit(self): log.debug("Checking for PolicyKit...") if check_file('PolicyKit.conf', "/etc/PolicyKit") and check_file('org.gnome.PolicyKit.AuthorizationManager.service', "/usr/share/dbus-1/services"): return True elif check_file('50-localauthority.conf', "/etc/polkit-1/localauthority.conf.d") and check_file('org.freedesktop.PolicyKit1.service', "/usr/share/dbus-1/system-services"): return True elif check_file('org.freedesktop.PolicyKit1.conf', '/etc/dbus-1/system.d'): return True elif check_file('polkitd', "/usr/lib/polkit-1") and check_file('polkit-agent-helper-1', "/usr/lib/polkit-1") and check_file('polkit.conf', "/usr/lib/sysusers.d"): return True else: return False def check_cupsext(self): log.debug("Checking 'cupsext' CUPS extension...") try: utils.import_ext('cupsext') except ImportError: log.error( "NOT FOUND OR FAILED TO LOAD! Please reinstall HPLIP and check for the proper installation of cupsext.") return False else: return True def check_hpmudext(self): log.debug("Checking 'hpmudext' I/O extension...") try: utils.import_ext('hpmudext') except ImportError: log.error( "NOT FOUND OR FAILED TO LOAD! Please reinstall HPLIP and check for the proper installation of hpmudext.") return False else: return True def check_pcardext(self): log.debug("Checking 'pcardext' Photocard extension...") try: utils.import_ext('pcardext') except ImportError: log.error( "NOT FOUND OR FAILED TO LOAD! Please reinstall HPLIP and check for the proper installation of pcardext.") return False else: return True def check_hpaio(self): found = False for path in ['/etc/sane.d/dll.conf', '/etc/sane.d/dll.d/hpaio', '/etc/sane.d/dll.d/hplip']: log.debug("'Checking for hpaio' in '%s'..." % path) try: f = open(path, 'r') except IOError: log.info("'%s' not found." % path) else: for line in f: lineNoSpace = re.sub(r'\s', '', line) hpaiomatched = re.match('hpaio', lineNoSpace) if hpaiomatched: found = True break if found: break if not found: log.error("'hpaio' not found in SANE conf files. Is SANE installed?") return found def update_hpaio(self): found = False home_dir = sys_conf.get('dirs', 'home') pat = re.compile(r"""(\S.*)share\/hplip""") usrbin_dir = None if pat.match(home_dir) is not None: usrlib_dir = pat.match(home_dir).group(1) + "lib/" if os.path.exists(usrlib_dir + 'sane/libsane-hpaio.so.1'): log.debug("'Updating hpaio' in '/etc/sane.d/dll.conf'...") try: f = open('/etc/sane.d/dll.conf', 'r') except IOError: log.error( "'/etc/sane.d/dll.conf' not found. Creating dll.conf file") cmd = self.passwordObj.getAuthCmd() % 'touch /etc/sane.d/dll.conf' log.debug("cmd=%s" % cmd) utils.run(cmd, self.passwordObj) else: for line in f: lineNoSpace = re.sub(r'\s', '', line) hpaiomatched = re.match('hpaio', lineNoSpace) if hpaiomatched: found = True break f.close() if not found: st = os.stat('/etc/sane.d/dll.conf') cmd = self.passwordObj.getAuthCmd() % 'chmod 777 /etc/sane.d/dll.conf' log.debug("cmd=%s" % cmd) utils.run(cmd, self.passwordObj) try: f = open('/etc/sane.d/dll.conf', 'a+') except IOError: log.error( "'/etc/sane.d/dll.conf' not found. Creating dll.conf file") else: f.write('hpaio') f.close() actv_permissions = st.st_mode & 0o777 cmd = 'chmod %o /etc/sane.d/dll.conf' % actv_permissions cmd = self.passwordObj.getAuthCmd() % cmd log.debug("cmd=%s" % cmd) utils.run(cmd, self.passwordObj) return found def check_scanext(self): log.debug("Checking 'scanext' SANE scanning extension...") found = False try: utils.import_ext('scanext') except ImportError: log.error( "NOT FOUND OR FAILED TO LOAD! Please reinstall HPLIP and check for the proper installation of scanext.") else: found = True return found def security_package_status(self): found = ["", False] for key in SEC_DICT.keys(): if glob.glob(SEC_DICT[key][0]): found[0] = key found[1] = all(map(glob.glob, SEC_DICT[key][1])) return found return found def selinux_install(self): src_dir = os.getcwd() profile_location = src_dir + "/selinux/hplip.pp" profile_cmd = "semodule -n -i " + profile_location cmd = self.passwordObj.getAuthCmd() % profile_cmd log.info("Installing SELinux profile...") status, output = utils.run(cmd, self.passwordObj) def get_hplip_version(self): self.version_description, self.version_public, self.version_internal = '', '', '' if self.mode == MODE_INSTALLER: ac_init_pat = re.compile( r"""AC_INIT\(\[(.*?)\], *\[(.*?)\], *\[(.*?)\], *\[(.*?)\] *\)""", re.IGNORECASE) try: config_in = open('./configure.in', 'r') except IOError: self.version_description, self.version_public, self.version_internal = \ '', sys_conf.get('configure', 'internal-tag', '0.0.0'), prop.installed_version else: for c in config_in: if c.startswith("AC_INIT"): match_obj = ac_init_pat.search(c) self.version_description = match_obj.group(1) self.version_public = match_obj.group(2) self.version_internal = match_obj.group(3) name = match_obj.group(4) break config_in.close() if name != 'hplip': log.error("Invalid archive!") else: # MODE_CHECK try: self.version_description, self.version_public, self.version_internal = \ '', sys_conf.get('configure', 'internal-tag', '0.0.0'), prop.installed_version except KeyError: self.version_description, self.version_public, self.version_internal = '', '', '' return self.version_description, self.version_public, self.version_internal def configure(self, bClassDriver): configure_cmd = './configure' configuration = {} if PY3: dbus_avail = self.have_dependencies[ 'dbus'] and self.have_dependencies['python3-dbus'] else: dbus_avail = self.have_dependencies[ 'dbus'] and self.have_dependencies['python-dbus'] configuration['network-build'] = self.selected_options['network'] if bClassDriver: configuration['scan-build'] = False configuration['fax-build'] = False configuration['dbus-build'] = False configuration['qt4'] = False configuration['qt5'] = False configuration['class-driver'] = True else: configuration['scan-build'] = self.selected_options['scan'] configuration[ 'fax-build'] = self.selected_options['fax'] and dbus_avail configuration['dbus-build'] = dbus_avail configuration['qt4'] = self.selected_options['gui_qt4'] configuration['qt5'] = self.selected_options['gui_qt5'] configuration['class-driver'] = self.selected_options[ 'class-driver'] configuration['doc-build'] = self.selected_options['docs'] configuration['policykit'] = self.selected_options['policykit'] configuration['libusb01_build'] = self.selected_options['libusb01'] configuration['udev_sysfs_rules'] = self.selected_options[ 'udev_sysfs_rule'] # Setup printer driver configure flags based on distro data... if self.native_cups: # hpcups configuration['hpcups-install'] = True configuration['hpijs-install'] = False configuration['foomatic-ppd-install'] = False configuration['foomatic-drv-install'] = False if self.enable_ppds: configuration['cups-ppd-install'] = True configuration['cups-drv-install'] = False else: configuration['cups-ppd-install'] = False configuration['cups-drv-install'] = True else: # HPIJS/foomatic configuration['hpcups-install'] = False configuration['hpijs-install'] = True configuration['cups-ppd-install'] = False configuration['cups-drv-install'] = False if self.enable_ppds: configuration['foomatic-ppd-install'] = True configuration['foomatic-drv-install'] = False else: configuration['foomatic-ppd-install'] = False configuration['foomatic-drv-install'] = True # ... and then override and adjust for consistency with passed in parameters if self.enable is not None: for c in self.enable: if c == 'hpcups-install': configuration['hpijs-install'] = False configuration['foomatic-ppd-install'] = False configuration['foomatic-drv-install'] = False elif c == 'hpijs-install': configuration['hpcups-install'] = False configuration['cups-ppd-install'] = False configuration['cups-drv-install'] = False elif c == 'foomatic-ppd-install': configuration['foomatic-drv-install'] = False elif c == 'foomatic-drv-install': configuration['foomatic-ppd-install'] = False elif c == 'cups-ppd-install': configuration['cups-drv-install'] = False elif c == 'cups-drv-install': configuration['cups-ppd-install'] = False if self.disable is not None: for c in self.disable: if c == 'hpcups-install': configuration['hpijs-install'] = True configuration['cups-ppd-install'] = False configuration['cups-drv-install'] = False elif c == 'hpijs-install': configuration['hpcups-install'] = True configuration['foomatic-ppd-install'] = False configuration['foomatic-drv-install'] = False elif c == 'foomatic-ppd-install': configuration['foomatic-drv-install'] = True elif c == 'foomatic-drv-install': configuration['foomatic-ppd-install'] = True elif c == 'cups-ppd-install': configuration['cups-drv-install'] = True elif c == 'cups-drv-install': configuration['cups-ppd-install'] = True if self.ppd_dir is not None: configure_cmd += ' --with-hpppddir=%s' % self.ppd_dir libdir_path = self.get_distro_ver_data('libdir_path', False) if libdir_path and self.bitness == 64: configure_cmd += ' --libdir=%s' % (libdir_path) elif self.bitness == 64: configure_cmd += ' --libdir=/usr/lib64' configure_cmd += ' --prefix=%s' % self.install_location if self.get_distro_ver_data('cups_path_with_bitness', False) and self.bitness == 64: configure_cmd += ' --with-cupsbackenddir=/usr/lib64/cups/backend --with-cupsfilterdir=/usr/lib64/cups/filter' if self.enable is not None: for c in self.enable: configuration[c] = True if self.disable is not None: for c in self.disable: configuration[c] = False for c in configuration: if configuration[c]: configure_cmd += ' --enable-%s' % c else: configure_cmd += ' --disable-%s' % c # For AppArmor Profiles if self.security_package == "AppArmor": configure_cmd += ' --enable-apparmor_build' if self.security_package == "SELinux": configure_cmd += ' --enable-selinux_build' # For Unit/Functional testing changes. if ".internal" in prop.version and os.path.exists('testcommon/'): configure_cmd += ' --enable-hplip_testing_flag' return configure_cmd def configure_html(self): configure_cmd = './configure' configure_cmd += ' --prefix=/usr' configure_cmd += ' --with-hpppddir=%s' % self.ppd_dir libdir_path = self.get_distro_ver_data('libdir_path', False) if libdir_path and self.bitness == 64: configure_cmd += ' --libdir=%s' % (libdir_path) elif self.bitness == 64: configure_cmd += ' --libdir=/usr/lib64' self.ui_toolkit = self.get_distro_ver_data('ui_toolkit') if self.ui_toolkit is not None and self.ui_toolkit == 'qt3': configure_cmd += ' --enable-qt3 --disable-qt4' else: configure_cmd += ' --enable-qt4' self.native_cups = self.get_distro_ver_data('native_cups') if self.native_cups is not None and self.native_cups == 1: if self.enable_ppds: configure_cmd += ' --enable-hpcups-install --disable-cups-drv-install --enable-cups-ppd-install --disable-hpijs-install --disable-foomatic-drv-install --disable-foomatic-ppd-install --disable-foomatic-rip-hplip-install' else: configure_cmd += ' --enable-hpcups-install --enable-cups-drv-install --disable-cups-ppd-install --disable-hpijs-install --disable-foomatic-drv-install --disable-foomatic-ppd-install --disable-foomatic-rip-hplip-install' else: configure_cmd += ' --disable-hpcups-install --disable-cups-drv-install --disable-cups-ppd-install --enable-hpijs-install --enable-foomatic-drv-install --enable-foomatic-ppd-install --enable-foomatic-rip-hplip-install' self.fax_supported = self.get_distro_ver_data('fax_supported') if self.fax_supported is None: configure_cmd += ' --disable-fax-build --disable-dbus-build' else: configure_cmd += ' --enable-fax-build --enable-dbus-build' self.network_supported = self.get_distro_ver_data('network_supported') if self.network_supported is None: configure_cmd += ' --disable-network-build' else: configure_cmd += ' --enable-network-build' self.scan_supported = self.get_distro_ver_data('scan_supported') if self.scan_supported is None: configure_cmd += ' --disable-scan-build' else: configure_cmd += ' --enable-scan-build' self.policykit = self.get_distro_ver_data('policykit') if self.policykit is not None and self.policykit == 1: configure_cmd += ' --enable-policykit' else: configure_cmd += ' --disable-policykit' self.libusb01 = self.get_distro_ver_data('libusb01') if self.libusb01 is not None and self.libusb01 == 1: configure_cmd += ' --enable-libusb01_build' else: configure_cmd += ' --disable-libusb01_build' self.udev_sysfs_rule = self.get_distro_ver_data('udev_sysfs_rule') if self.udev_sysfs_rule is not None and self.udev_sysfs_rule == 1: configure_cmd += ' --enable-udev_sysfs_rules' else: configure_cmd += ' --disable-udev_sysfs_rules' configure_cmd += ' --enable-doc-build' return configure_cmd def build_cmds(self, bClassDriver, option): if option == 'i': cmnd = "make install" log.info("cmnd:%s" % cmnd) return [self.configure(bClassDriver), 'make clean', 'make', self.passwordObj.getAuthCmd() % cmnd] elif option == 't': cmnd = "make dist" log.info("cmnd:%s" % cmnd) return [self.configure(bClassDriver), 'make clean', 'make', cmnd] elif option == 'r': cmnd = "make rpm" log.info("cmnd:%s" % cmnd) return [self.configure(bClassDriver), 'make clean', 'make', cmnd] elif option == 'b': cmnd = "make deb" log.info("cmnd:%s" % cmnd) return [self.configure(bClassDriver), 'make clean', 'make', self.passwordObj.getAuthCmd() % cmnd] elif option == 'd': return [self.configure(bClassDriver), 'make clean', 'make', self.passwordObj.getAuthCmd() % 'make install'] else: return [self.configure(bClassDriver), 'make clean', 'make', self.passwordObj.getAuthCmd() % 'make install'] def get_distro_ver_data(self, key, default=None, distro_ver=None): try: if distro_ver: return self.distros[self.distro_name]['versions'][distro_ver].get(key, None) or \ self.distros[self.distro_name].get(key, None) or default else: return self.distros[self.distro_name]['versions'][self.distro_version].get(key, None) or \ self.distros[self.distro_name].get(key, None) or default except KeyError: return default return value def get_distro_data(self, key, default=None): try: return self.distros[self.distro_name].get(key, None) or default except KeyError: return default def get_ver_data(self, key, default=None, distro_ver=None): try: if distro_ver: return self.distros[self.distro_name]['versions'][distro_ver].get(key, None) or default else: return self.distros[self.distro_name]['versions'][self.distro_version].get(key, None) or default except KeyError: return default return value def get_dependency_data(self, dependency, supported_distro_vrs=None): dependency_cmds = self.get_ver_data( "dependency_cmds", {}, supported_distro_vrs) dependency_data = dependency_cmds.get(dependency, {}) packages = dependency_data.get('packages', []) commands = dependency_data.get('commands', []) return packages, commands def get_dependency_commands(self): dd = list(self.dependencies.keys()) dd.sort() commands_to_run = [] packages_to_install = [] overall_commands_to_run = [] for d in dd: include = False for opt in self.dependencies[d][1]: if self.selected_options[opt]: include = True if include: pkgs, cmds = self.get_dependency_data(d) if pkgs: for p in pkgs: if not p in packages_to_install: packages_to_install.append(p) if cmds: commands_to_run.extend(cmds) package_mgr_cmd = self.get_distro_ver_data('package_mgr_cmd') overall_commands_to_run.extend(commands_to_run) if package_mgr_cmd: packages_to_install = ' '.join(packages_to_install) overall_commands_to_run.append(utils.cat(package_mgr_cmd)) if not overall_commands_to_run: log.error("No cmds/pkgs") return overall_commands_to_run def distro_known(self): return self.distro != DISTRO_UNKNOWN and self.distro_version != DISTRO_VER_UNKNOWN def distro_supported(self): if self.mode == MODE_INSTALLER: return self.distro != DISTRO_UNKNOWN and self.distro_version != DISTRO_VER_UNKNOWN and self.get_ver_data('supported', False) else: return True # For docs (manual install) def count_num_required_missing_dependencies(self): num_req_missing = 0 for d, desc, opt in self.missing_required_dependencies(): num_req_missing += 1 return num_req_missing def count_num_optional_missing_dependencies(self): num_opt_missing = 0 for d, desc, req, opt in self.missing_optional_dependencies(): num_opt_missing += 1 return num_opt_missing # missing req. deps for selected components def missing_required_dependencies(self): for comp in self.components[self.selected_component][1]: if self.selected_options[comp]: # if the component was selected # dependencies for this component for dep in self.options[comp][2]: # Is it required dependency? if self.dependencies[dep][DEPENDENCY_REQUIRED_INDEX]: # Is it not already installed? if not self.have_dependencies[dep]: log.debug("Missing required dependency: %s" % dep) yield dep, self.dependencies[dep][DEPENDENCY_DISPLAY_INDEX], comp def missing_optional_dependencies(self): for comp in self.components[self.selected_component][1]: if self.selected_options[comp]: # if the component was selected # dependencies for this component for dep in self.options[comp][2]: # Is it optional dependency? if not self.dependencies[dep][DEPENDENCY_REQUIRED_INDEX]: # Is it not already installed? if not self.have_dependencies[dep]: log.debug("Missing optional dependency: %s" % dep) yield dep, self.dependencies[dep][DEPENDENCY_DISPLAY_INDEX], self.dependencies[dep][0], comp def select_options(self, answer_callback): num_opt_missing = 0 # not-required options for opt in self.components[self.selected_component][1]: if opt.find("gui_") != -1 and opt.find(self.ui_toolkit) == -1: continue if not self.options[opt][0]: # not required default = 'y' if not self.selected_options[opt]: default = 'n' self.selected_options[opt] = answer_callback( opt, self.options[opt][1], default) if self.selected_options[opt]: # only for options that are ON for d in self.options[opt][2]: # dependencies if not self.have_dependencies[d]: # missing dependency log.debug("Missing optional dependency: %s" % d) num_opt_missing += 1 return num_opt_missing def check_wget(self): if utils.which("wget"): return True else: log.debug("wget is not installed") return False def check_avahi_utils(self): if utils.which("avahi-browse"): return True else: log.debug("avahi-browse is not installed") return False ''' def check_passwd_util(self): if utils.which("gksu"): return True elif utils.which("kdesu"): return True elif utils.which("kdesudo"): return True else: log.debug("GUI password gksu/kdesu/kdesudo utility is not installed") return False''' def run_pre_install(self, callback=None, distro_ver=None): pre_cmd = self.get_distro_ver_data('pre_install_cmd', None, distro_ver) log.debug(pre_cmd) if pre_cmd: x = 1 for cmd in pre_cmd: status, output = utils.run(cmd, self.passwordObj) if status != 0: log.warn("An error occurred running '%s'" % cmd) if callback is not None: callback(cmd, "Pre-install step %d" % x) x += 1 return True else: return False def remove_default_hplip_libs(self, callback=None, distro_ver=None): hp_lib_rm_cmd = self.get_distro_ver_data('hp_libs_remove_cmd', None, distro_ver) log.debug(hp_lib_rm_cmd) print(hp_lib_rm_cmd) if hp_lib_rm_cmd: x = 1 #for cmd in hp_lib_rm_cmd: status, output = utils.run(hp_lib_rm_cmd, self.passwordObj) if any(['yum' in hp_lib_rm_cmd,'zypper' in hp_lib_rm_cmd, 'dnf' in hp_lib_rm_cmd, 'pacman' in hp_lib_rm_cmd]): if status == 1: log.warn("An error occurred running '%s'" % hp_lib_rm_cmd) else: if status != 0: log.warn("An error occurred running '%s'" % hp_lib_rm_cmd) if callback is not None: callback(hp_lib_rm_cmd, " hp_libs_remove step %d" % x) x += 1 def run_pre_depend(self, callback=None, distro_ver=None): pre_cmd = self.get_distro_ver_data('pre_depend_cmd', None, distro_ver) log.debug(pre_cmd) if pre_cmd: x = 1 for cmd in pre_cmd: status, output = utils.run(cmd, self.passwordObj) if any(['yum' in cmd, 'zypper' in cmd, 'dnf' in cmd, 'pacman' in cmd]): if status == 1: log.warn("An error occurred running '%s'" % cmd) else: if status != 0: log.warn("An error occurred running '%s'" % cmd) if callback is not None: callback(cmd, "Pre-depend step %d" % x) x += 1 def run_post_depend(self, callback=None, distro_ver=None): post_cmd = self.get_distro_ver_data( 'post_depend_cmd', None, distro_ver) log.debug(post_cmd) if post_cmd: x = 1 for cmd in post_cmd: status, output = utils.run(cmd, self.passwordObj) if status != 0: log.warn("An error occurred running '%s'" % cmd) if callback is not None: callback(cmd, "Post-depend step %d" % x) x += 1 def run_scanjet_depend(self, callback=None, distro_ver=None): from base.sixext import PY3 if PY3: scanjet_cmd = self.get_distro_ver_data('scanjet_py3_depend_cmd', None, distro_ver) else: scanjet_cmd = self.get_distro_ver_data('scanjet_depend_cmd', None, distro_ver) log.debug(scanjet_cmd) if scanjet_cmd: x = 1 #log.info("x is %d"%x) for cmd in scanjet_cmd: #log.info("cmd is %s"%cmd) if callback is not None: callback(cmd, "Scanjet-depend step %d" % x) status, output = utils.run(cmd, self.passwordObj) #log.info("status is %d"%status) if status !=0: log.warn("Failed to install this Scanjet dependency package. Some Scanjet features will not work.") #if callback is not None: #callback(cmd, "Scanjet-depend step %d" % x) x += 1 '''if status !=0: sys.exit(0)''' def pre_build(self, distro_ver=None): cmds = [] if self.get_distro_ver_data('fix_ppd_symlink', False, distro_ver): cmds.append(self.passwordObj.getAuthCmd() % 'python ./installer/fix_symlink.py') return cmds def run_pre_build(self, callback=None, distro_ver=None): x = 1 for cmd in self.pre_build(distro_ver): status, output = utils.run(cmd, self.passwordObj) if callback is not None: callback(cmd, "Pre-build step %d" % x) x += 1 def run_post_build(self, callback=None, distro_ver=None): x = 1 for cmd in self.post_build(distro_ver): status, output = utils.run(cmd, self.passwordObj) if callback is not None: callback(cmd, "Post-build step %d" % x) x += 1 def post_build(self, distro_ver=None): cmds = [] # Reload DBUS configuration if distro supports it and PolicyKit # support installed if self.reload_dbus and self.selected_options['policykit']: cmds.append(self.passwordObj.getAuthCmd() % "sh /etc/init.d/dbus reload") log.debug("Will reload DBUS configuration for PolicyKit support") # Kill any running hpssd.py instance from a previous install pid_list = get_ps_pid(['hp-systray', 'hpssd']) kill_cmd = utils.which("kill", True) for pid in pid_list: log.debug("Found %s for %s process" % (pid, pid_list[pid])) kill = kill_cmd + " %s" % pid cmds.append(self.passwordObj.getAuthCmd() % kill) return cmds def remove_soT(self): #log.info("\n Clearing unnecessary sos: ") run_cmd = 'rm -rf .libs/libhpipp.so.0.0.1T .libs/libsane-hpaio.so.1.0.0T .libs/libhpmud.so.0.0.6T .libs/hpmudext.soT .libs/cupsext.soT' cmd = self.passwordObj.getAuthCmd() % run_cmd #run_cmd.append(self.passwordObj.getAuthCmd() % "rm -rf .libs/libhpipp.so.0.0.1T .libs/libsane-hpaio.so.1.0.0T .libs/libhpmud.so.0.0.6T .libs/hpmudext.soT .libs/cupsext.soT") #self.passwordObj.getAuthCmd() % run_cmd status, output = utils.run(cmd, self.passwordObj) def remove_hplip(self, callback=None): failed = True hplip_remove_cmd = self.get_distro_ver_data('hplip_remove_cmd') if hplip_remove_cmd: if callback is not None: callback(hplip_remove_cmd, "Removing old HPLIP version") status, output = utils.run(hplip_remove_cmd, self.passwordObj) if status == 0: self.hplip_present = self.check_hplip() if not self.hplip_present: failed = False return failed def check_password(self): self.passwordObj.clearPassword() if self.passwordObj.getPassword() == "": return False else: return True # PLUGIN HELPERS def isErrorPage(self, page): """ Example code from David Mertz' Text Processing in Python. Released in the Public Domain. """ err_score = 0.0 for pat, prob in list(err_pats.items()): if err_score > 0.9: break if re.search(pat, page): err_score += prob log.debug("File error page score: %f" % (err_score)) return err_score > 0.50 def validate_disto(self): if self.distro != DISTRO_UNKNOWN: return True else: return True def validate_distro_version(self): # It's shipped in Debian. It's supported. return True def is_auto_installer_support(self, distro_version=DISTRO_VER_UNKNOWN): # No auto install ever. return False # Uninstalls the HPLIP package. # Input: # mode --> INTERACTIVE_MODE, GUI_MODE # # Output: # result --> returns True on success. def uninstall(self, mode=INTERACTIVE_MODE, callback=None): checkSudo = False if os.getuid() != 0: checkSudo = True # log.error("To run 'hp-uninstall' utility, you must have root privileges.") # return False home_dir = sys_conf.get("dirs", "home", "") version = sys_conf.get("hplip", "version", "0.0.0") if home_dir == "": log.error("HPLIP is not installed.") return False if mode != NON_INTERACTIVE_MODE: ok, choice = tui.enter_choice( "\nAre you sure to uninstall HPLIP-%s (y=yes, n=no*)?:" % version, ['y', 'n'], 'n') if not ok or choice == 'n': return False hplip_remove_cmd = self.get_distro_data('hplip_remove_cmd') log.debug("hplip_remove_cmd =%s " % hplip_remove_cmd) # read conf file to enter into installed dir log.info("Starting uninstallation...") plugin_state = sys_state.get( 'plugin', 'installed', PLUGIN_NOT_INSTALLED) # check systray is running? status, output = utils.Is_Process_Running('hp-systray') if status is True: if mode != NON_INTERACTIVE_MODE: ok, choice = tui.enter_choice( "\nSome HPLIP applications are running. Press 'y' to close and proceed or Press 'n' to quit uninstall (y=yes*, n=no):", ['y', 'n'], 'y') if not ok or choice == 'n': log.info( "Quiting HPLIP unininstallation. Close application(s) manually and run again.") return False # Kill any running hpssd.py instance from a previous install pid_list = get_ps_pid(['hp-systray']) kill_cmd = utils.which("kill", True) for pid in pid_list: log.debug("Found %s for %s process" % (pid, pid_list[pid])) kill = kill_cmd + " %s" % pid sts, out = utils.run(kill) log.debug("sts =%s out=%s" % (sts, out)) toolbox_status, output = utils.Is_Process_Running('hp-toolbox') systray_status, output = utils.Is_Process_Running('hp-systray') if toolbox_status is True or systray_status is True: log.error( "Failed to close HP-Toolbox/HP-Systray. Close manually and run hp-uninstall again.") return False if hplip_remove_cmd: User_exit, Is_pkg_mgr_running = self.close_package_managers() if User_exit: sys.exit(0) self.remove_hplip(callback) # removing .hplip directory cmd = 'find /home -name .hplip' if checkSudo: cmd = self.passwordObj.getAuthCmd() % cmd status, output = utils.run(cmd, self.passwordObj) if output is not None: for p in output.splitlines(): if p.find("find:") != -1: continue utils.remove(p, self.passwordObj, checkSudo) # Removing Security profiles/policies package_st = self.security_package_status() if package_st[1]: log.debug("Removing Security Profiles") [utils.remove(f, self.passwordObj, checkSudo) for f in SEC_DICT[package_st[0]][1]] # remove the binaries and libraries pat = re.compile(r"""(\S.*)share\/hplip""") base = pat.match(home_dir) usrbin_dir = None if base is not None: usrbin_dir = base.group(1) + "bin/" usrlib_dir = base.group(1) + "lib/" cnt = 0 BINS_LIST_FULL = utils.expandList(BINS_LIST, usrbin_dir) while cnt < len(BINS_LIST_FULL): utils.remove(BINS_LIST_FULL[cnt], self.passwordObj, checkSudo) cnt += 1 cnt = 0 LIBS_LIST_FULL = utils.expandList(LIBS_LIST, usrlib_dir) while cnt < len(LIBS_LIST_FULL): utils.remove(LIBS_LIST_FULL[cnt], self.passwordObj, checkSudo) cnt += 1 remove_plugins = False if mode != NON_INTERACTIVE_MODE and plugin_state != PLUGIN_NOT_INSTALLED: ok, choice = tui.enter_choice( "\nDo you want to remove HP proprietary plug-ins (y=yes*, n=no)?:", ['y', 'n'], 'y') if ok and choice == 'y': remove_plugins = True else: remove_plugins = True # removing HPLIP installed directories/files if remove_plugins is False: HPLIP_LIST_FULL = utils.expandList(HPLIP_LIST, home_dir) else: HPLIP_LIST_FULL = [] cnt = 0 while cnt < len(HPLIP_LIST_FULL): utils.remove(HPLIP_LIST_FULL[cnt], self.passwordObj, checkSudo) cnt += 1 # removing ppd directory ppd_dir = sys_conf.get('dirs', 'ppd', '') if ppd_dir: utils.remove(ppd_dir, self.passwordObj, checkSudo) # removing configuration files FILES_LIST_FULL = utils.expandList(FILES_LIST) cnt = 0 while cnt < len(FILES_LIST_FULL): utils.remove(FILES_LIST_FULL[cnt], self.passwordObj, checkSudo) cnt += 1 # removing Rules files RULES_LIST_FULL = utils.expandList(RULES_LIST, '/etc/udev/rules.d') for fl in RULES_LIST_FULL: utils.remove(fl, self.passwordObj, checkSudo) RULES_LIST_FULL = utils.expandList(RULES_LIST, '/lib/udev/rules.d') for fl in RULES_LIST_FULL: utils.remove(fl, self.passwordObj, checkSudo) # removing (unused) hplip folder from other location cmd = 'find /usr -type d -name hplip' cmd = self.passwordObj.getAuthCmd() % cmd status, output = utils.run(cmd, self.passwordObj, checkSudo) if status == 0: hplip_folders = output.splitlines() for hplip_d in hplip_folders: if hplip_d != home_dir: utils.remove(hplip_d, self.passwordObj, checkSudo) # removing all hplip extension libraries for ext_f in HPLIP_EXT_LIST: if ext_f: cmd = 'find /usr -type f -name %s -delete' % ext_f cmd = self.passwordObj.getAuthCmd() % cmd status, output = utils.run(cmd, self.passwordObj, checkSudo) if status != 0: log.warn( "Failed to delete %s library [%s]" % (ext_f, output)) # removing Plug-in files if remove_plugins == True: cnt = 0 PLUGIN_LIST_FULL = utils.expandList(PLUGIN_LIST, home_dir) while cnt < len(PLUGIN_LIST_FULL): utils.remove(PLUGIN_LIST_FULL[cnt], self.passwordObj, checkSudo) cnt += 1 cnt = 0 PLUGIN_STATE_FULL = utils.expandList(PLUGIN_STATE) while cnt < len(PLUGIN_STATE_FULL): utils.remove(PLUGIN_STATE_FULL[ cnt], self.passwordObj, checkSudo) cnt += 1 utils.remove(home_dir, self.passwordObj, checkSudo) # removing HPLIP uninstall link if usrbin_dir is not None: hp_uninstall = usrbin_dir + "hp-unistall" utils.remove(hp_uninstall, self.passwordObj, checkSudo) log.info("HPLIP uninstallation is completed") return True # close_package_managers() closes the package managers, if running # Input: # MODE --> INTERACTIVE_MODE, GUI_MODE (GUI_MODE is not yet supported). # Output: # User_exit (bool) --> returns True, if user quits. # --> returns False, if user doesn't select quit option. # Is_pkg_mgr_running (bool) -->returns False, if no packages are running at end of function. # -->returns True, if some package(s) is(are) running at end of function. def close_package_managers(self, MODE=INTERACTIVE_MODE): User_exit = False Is_pkg_mgr_running = False pid, cmdline = utils.check_pkg_mgr(self.package_mgrs) while pid: if MODE == INTERACTIVE_MODE: ok, user_input = tui.enter_choice( "A package manager '%s' appears to be running. Please quit the package manager and press enter to continue (i=ignore, r=retry*, f=force, q=quit) :" % cmdline, ['i', 'r', 'q', 'f'], 'r') if not ok: return True, True # --> User_exit = True , Is_pkg_mgr_running =True if user_input == 'i': log.warn( "Ignoring running package manager. Some package operations may fail.") break if user_input == 'f': ok, ans = tui.enter_yes_no( "\nForce quit of package manager '%s'" % cmdline, 'y') if not ok: return True, True # --> User_exit = True , Is_pkg_mgr_running =True if ans: cmd = self.passwordObj.getAuthCmd() % ("kill %s" % pid) status, output = utils.run(cmd, self.passwordObj) if status != 0: log.error( "Failed to kill process. You may need to manually quit the program.") else: log.error("GUI is not yet supported") # TBD break pid, cmdline = utils.check_pkg_mgr(self.package_mgrs) if pid: # checking for still running package managers Is_pkg_mgr_running = True return User_exit, Is_pkg_mgr_running # add_groups_to_user() # Input: # missing_user_groups (string) --> Contains only missing groups, to show to user. # missing_user_groups_cmd (string) --> command as per distro.dat (i.e. add_user_to_group) # mode --> INTERACTIVE_MODE, GUI_MODE (GUI_MODE is not yet supported). # Output: # ret_val (bool) --> returns True, if succeeded to add groups to user. # --> returns False, if Failed to add groups to user. # Move to utils def add_groups_to_user(self, missing_user_groups, missing_user_groups_cmd, mode=INTERACTIVE_MODE): ret_val = False if mode == INTERACTIVE_MODE: if not missing_user_groups or not missing_user_groups_cmd: return False ok, user_input = tui.enter_choice( "Do you want to add missing groups %s to user?(y=yes*, n=no)" % missing_user_groups, ['y', 'n'], 'y') if ok and user_input == 'y': usermod_path = utils.which('usermod', True) if usermod_path: cmd = "%s %s %s" % ( usermod_path, missing_user_groups_cmd, prop.username) cmd = self.passwordObj.getAuthCmd() % cmd log.debug("cmd = %s" % cmd) sts, out = utils.run(cmd, self.passwordObj) if sts == 0: ret_val = True else: log.error("usermod command not found.") else: log.info(log.bold("Please add %s groups to %s user" % (missing_user_groups, prop.username))) else: log.error("GUI is not yet supported") # TBD return ret_val # disable_SELinux() # Input: # MODE --> INTERACTIVE_MODE, GUI_MODE (GUI_MODE is not yet supported). # Output: # ret_val (bool) --> returns True, if succeeded to disable SELinux. # --> returns False, if Failed to disable SELinux. def disable_SELinux(self, mode=INTERACTIVE_MODE): # Move to utils ret_val = False SELinux_file = '/etc/selinux/config' if mode == INTERACTIVE_MODE: ok, user_input = tui.enter_choice( "SELinux is currently enabled in your system. Device may not work properly. Do you want to disable SELinux?(y=yes, n=no*)", ['y', 'n'], 'n') if ok and user_input != 'n': if not os.path.exists(SELinux_file): log.debug("File %s is not found" % SELinux_file) return False cmd = self.passwordObj.getAuthCmd() % ( "vi -c %s/enforcing$/disabled -c wq " + SELinux_file) log.debug("cmd= %s " % cmd) sts, out = utils.run(cmd, self.passwordObj) if sts == 0: ret_val = True if os.path.exists('/selinux/enforce'): cmd = "echo 0 >/selinux/enforce" cmd = self.passwordObj.getAuthCmd() % cmd log.debug("cmd= %s " % cmd) # utils.run(cmd, self.passwordObj) os_utils.execute(cmd) else: log.error("GUI is not yet supported") # TBD return ret_val # Move to core_install def install_missing_dependencies(self, mode=INTERACTIVE_MODE, required_dependencies=[], optional_dependencies=[], missing_cmd=[]): package_mgr_cmd = self.get_distro_ver_data('package_mgr_cmd') pre_depend_cmd = self.get_distro_ver_data('pre_depend_cmd') overall_install_cmds = {} if len(required_dependencies): for packages_to_install in required_dependencies: if package_mgr_cmd: overall_install_cmds[ packages_to_install] = utils.cat(package_mgr_cmd) else: overall_install_cmds[ packages_to_install] = packages_to_install if len(optional_dependencies): for packages_to_install in optional_dependencies: if package_mgr_cmd: overall_install_cmds[ packages_to_install] = utils.cat(package_mgr_cmd) else: overall_install_cmds[ packages_to_install] = packages_to_install if len(overall_install_cmds) == 0 and len(missing_cmd) == 0: log.info("No missing dependencies") return 0 # Do not allow HPLIP to run APT or anything else, especially not as root. return 0