__pycache__/__init__.cpython-36.opt-1.pyc000064400000000161147204717450014111 0ustar003 uAc@sdS)Nrrr/usr/lib/python3.6/__init__.pys__pycache__/__init__.cpython-36.pyc000064400000000161147204717450013152 0ustar003 uAc@sdS)Nrrr/usr/lib/python3.6/__init__.pys_wrappers/__pycache__/__init__.cpython-36.opt-1.pyc000064400000000161147204717450016113 0ustar003 uAc@sdS)Nrrr/usr/lib/python3.6/__init__.pys_wrappers/__pycache__/__init__.cpython-36.pyc000064400000000161147204717450015154 0ustar003 uAc@sdS)Nrrr/usr/lib/python3.6/__init__.pys_wrappers/__pycache__/_glib.cpython-36.opt-1.pyc000064400000001250147204717450015430 0ustar003 uAc\ @sdZddlmZddlZdddgZejeZdZxhedkrdejkrPejdZndejkrdejdZedkr2y ddl Z Wq2e k rddl Z Yq2Xq2Wx*eD]"Z e eekreee eee qWdS) zjThis module lets some other slip modules cooperate with either the glib or the gi.repository.GLib modules.)absolute_importNZMainLoopZ source_removeZ timeout_addzgi.repository.GLibglib)__doc__Z __future__rsys__all__modules__name___selfZ_modr ImportErrorZgi.repository.GLibZgiZwhatdirsetattrgetattrrr/usr/lib/python3.6/_glib.pys$           _wrappers/__pycache__/_glib.cpython-36.pyc000064400000001250147204717450014471 0ustar003 uAc\ @sdZddlmZddlZdddgZejeZdZxhedkrdejkrPejdZndejkrdejdZedkr2y ddl Z Wq2e k rddl Z Yq2Xq2Wx*eD]"Z e eekreee eee qWdS) zjThis module lets some other slip modules cooperate with either the glib or the gi.repository.GLib modules.)absolute_importNZMainLoopZ source_removeZ timeout_addzgi.repository.GLibglib)__doc__Z __future__rsys__all__modules__name___selfZ_modr ImportErrorZgi.repository.GLibZgiZwhatdirsetattrgetattrrr/usr/lib/python3.6/_glib.pys$           _wrappers/__init__.py000064400000000000147204717450010660 0ustar00_wrappers/_glib.py000064400000003134147204717450010210 0ustar00# -*- coding: utf-8 -*- # slip._wrappers._glib -- abstract (some) differences between glib and # gi.repository.GLib # # Copyright © 2012, 2015 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module lets some other slip modules cooperate with either the glib or the gi.repository.GLib modules.""" from __future__ import absolute_import import sys __all__ = ['MainLoop', 'source_remove', 'timeout_add'] _self = sys.modules[__name__] _mod = None while _mod is None: if 'gi.repository.GLib' in sys.modules: _mod = sys.modules['gi.repository.GLib'] elif 'glib' in sys.modules: _mod = sys.modules['glib'] # if not yet imported, try to import glib first, then # gi.repository.GLib ... if _mod is None: try: import glib except ImportError: import gi.repository.GLib # ... then repeat. for what in __all__: if what not in dir(_self): setattr(_self, what, getattr(_mod, what)) util/__pycache__/__init__.cpython-36.opt-1.pyc000064400000000345147204717450015072 0ustar003 uAcl@s(ddlmZddlmZddlmZdS))absolute_import)hookable)filesN)Z __future__rrrrr/usr/lib/python3.6/__init__.pys  util/__pycache__/__init__.cpython-36.pyc000064400000000345147204717450014133 0ustar003 uAcl@s(ddlmZddlmZddlmZdS))absolute_import)hookable)filesN)Z __future__rrrrr/usr/lib/python3.6/__init__.pys  util/__pycache__/files.cpython-36.opt-1.pyc000064400000011525147204717450014437 0ustar003 uAc@sdZddlmZdeekr eZdddddgZdd lZdd l Z dd l Z dd l Z dd l Z d Z d d Zgfd dZddZdddZdddZdddZdddZd S)z=This module contains helper functions for dealing with files.)absolute_importxrange issamefilelinkfilecopyfilelinkorcopyfileoverwrite_safelyNicCs"tj|}tj|}tjj||S)N)osstatpathsamestat)path1path2s1s2r/usr/lib/python3.6/files.py _issamefile+s  rc Cs0|dkr t}y t||S|k r*dSXdS)zECheck whether two paths point to the same file (i.e. are hardlinked).TFN) Exceptionr)r rcatch_stat_exceptionsrrrr2s  cCst||tdrdStjj|}tjj|}tjj|}d}xpttj D]b}tj |tj |d}ytj ||Wn2tk r}z|j t jkrnWYdd}~XqFXd}PqFW|rtj||dS)zUHardlink srcpath to dstpath. Attempt to atomically replace dstpath if it exists.)rNF)prefixdirT)rOSErrorr r abspathdirnamebasenamerangetempfileTMP_MAXmktempextseplinkerrnoEEXISTrename)srcpathdstpathdstdnamedstbnameZ hardlinkedattempt_dsttmperrrr>s$    Tc Cs8t||tdrdStjj|}tjj|}tjj|}t|d}tj |tjj |dd}tj |}|rytj |}Wntk rYnXtj |j t j|jd} xP| dkr|jt} y|j| Wq|j|jtj|jYqXqW|j|jtj|j||r4tjdkr4tj|dS)zCopy srcpath to dstpath. Abort operation if e.g. not enough space is available. Attempt to atomically replace dstpath if it exists.)rNrbF)rrdeleter)rrr r rrropenrZNamedTemporaryFiler r fchmodfilenoS_IMODEst_moderead BLOCKSIZEwritecloseunlinknamer$selinuxis_selinux_enabled restorecon) r%r&copy_mode_from_dstrun_restoreconr'r(ZsrcfileZ dsttmpfilesdatarrrr_s<         cCs^yt||dStk rJ}z |jtjtjtjfkr:nWYdd}~XnXt||||dS)ztFirst attempt to hardlink srcpath to dstpath, if hardlinking isn't possible, attempt copying srcpath to dstpath.N)rrr"ZEMLINKZEPERMZEXDEVr)r%r&r=r>r+rrrrs Fc Cstjj|}tjj|}d}d}|r6tjdkr6d}n^y&tj|\}}|dkrZtd|Wn6tk r} z| j t j krd}nWYdd} ~ XnX|stj |||rtj |nd} xtt tjD]f} tj|tj|d} ytj || Wn6tk r"} z| j t jkrwĂWYdd} ~ XqX| } PqW| dkrDtt jd|r^| r^tj| |ytj| |Wntj| YnX|rtj |dS)zpCreate a symlink, optionally replacing dstpath atomically, optionally setting or preserving SELinux context.FNrzgetfilecon(%r) failedT)rrz/No suitable temporary symlink could be created.)r r rrr:r;Z lgetfilecon RuntimeErrorrr"ENOENTsymlinkr<rrrrr r#IOErrorZ lsetfileconr$remove) r%r&forcepreserve_contextr'r(r>ctxretr+Zdsttmpr)r*rrrsymlink_atomicallysV        rJcCs~tjj|}tjj|}tjj|}d}d}d} tjj|} |rPtjdkrPd}ztj |tjj |d\}} | rtj |} |rtj || j | j|rtj|t j| j|rtj|\} } | dkrtd|tj|d}d}|j||jd}tj| ||r$| rtj|| n tj|Wd|r8|jn|rHtj|| rxtjj| rxytj| Wn YnXXdS)zSafely overwrite a file by creating a temporary file in the same directory, writing it, moving it over the original file, eventually preserving file mode, SELinux context and ownership.NrF)rrzgetfilecon(%r) failedw)r r realpathrrexistsr:r;rZmkstempr r fchownst_uidst_gidr0r2r3Z getfileconrAfdopenr6r7r$Z setfileconr<isfiler8)r ZcontentZ preserve_moderGZpreserve_ownershipZdir_basefdfZtmpnamerMr?rIrHrrrrsR            )TT)TT)FT)TTT)__doc__Z __future__rr __builtins__rr__all__r r:rr"r r5rrrrrrJrrrrrs&   ! 5  ?util/__pycache__/files.cpython-36.pyc000064400000011525147204717450013500 0ustar003 uAc@sdZddlmZdeekr eZdddddgZdd lZdd l Z dd l Z dd l Z dd l Z d Z d d Zgfd dZddZdddZdddZdddZdddZd S)z=This module contains helper functions for dealing with files.)absolute_importxrange issamefilelinkfilecopyfilelinkorcopyfileoverwrite_safelyNicCs"tj|}tj|}tjj||S)N)osstatpathsamestat)path1path2s1s2r/usr/lib/python3.6/files.py _issamefile+s  rc Cs0|dkr t}y t||S|k r*dSXdS)zECheck whether two paths point to the same file (i.e. are hardlinked).TFN) Exceptionr)r rcatch_stat_exceptionsrrrr2s  cCst||tdrdStjj|}tjj|}tjj|}d}xpttj D]b}tj |tj |d}ytj ||Wn2tk r}z|j t jkrnWYdd}~XqFXd}PqFW|rtj||dS)zUHardlink srcpath to dstpath. Attempt to atomically replace dstpath if it exists.)rNF)prefixdirT)rOSErrorr r abspathdirnamebasenamerangetempfileTMP_MAXmktempextseplinkerrnoEEXISTrename)srcpathdstpathdstdnamedstbnameZ hardlinkedattempt_dsttmperrrr>s$    Tc Cs8t||tdrdStjj|}tjj|}tjj|}t|d}tj |tjj |dd}tj |}|rytj |}Wntk rYnXtj |j t j|jd} xP| dkr|jt} y|j| Wq|j|jtj|jYqXqW|j|jtj|j||r4tjdkr4tj|dS)zCopy srcpath to dstpath. Abort operation if e.g. not enough space is available. Attempt to atomically replace dstpath if it exists.)rNrbF)rrdeleter)rrr r rrropenrZNamedTemporaryFiler r fchmodfilenoS_IMODEst_moderead BLOCKSIZEwritecloseunlinknamer$selinuxis_selinux_enabled restorecon) r%r&copy_mode_from_dstrun_restoreconr'r(ZsrcfileZ dsttmpfilesdatarrrr_s<         cCs^yt||dStk rJ}z |jtjtjtjfkr:nWYdd}~XnXt||||dS)ztFirst attempt to hardlink srcpath to dstpath, if hardlinking isn't possible, attempt copying srcpath to dstpath.N)rrr"ZEMLINKZEPERMZEXDEVr)r%r&r=r>r+rrrrs Fc Cstjj|}tjj|}d}d}|r6tjdkr6d}n^y&tj|\}}|dkrZtd|Wn6tk r} z| j t j krd}nWYdd} ~ XnX|stj |||rtj |nd} xtt tjD]f} tj|tj|d} ytj || Wn6tk r"} z| j t jkrwĂWYdd} ~ XqX| } PqW| dkrDtt jd|r^| r^tj| |ytj| |Wntj| YnX|rtj |dS)zpCreate a symlink, optionally replacing dstpath atomically, optionally setting or preserving SELinux context.FNrzgetfilecon(%r) failedT)rrz/No suitable temporary symlink could be created.)r r rrr:r;Z lgetfilecon RuntimeErrorrr"ENOENTsymlinkr<rrrrr r#IOErrorZ lsetfileconr$remove) r%r&forcepreserve_contextr'r(r>ctxretr+Zdsttmpr)r*rrrsymlink_atomicallysV        rJcCs~tjj|}tjj|}tjj|}d}d}d} tjj|} |rPtjdkrPd}ztj |tjj |d\}} | rtj |} |rtj || j | j|rtj|t j| j|rtj|\} } | dkrtd|tj|d}d}|j||jd}tj| ||r$| rtj|| n tj|Wd|r8|jn|rHtj|| rxtjj| rxytj| Wn YnXXdS)zSafely overwrite a file by creating a temporary file in the same directory, writing it, moving it over the original file, eventually preserving file mode, SELinux context and ownership.NrF)rrzgetfilecon(%r) failedw)r r realpathrrexistsr:r;rZmkstempr r fchownst_uidst_gidr0r2r3Z getfileconrAfdopenr6r7r$Z setfileconr<isfiler8)r ZcontentZ preserve_moderGZpreserve_ownershipZdir_basefdfZtmpnamerMr?rIrHrrrrsR            )TT)TT)FT)TTT)__doc__Z __future__rr __builtins__rr__all__r r:rr"r r5rrrrrrJrrrrrs&   ! 5  ?util/__pycache__/hookable.cpython-36.opt-1.pyc000064400000013376147204717450015127 0ustar003 uAc^@sldZddlZddlmZddgZGdddeZGdd d eZGd ddeeeZ Gd dde e Z dS) z[This module contains variants of certain base types which call registered hooks on changes.N)with_metaclassHookable HookableSetc@s eZdZddZeddZdS) HookableTypec Csd|kry |d}WnJtk r^d}x0dd|DD]}|rRtdt|q8|}q8WYnXx |dD]}tj||||<qjWtj||||S)N_hookable_change_methodsZ_hookable_base_classcss|]}|tkr|VqdS)N)r).0xr /usr/lib/python3.6/hookable.py )sz'HookableType.__new__..ztoo many base classes: %s)KeyError TypeErrorstrr wrap_methodtype__new__)clsnamebasesZdctbaseZbase_candidate methodnamer r r r"s zHookableType.__new__cs t||fdd}||_|S)Ncs|f||}|j|S)N) _run_hooks)selfpkZretval)funcr r methodwrapper9sz/HookableType.wrap_method..methodwrapper)getattr__name__)rrrrr )rr r5s  zHookableType.wrap_methodN)r __module__ __qualname__r classmethodrr r r r r src@s6eZdZd ddZddZddZdd Zd d ZdS) _HookEntryNc CsxFt|D]:\}}y t|Wq tk rBtd||fYq Xq WxF|jD]:\}}y t|WqRtk rtd||fYqRXqRWt|tst|}||_||_||_||_ d|_ dS)Nz*Positional argument %d is not hashable: %rz'Keyword argument %r is not hashable: %r) enumeratehashr items isinstancetuple_HookEntry__hook_HookEntry__args_HookEntry__kwargs_HookEntry__hookable_HookEntry__hash)rhookargskwargshookablenrrr r r __init__Ds*   z_HookEntry.__init__cCs$|j|jko"|j|jko"|j|jkS)N)r(r)r*)robjr r r __cmp__cs  z_HookEntry.__cmp__cCs|js|j|_|jS)N)r, _compute_hash)rr r r __hash__is z_HookEntry.__hash__cCs>t|j}t|t|jA}t|ttt|jjA}|S)N)r$r(r)r'sortedr*r%)r hashvaluer r r r5ns  z_HookEntry._compute_hashcCs4|jr |j|jf|j|jn|j|j|jdS)N)r+r(r)r*)rr r r runusz_HookEntry.run)N)rrr r2r4r6r5r9r r r r r"Bs  r"c@seZdZdZeddZddZddZeeeZdd Z d d Z ee e Z d d Z ddZ ddZddZddZddZddZdS)rz2An object which calls registered hooks on changes.cOst|dst|_|jS)N__real_hooks__)hasattrsetr:)rrrr r r __hooks__s zHookable.__hooks__cCst|dsd|_|jS)N__hooks_enabled__T)r;r>)rr r r _get_hooks_enableds zHookable._get_hooks_enabledcCs ||_dS)N)r>)rZenabledr r r _set_hooks_enabledszHookable._set_hooks_enabledcCst|dsd|_|jS)N__hooks_frozen__F)r;rA)rr r r _get_hooks_frozens zHookable._get_hooks_frozencCsB||jkrdS||_|r"t|_nx|jD] }|jq*W|`dS)N) hooks_frozenrAr<__hooks_frozen_entries__r9)rZfreeze hookentryr r r _set_hooks_frozens    zHookable._set_hooks_frozencCs d|_dS)NT)rC)rr r r freeze_hooksszHookable.freeze_hookscCs d|_dS)NF)rC)rr r r thaw_hooksszHookable.thaw_hookscOs|j|df||dS)N)_Hookable__add_hook)rr-r.r/r r r add_hookszHookable.add_hookcOs|j||f||dS)N)rI)rr-r.r/r r r add_hook_hookableszHookable.add_hook_hookablecOs t||||d}|jj|dS)N)r0)r"r=add)rr-Z _hookabler.r/rEr r r Z __add_hookszHookable.__add_hookcOs|jjt|||dS)N)r=remover")rr-r.r/r r r remove_hookszHookable.remove_hookcCs8|jr4|js&x&|jD] }|jqWn|jj|jdS)N) hooks_enabledrCr=r9rDupdate)rrEr r r rs  zHookable._run_hooksN)rrr __doc__propertyr=r?r@rOrBrFrCrGrHrJrKrIrNrr r r r r|s   c @seZdZdZdZd d Zd S)rz5A set object which calls registered hooks on changes.rLcleardifference_updatediscardintersection_updatepoprMsymmetric_difference_updaterPcCstj|}t|_|S)N)r<copyr:)rr3r r r rYs zHookableSet.copyN) rLrSrTrUrVrWrMrXrP)rrr rQrrYr r r r rs) rQ collectionsZsixr__all__rrobjectr"rr<rr r r r s ":Gutil/__pycache__/hookable.cpython-36.pyc000064400000013577147204717450014173 0ustar003 uAc^@sldZddlZddlmZddgZGdddeZGdd d eZGd ddeeeZ Gd dde e Z dS) z[This module contains variants of certain base types which call registered hooks on changes.N)with_metaclassHookable HookableSetc@s eZdZddZeddZdS) HookableTypec Csd|kry |d}WnJtk r^d}x0dd|DD]}|rRtdt|q8|}q8WYnXx |dD]}tj||||<qjWtj||||S)N_hookable_change_methodsZ_hookable_base_classcss|]}|tkr|VqdS)N)r).0xr /usr/lib/python3.6/hookable.py )sz'HookableType.__new__..ztoo many base classes: %s)KeyError TypeErrorstrr wrap_methodtype__new__)clsnamebasesZdctbaseZbase_candidate methodnamer r r r"s zHookableType.__new__cs t||fdd}||_|S)Ncs|f||}|j|S)N) _run_hooks)selfpkZretval)funcr r methodwrapper9sz/HookableType.wrap_method..methodwrapper)getattr__name__)rrrrr )rr r5s  zHookableType.wrap_methodN)r __module__ __qualname__r classmethodrr r r r r src@s6eZdZd ddZddZddZdd Zd d ZdS) _HookEntryNc Cst|tjstt|tstxFt|D]:\}}y t|Wq(tk r`td||fYq(Xq(WxF|jD]:\}}y t|Wqptk rtd||fYqpXqpWt|t st |}||_ ||_ ||_ ||_ d|_dS)Nz*Positional argument %d is not hashable: %rz'Keyword argument %r is not hashable: %r) isinstance collectionsCallableAssertionErrorr enumeratehashr itemstuple_HookEntry__hook_HookEntry__args_HookEntry__kwargs_HookEntry__hookable_HookEntry__hash)rhookargskwargshookablenrrr r r __init__Ds.   z_HookEntry.__init__cCs$|j|jko"|j|jko"|j|jkS)N)r+r,r-)robjr r r __cmp__cs  z_HookEntry.__cmp__cCs|js|j|_|jS)N)r/ _compute_hash)rr r r __hash__is z_HookEntry.__hash__cCs>t|j}t|t|jA}t|ttt|jjA}|S)N)r(r+r,r*sortedr-r))r hashvaluer r r r8ns  z_HookEntry._compute_hashcCs4|jr |j|jf|j|jn|j|j|jdS)N)r.r+r,r-)rr r r runusz_HookEntry.run)N)rrr r5r7r9r8r<r r r r r"Bs  r"c@seZdZdZeddZddZddZeeeZdd Z d d Z ee e Z d d Z ddZ ddZddZddZddZddZdS)rz2An object which calls registered hooks on changes.cOst|dst|_|jS)N__real_hooks__)hasattrsetr=)rrrr r r __hooks__s zHookable.__hooks__cCst|dsd|_|jS)N__hooks_enabled__T)r>rA)rr r r _get_hooks_enableds zHookable._get_hooks_enabledcCs ||_dS)N)rA)rZenabledr r r _set_hooks_enabledszHookable._set_hooks_enabledcCst|dsd|_|jS)N__hooks_frozen__F)r>rD)rr r r _get_hooks_frozens zHookable._get_hooks_frozencCsB||jkrdS||_|r"t|_nx|jD] }|jq*W|`dS)N) hooks_frozenrDr?__hooks_frozen_entries__r<)rZfreeze hookentryr r r _set_hooks_frozens    zHookable._set_hooks_frozencCs d|_dS)NT)rF)rr r r freeze_hooksszHookable.freeze_hookscCs d|_dS)NF)rF)rr r r thaw_hooksszHookable.thaw_hookscOs|j|df||dS)N)_Hookable__add_hook)rr0r1r2r r r add_hookszHookable.add_hookcOs|j||f||dS)N)rL)rr0r1r2r r r add_hook_hookableszHookable.add_hook_hookablecOs>t|tjstt|tstt||||d}|jj|dS)N)r3)r#r$r%r&rr"r@add)rr0Z _hookabler1r2rHr r r Z __add_hookszHookable.__add_hookcOs|jjt|||dS)N)r@remover")rr0r1r2r r r remove_hookszHookable.remove_hookcCs8|jr4|js&x&|jD] }|jqWn|jj|jdS)N) hooks_enabledrFr@r<rGupdate)rrHr r r rs  zHookable._run_hooksN)rrr __doc__propertyr@rBrCrRrErIrFrJrKrMrNrLrQrr r r r r|s   c @seZdZdZdZd d Zd S)rz5A set object which calls registered hooks on changes.rOcleardifference_updatediscardintersection_updatepoprPsymmetric_difference_updaterScCstj|}t|_|S)N)r?copyr=)rr6r r r r\s zHookableSet.copyN) rOrVrWrXrYrZrPr[rS)rrr rTrr\r r r r rs) rTr$Zsixr__all__rrobjectr"rr?rr r r r s ":Gutil/__init__.py000064400000000154147204717450007645 0ustar00# -*- coding: utf-8 -*- from __future__ import absolute_import from . import hookable from . import files util/files.py000064400000017257147204717450007224 0ustar00# -*- coding: utf-8 -*- # slip.util.files -- file helper functions # # Copyright © 2009, 2010, 2012, 2015 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains helper functions for dealing with files.""" from __future__ import absolute_import # ensure range() returns a generator if 'xrange' in dir(__builtins__): range = xrange __all__ = ["issamefile", "linkfile", "copyfile", "linkorcopyfile", "overwrite_safely"] import os import selinux import tempfile import errno import stat BLOCKSIZE = 1024 def _issamefile(path1, path2): s1 = os.stat(path1) s2 = os.stat(path2) return os.path.samestat(s1, s2) def issamefile(path1, path2, catch_stat_exceptions=[]): """Check whether two paths point to the same file (i.e. are hardlinked).""" if catch_stat_exceptions is True: catch_stat_exceptions = Exception try: return _issamefile(path1, path2) except catch_stat_exceptions: return False def linkfile(srcpath, dstpath): """Hardlink srcpath to dstpath. Attempt to atomically replace dstpath if it exists.""" if issamefile(srcpath, dstpath, catch_stat_exceptions=OSError): return dstpath = os.path.abspath(dstpath) dstdname = os.path.dirname(dstpath) dstbname = os.path.basename(dstpath) hardlinked = False for attempt in range(tempfile.TMP_MAX): _dsttmp = tempfile.mktemp(prefix=dstbname + os.extsep, dir=dstdname) try: os.link(srcpath, _dsttmp) except OSError as e: if e.errno == errno.EEXIST: # try another name pass else: raise else: hardlinked = True break if hardlinked: os.rename(_dsttmp, dstpath) def copyfile(srcpath, dstpath, copy_mode_from_dst=True, run_restorecon=True): """Copy srcpath to dstpath. Abort operation if e.g. not enough space is available. Attempt to atomically replace dstpath if it exists.""" if issamefile(srcpath, dstpath, catch_stat_exceptions=OSError): return dstpath = os.path.abspath(dstpath) dstdname = os.path.dirname(dstpath) dstbname = os.path.basename(dstpath) srcfile = open(srcpath, "rb") dsttmpfile = tempfile.NamedTemporaryFile( prefix=dstbname + os.path.extsep, dir=dstdname, delete=False) s = os.stat(srcpath) if copy_mode_from_dst: # attempt to copy mode from destination file (if it exists, # otherwise fall back to copying it from the source file below) try: s = os.stat(dstpath) except OSError: pass os.fchmod(dsttmpfile.fileno(), stat.S_IMODE(s.st_mode)) data = None while data != "": data = srcfile.read(BLOCKSIZE) try: dsttmpfile.write(data) except: srcfile.close() dsttmpfile.close() os.unlink(dsttmpfile.name) raise srcfile.close() dsttmpfile.close() os.rename(dsttmpfile.name, dstpath) if run_restorecon and selinux.is_selinux_enabled() > 0: selinux.restorecon(dstpath) def linkorcopyfile( srcpath, dstpath, copy_mode_from_dst=True, run_restorecon=True): """First attempt to hardlink srcpath to dstpath, if hardlinking isn't possible, attempt copying srcpath to dstpath.""" try: linkfile(srcpath, dstpath) return except OSError as e: if e.errno not in (errno.EMLINK, errno.EPERM, errno.EXDEV): # don't bother copying raise else: # try copying pass copyfile(srcpath, dstpath, copy_mode_from_dst, run_restorecon) def symlink_atomically(srcpath, dstpath, force=False, preserve_context=True): """Create a symlink, optionally replacing dstpath atomically, optionally setting or preserving SELinux context.""" dstdname = os.path.dirname(dstpath) dstbname = os.path.basename(dstpath) run_restorecon = False ctx = None if preserve_context and selinux.is_selinux_enabled() <= 0: preserve_context = False else: try: ret, ctx = selinux.lgetfilecon(dstpath) if ret < 0: raise RuntimeError("getfilecon(%r) failed" % dstpath) except OSError as e: if e.errno == errno.ENOENT: run_restorecon = True else: raise if not force: os.symlink(srcpath, dstpath) if preserve_context: selinux.restorecon(dstpath) else: dsttmp = None for attempt in range(tempfile.TMP_MAX): _dsttmp = tempfile.mktemp( prefix=dstbname + os.extsep, dir=dstdname) try: os.symlink(srcpath, _dsttmp) except OSError as e: if e.errno == errno.EEXIST: # try again continue raise else: dsttmp = _dsttmp break if dsttmp is None: raise IOError( errno.EEXIST, "No suitable temporary symlink could be created.") if preserve_context and not run_restorecon: selinux.lsetfilecon(dsttmp, ctx) try: os.rename(dsttmp, dstpath) except: # clean up os.remove(dsttmp) raise if run_restorecon: selinux.restorecon(dstpath) def overwrite_safely( path, content, preserve_mode=True, preserve_context=True, preserve_ownership=True): """Safely overwrite a file by creating a temporary file in the same directory, writing it, moving it over the original file, eventually preserving file mode, SELinux context and ownership.""" path = os.path.realpath(path) dir_ = os.path.dirname(path) base = os.path.basename(path) fd = None f = None tmpname = None exists = os.path.exists(path) if preserve_context and selinux.is_selinux_enabled() <= 0: preserve_context = False try: fd, tmpname = tempfile.mkstemp(prefix=base + os.path.extsep, dir=dir_) if exists: s = os.stat(path) if preserve_ownership: os.fchown(fd, s.st_uid, s.st_gid) if preserve_mode: os.fchmod(fd, stat.S_IMODE(s.st_mode)) if preserve_context: ret, ctx = selinux.getfilecon(path) if ret < 0: raise RuntimeError("getfilecon(%r) failed" % path) f = os.fdopen(fd, "w") fd = None f.write(content) f.close() f = None os.rename(tmpname, path) if preserve_context: if exists: selinux.setfilecon(path, ctx) else: selinux.restorecon(path) finally: if f: f.close() elif fd: os.close(fd) if tmpname and os.path.isfile(tmpname): try: os.unlink(tmpname) except: pass util/hookable.py000064400000014136147204717450007677 0ustar00# -*- coding: utf-8 -*- # slip.util.hookable -- run hooks on changes in objects # # Copyright © 2008 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains variants of certain base types which call registered hooks on changes.""" import collections from six import with_metaclass __all__ = ["Hookable", "HookableSet"] class HookableType(type): def __new__(cls, name, bases, dct): if '_hookable_change_methods' in dct: try: base = dct["_hookable_base_class"] except KeyError: base = None for base_candidate in (x for x in bases if x != Hookable): if base: raise TypeError( "too many base classes: %s" % str(bases)) else: base = base_candidate for methodname in dct["_hookable_change_methods"]: dct[methodname] = HookableType.wrap_method(base, methodname) return type.__new__(cls, name, bases, dct) @classmethod def wrap_method(cls, base, methodname): func = getattr(base, methodname) def methodwrapper(self, *p, **k): retval = func(self, *p, **k) self._run_hooks() return retval methodwrapper.__name__ = methodname return methodwrapper class _HookEntry(object): def __init__(self, hook, args, kwargs, hookable=None): assert(isinstance(hook, collections.Callable)) assert(isinstance(hookable, Hookable)) for n, x in enumerate(args): try: hash(x) except TypeError: raise TypeError( "Positional argument %d is not hashable: %r" % (n, x)) for k, x in kwargs.items(): try: hash(x) except TypeError: raise TypeError( "Keyword argument %r is not hashable: %r" % (k, x)) if not isinstance(args, tuple): args = tuple(args) self.__hook = hook self.__args = args self.__kwargs = kwargs self.__hookable = hookable self.__hash = None def __cmp__(self, obj): return ( self.__hook == obj.__hook and self.__args == obj.__args and self.__kwargs == obj.__kwargs) def __hash__(self): if not self.__hash: self.__hash = self._compute_hash() return self.__hash def _compute_hash(self): hashvalue = hash(self.__hook) hashvalue = hash(hashvalue) ^ hash(self.__args) hashvalue = hash(hashvalue) ^ hash( tuple(sorted(self.__kwargs.items()))) return hashvalue def run(self): if self.__hookable: self.__hook(self.__hookable, *self.__args, **self.__kwargs) else: self.__hook(*self.__args, **self.__kwargs) class Hookable(with_metaclass(HookableType, object)): """An object which calls registered hooks on changes.""" @property def __hooks__(self, *p, **k): if not hasattr(self, "__real_hooks__"): self.__real_hooks__ = set() return self.__real_hooks__ def _get_hooks_enabled(self): if not hasattr(self, "__hooks_enabled__"): self.__hooks_enabled__ = True return self.__hooks_enabled__ def _set_hooks_enabled(self, enabled): self.__hooks_enabled__ = enabled hooks_enabled = property(_get_hooks_enabled, _set_hooks_enabled) def _get_hooks_frozen(self): if not hasattr(self, "__hooks_frozen__"): self.__hooks_frozen__ = False return self.__hooks_frozen__ def _set_hooks_frozen(self, freeze): if freeze == self.hooks_frozen: return self.__hooks_frozen__ = freeze if freeze: self.__hooks_frozen_entries__ = set() else: for hookentry in self.__hooks_frozen_entries__: hookentry.run() del self.__hooks_frozen_entries__ hooks_frozen = property(_get_hooks_frozen, _set_hooks_frozen) def freeze_hooks(self): self.hooks_frozen = True def thaw_hooks(self): self.hooks_frozen = False def add_hook(self, hook, *args, **kwargs): self.__add_hook(hook, None, *args, **kwargs) def add_hook_hookable(self, hook, *args, **kwargs): self.__add_hook(hook, self, *args, **kwargs) def __add_hook(self, hook, _hookable, *args, **kwargs): assert isinstance(hook, collections.Callable) assert isinstance(_hookable, Hookable) hookentry = _HookEntry(hook, args, kwargs, hookable=_hookable) self.__hooks__.add(hookentry) def remove_hook(self, hook, *args, **kwargs): self.__hooks__.remove(_HookEntry(hook, args, kwargs)) def _run_hooks(self): if self.hooks_enabled: if not self.hooks_frozen: for hookentry in self.__hooks__: hookentry.run() else: self.__hooks_frozen_entries__.update(self.__hooks__) class HookableSet(set, Hookable): """A set object which calls registered hooks on changes.""" _hookable_change_methods = ( "add", "clear", "difference_update", "discard", "intersection_update", "pop", "remove", "symmetric_difference_update", "update") def copy(self): obj = set.copy(self) obj.__real_hooks__ = set() return obj __init__.py000064400000000000147204717450006656 0ustar00dbus/__pycache__/__init__.cpython-36.opt-1.pyc000064400000000606147204717450015052 0ustar003 uAc@s`ddlmZddlmZddlmZmZmZddlmZddlmZddlm Z ddlm Z d S) )absolute_import)bus) SessionBus SystemBus StarterBus)proxies)service)polkit)mainloopN) Z __future__rrrrrrr r r r r /usr/lib/python3.6/__init__.pys     dbus/__pycache__/__init__.cpython-36.pyc000064400000000606147204717450014113 0ustar003 uAc@s`ddlmZddlmZddlmZmZmZddlmZddlmZddlm Z ddlm Z d S) )absolute_import)bus) SessionBus SystemBus StarterBus)proxies)service)polkit)mainloopN) Z __future__rrrrrrr r r r r /usr/lib/python3.6/__init__.pys     dbus/__pycache__/bus.cpython-36.opt-1.pyc000064400000001322147204717450014100 0ustar003 uAcY@sXdZddlmZddlZddlmZddlmZx"d D]Zed ee ej d q6WdS)zQThis module contains functions which create monkey-patched/augmented D-Bus buses.)absolute_importN)proxies) constantsBus SystemBus SessionBus StarterBuszdef %(name)s(*args, **kwargs): busobj = dbus.%(name)s(*args, **kwargs) busobj.ProxyObjectClass = proxies.ProxyObject busobj.default_timeout = %(default_timeout)s return busobj )namemodnameZdefault_timeout)rrrr ) __doc__Z __future__rZdbusrrr exec__name__Zmethod_call_no_timeoutrr/usr/lib/python3.6/bus.pys    dbus/__pycache__/bus.cpython-36.pyc000064400000001322147204717450013141 0ustar003 uAcY@sXdZddlmZddlZddlmZddlmZx"d D]Zed ee ej d q6WdS)zQThis module contains functions which create monkey-patched/augmented D-Bus buses.)absolute_importN)proxies) constantsBus SystemBus SessionBus StarterBuszdef %(name)s(*args, **kwargs): busobj = dbus.%(name)s(*args, **kwargs) busobj.ProxyObjectClass = proxies.ProxyObject busobj.default_timeout = %(default_timeout)s return busobj )namemodnameZdefault_timeout)rrrr ) __doc__Z __future__rZdbusrrr exec__name__Zmethod_call_no_timeoutrr/usr/lib/python3.6/bus.pys    dbus/__pycache__/constants.cpython-36.opt-1.pyc000064400000000335147204717450015326 0ustar003 uAc@s dZdZdS)z*This module contains some constant values.ig@@Ng`Mb@A)__doc__Zmethod_call_no_timeoutrr/usr/lib/python3.6/constants.pys dbus/__pycache__/constants.cpython-36.pyc000064400000000335147204717450014367 0ustar003 uAc@s dZdZdS)z*This module contains some constant values.ig@@Ng`Mb@A)__doc__Zmethod_call_no_timeoutrr/usr/lib/python3.6/constants.pys dbus/__pycache__/introspection.cpython-36.opt-1.pyc000064400000011116147204717450016211 0ustar003 uAc@sdZddlmZddlmZddlmZddlmZGddde Z Gdd d ee e Z Gd d d e Z Gd d d e ZGddde eZGddde ZGddde ZGddde ZGddde eZddZdS)z?Classes and functions to easily access DBus introspection data.)absolute_import) ElementTree)StringIO)with_metaclassc@s(eZdZdZiZeddZddZdS) IElemMetazMetaclass for introspection elements. Sets elemname class member automatically from class name if not set explicitly. Registers classes for their element names.cCs>d}x4|D],}|j}||kr.t|r.|d7}||7}q W|S)N_)lowerlen)clsZclsnameelemnamecZc_lowerr#/usr/lib/python3.6/introspection.pyclsname_to_elemname(s  zIElemMeta.clsname_to_elemnamecCs|dkrtj||||Sd|krL|jds6td|tj|dd|d<|d}|tjkrntd||ftj||||}|tj|<|S)NIElemr z;Class '%s' needs to set elemname (or be called 'IElem...'))z4Class '%s' tries to register duplicate elemname '%s')type__new__ startswith TypeErrorrrelemnames_to_classes)r namebasesZdctr klsrrrr3s     zIElemMeta.__new__N)__name__ __module__ __qualname____doc__r classmethodrrrrrrr s rcs@eZdZdZd fdd Zd ddZddZed d ZZ S) rz&Base class for introspection elements.Ncs*tjj|jtjd}tt|j|||S)N)rrgettagsuperrr)r elemparentr) __class__rrrOsz IElem.__new__cs$|_|_fdd|D_dS)Ncsg|]}t|dqS))r$)r).0r )selfrr Wsz"IElem.__init__..)r#r$child_elements)r'r#r$r)r'r__init__TszIElem.__init__cCsZd|jr|jn d|jj|jf}x2|jD](}x"t|jdD]}|d|7}q>Wq*W|S)Nz%s %rz unknown:%s z %s)r r#r!attribr)strsplit)r'sr Zccrrr__str__Ys  z IElem.__str__cCs|jjS)N)r#r,)r'rrrr,asz IElem.attrib)N)N) rrrrrr*r0propertyr, __classcell__rr)r%rrLs  rc@seZdZdZdZdS) IElemUnknownz-Catch-all for unknown introspection elements.N)rrrrr rrrrr3fsr3c@seZdZdZeddZdS)IElemNameMixinz,Mixin for introspection elements with names.cCs |jdS)Nr)r,)r'rrrroszIElemNameMixin.nameN)rrrrr1rrrrrr4lsr4cs"eZdZdZdfdd ZZS) IElemNodezIntrospection node.Ncs(tt|j||dd|jD|_dS)NcSsg|]}t|tr|qSr) isinstancer5)r&r rrrr({sz&IElemNode.__init__..)r"r5r*r)Z child_nodes)r'r#r$)r%rrr*wszIElemNode.__init__)N)rrrrr*r2rr)r%rr5tsr5c@seZdZdZdS)IElemInterfacezIntrospection interface.N)rrrrrrrrr7~sr7c@seZdZdZdS) IElemMethodzIntrospection interface method.N)rrrrrrrrr8sr8c@seZdZdZdS)IElemArgzIntrospection method argument.N)rrrrrrrrr9sr9c@seZdZdZdS) IElemSignalzIntrospection interface signal.N)rrrrrrrrr:sr:cCs.t}t|dst|}|j|}t|}|S)Nread)rhasattrrparser)Zstring_or_fileZtreeZxml_rootZ elem_rootrrr introspects   r>N)rZ __future__rZxml.etree.ElementTreeriorZsixrrrobjectrr3r4r5r7r8r9r:r>rrrrs    , dbus/__pycache__/introspection.cpython-36.pyc000064400000011116147204717450015252 0ustar003 uAc@sdZddlmZddlmZddlmZddlmZGddde Z Gdd d ee e Z Gd d d e Z Gd d d e ZGddde eZGddde ZGddde ZGddde ZGddde eZddZdS)z?Classes and functions to easily access DBus introspection data.)absolute_import) ElementTree)StringIO)with_metaclassc@s(eZdZdZiZeddZddZdS) IElemMetazMetaclass for introspection elements. Sets elemname class member automatically from class name if not set explicitly. Registers classes for their element names.cCs>d}x4|D],}|j}||kr.t|r.|d7}||7}q W|S)N_)lowerlen)clsZclsnameelemnamecZc_lowerr#/usr/lib/python3.6/introspection.pyclsname_to_elemname(s  zIElemMeta.clsname_to_elemnamecCs|dkrtj||||Sd|krL|jds6td|tj|dd|d<|d}|tjkrntd||ftj||||}|tj|<|S)NIElemr z;Class '%s' needs to set elemname (or be called 'IElem...'))z4Class '%s' tries to register duplicate elemname '%s')type__new__ startswith TypeErrorrrelemnames_to_classes)r namebasesZdctr klsrrrr3s     zIElemMeta.__new__N)__name__ __module__ __qualname____doc__r classmethodrrrrrrr s rcs@eZdZdZd fdd Zd ddZddZed d ZZ S) rz&Base class for introspection elements.Ncs*tjj|jtjd}tt|j|||S)N)rrgettagsuperrr)r elemparentr) __class__rrrOsz IElem.__new__cs$|_|_fdd|D_dS)Ncsg|]}t|dqS))r$)r).0r )selfrr Wsz"IElem.__init__..)r#r$child_elements)r'r#r$r)r'r__init__TszIElem.__init__cCsZd|jr|jn d|jj|jf}x2|jD](}x"t|jdD]}|d|7}q>Wq*W|S)Nz%s %rz unknown:%s z %s)r r#r!attribr)strsplit)r'sr Zccrrr__str__Ys  z IElem.__str__cCs|jjS)N)r#r,)r'rrrr,asz IElem.attrib)N)N) rrrrrr*r0propertyr, __classcell__rr)r%rrLs  rc@seZdZdZdZdS) IElemUnknownz-Catch-all for unknown introspection elements.N)rrrrr rrrrr3fsr3c@seZdZdZeddZdS)IElemNameMixinz,Mixin for introspection elements with names.cCs |jdS)Nr)r,)r'rrrroszIElemNameMixin.nameN)rrrrr1rrrrrr4lsr4cs"eZdZdZdfdd ZZS) IElemNodezIntrospection node.Ncs(tt|j||dd|jD|_dS)NcSsg|]}t|tr|qSr) isinstancer5)r&r rrrr({sz&IElemNode.__init__..)r"r5r*r)Z child_nodes)r'r#r$)r%rrr*wszIElemNode.__init__)N)rrrrr*r2rr)r%rr5tsr5c@seZdZdZdS)IElemInterfacezIntrospection interface.N)rrrrrrrrr7~sr7c@seZdZdZdS) IElemMethodzIntrospection interface method.N)rrrrrrrrr8sr8c@seZdZdZdS)IElemArgzIntrospection method argument.N)rrrrrrrrr9sr9c@seZdZdZdS) IElemSignalzIntrospection interface signal.N)rrrrrrrrr:sr:cCs.t}t|dst|}|j|}t|}|S)Nread)rhasattrrparser)Zstring_or_fileZtreeZxml_rootZ elem_rootrrr introspects   r>N)rZ __future__rZxml.etree.ElementTreeriorZsixrrrobjectrr3r4r5r7r8r9r:r>rrrrs    , dbus/__pycache__/mainloop.cpython-36.opt-1.pyc000064400000006142147204717450015132 0ustar003 uAc# @s@dZddlmZd ZGdddeZGdddeZddZd S) zVThis module contains mainloop wrappers. Currently only glib main loops are supported.)absolute_importMainLoopset_typecsXeZdZdZdZfddZeddZddZd d Z d d Z d dZ ddZ Z S)raAn abstract main loop wrapper class and factory. Use MainLoop() to get a main loop wrapper object for a main loop type previously registered with set_type(). Defaults to glib main loops. Actual main loop wrapper classes are derived from this class.Ncs.tjdkrtjdtt|jtjf||S)Nglib)rZ_mainloop_classrsuper__new___MainLoop__mainloop_class)clsargskwargs) __class__/usr/lib/python3.6/mainloop.pyr*s   zMainLoop.__new__cCsHtjdk rtddti}||kr.||t_ntd|dj|fdS)zxSet a main loop type for non-blocking interfaces. mltype: "glib" (currently only glib main loops are supported)Nz(The main loop type can only be set once.rz0'%s' is not one of the valid main loop types: %sz, )rr RuntimeError GlibMainLoop ValueErrorjoin)r mltypeZ ml_type_classr r rr1s  zMainLoop.set_typecCs tdS)z$Returns if there are pending events.N)NotImplementedError)selfr r rpendingCszMainLoop.pendingcCs tdS)z Iterates over one pending event.N)r)rr r riterateHszMainLoop.iteratecCsx|jr|jqWdS)z!Iterates over all pending events.N)rr)rr r riterate_over_pending_eventsMs z$MainLoop.iterate_over_pending_eventscCs tdS)zRuns the main loop.N)r)rr r rrunSsz MainLoop.runcCs tdS)zQuits the main loop.N)r)rr r rquitXsz MainLoop.quit)__name__ __module__ __qualname____doc__rr classmethodrrrrrr __classcell__r r )r rr s  c@seZdZddZdS)rcCsFddlm}|j}|j}||_|j|_|j|_|j|_|j |_ dS)N)_glib) Z _wrappersr"rZ get_contextZ _mainlooprZ iterationrrr)rr"ZmlZctxr r r__init__`s zGlibMainLoop.__init__N)rrrr#r r r rr^srcCs$ddlm}|dttj|dS)zSet a main loop type for non-blocking interfaces. mltype: "glib" (currently only glib main loops are supported) Deprecated, use MainLoop.set_type() instead.r)warnzuse MainLoop.set_type() insteadN)warningsr$DeprecationWarningrr)rr$r r rrls  N)rr)rZ __future__r__all__objectrrrr r r rs  >dbus/__pycache__/mainloop.cpython-36.pyc000064400000006142147204717450014173 0ustar003 uAc# @s@dZddlmZd ZGdddeZGdddeZddZd S) zVThis module contains mainloop wrappers. Currently only glib main loops are supported.)absolute_importMainLoopset_typecsXeZdZdZdZfddZeddZddZd d Z d d Z d dZ ddZ Z S)raAn abstract main loop wrapper class and factory. Use MainLoop() to get a main loop wrapper object for a main loop type previously registered with set_type(). Defaults to glib main loops. Actual main loop wrapper classes are derived from this class.Ncs.tjdkrtjdtt|jtjf||S)Nglib)rZ_mainloop_classrsuper__new___MainLoop__mainloop_class)clsargskwargs) __class__/usr/lib/python3.6/mainloop.pyr*s   zMainLoop.__new__cCsHtjdk rtddti}||kr.||t_ntd|dj|fdS)zxSet a main loop type for non-blocking interfaces. mltype: "glib" (currently only glib main loops are supported)Nz(The main loop type can only be set once.rz0'%s' is not one of the valid main loop types: %sz, )rr RuntimeError GlibMainLoop ValueErrorjoin)r mltypeZ ml_type_classr r rr1s  zMainLoop.set_typecCs tdS)z$Returns if there are pending events.N)NotImplementedError)selfr r rpendingCszMainLoop.pendingcCs tdS)z Iterates over one pending event.N)r)rr r riterateHszMainLoop.iteratecCsx|jr|jqWdS)z!Iterates over all pending events.N)rr)rr r riterate_over_pending_eventsMs z$MainLoop.iterate_over_pending_eventscCs tdS)zRuns the main loop.N)r)rr r rrunSsz MainLoop.runcCs tdS)zQuits the main loop.N)r)rr r rquitXsz MainLoop.quit)__name__ __module__ __qualname____doc__rr classmethodrrrrrr __classcell__r r )r rr s  c@seZdZddZdS)rcCsFddlm}|j}|j}||_|j|_|j|_|j|_|j |_ dS)N)_glib) Z _wrappersr"rZ get_contextZ _mainlooprZ iterationrrr)rr"ZmlZctxr r r__init__`s zGlibMainLoop.__init__N)rrrr#r r r rr^srcCs$ddlm}|dttj|dS)zSet a main loop type for non-blocking interfaces. mltype: "glib" (currently only glib main loops are supported) Deprecated, use MainLoop.set_type() instead.r)warnzuse MainLoop.set_type() insteadN)warningsr$DeprecationWarningrr)rr$r r rrls  N)rr)rZ __future__r__all__objectrrrr r r rs  >dbus/__pycache__/polkit.cpython-36.opt-1.pyc000064400000017150147204717450014617 0ustar003 uAcI$@sdZddlmZddlZddlZddlmZddlmZddlm Z dd d d d d gZ ddZ dZ Gdd d e Zdeddfdd ZGdd d ejZGddde ZeZdd Zdifdd ZdS)zmThis module contains convenience decorators and functions for using PolicyKit with dbus services and clients.)absolute_importN) decorator)reduce)method_call_no_timeout require_auth enable_proxyAUTHFAIL_DONTCATCHNotAuthorizedExceptionAreAuthorizationsObtainableIsSystemBusNameAuthorizedAsynccsfdd}|S)uDecorator for DBus service methods. Specify that a user needs a specific PolicyKit authorization `polkit_auth´ to execute it.cst|d|S)NZ_slip_polkit_auth_required)setattr)method) polkit_auth/usr/lib/python3.6/polkit.pyrequire_auth_decorator/s z,require_auth..require_auth_decoratorr)rrr)rrr)s zBorg.fedoraproject.slip.dbus.service.PolKit.NotAuthorizedException.c@s eZdZdS)r N)__name__ __module__ __qualname__rrrrr <scs6fdd|dk r"t|Sfdd}|SdS)uDecorator for DBus proxy methods. Let's you (optionally) specify either a result value or an exception type and a callback which is returned, thrown or called respectively if a PolicyKit authorization doesn't exist or can't be obtained in the DBus mechanism, i.e. an appropriate DBus exception is thrown. An exception constructor may and a callback must accept an `action_id´ parameter which will be set to the id of the PolicyKit action for which authorization could not be obtained. Examples: 1) Return `False´ in the event of an authorization problem, and call `error_handler´: def error_handler(action_id=None): print "Authorization problem:", action_id class MyProxy(object): @polkit.enable_proxy(authfail_result=False, authfail_callback=error_handler) def some_method(self, ...): ... 2) Throw a `MyAuthError´ instance in the event of an authorization problem: class MyAuthError(Exception): def __init__(self, *args, **kwargs): action_id = kwargs.pop("action_id") super(MyAuthError, self).__init__(*args, **kwargs) self.action_id = action_id class MyProxy(object): @polkit.enable_proxy(authfail_exception=MyAuthError) def some_method(self, ...): ...csy |||Stjk r}zr|j}|jts2|ttd}dk rT|ddk ry|d}Wn}YnX|tkrSd}~XnXdS)N) action_id)dbus DBusExceptionZ get_dbus_name startswithAUTH_EXC_PREFIXlenr )funcpkeZexc_namerZaf_exc)authfail_callbackauthfail_exceptionauthfail_resultrr _enable_proxyvs$    z#enable_proxy.._enable_proxyNcs t|S)N)r)r)r#rrdecorateszenable_proxy..decorate)r)rr"r!r r$r)r#r r!r"rr@s 6  cs$eZdZdZdZfddZZS)r zqException which a DBus service method throws if an authorization required for executing it can't be obtained.zAorg.fedoraproject.slip.dbus.service.PolKit.NotAuthorizedExceptioncs(|jjd||_tt|j||dS)N.) __class___dbus_error_namesuperr __init__)selfrrr)r&rrr)s zNotAuthorizedException.__init__)rrr__doc__r'r) __classcell__rr)r&rr sc@seZdZdZdZdZdZdZdZdZ dZ e ddZ e dd Ze d d Ze d d Ze ddZddZddZddZdifddZdS)PolKitz"Convenience wrapper around polkit.zorg.freedesktop.PolicyKit1z%/org/freedesktop/PolicyKit1/Authorityz$org.freedesktop.PolicyKit1.AuthorityNcCs4||jkr0tjr0tjjtjdt_dt_dt_dS)N) _dbus_namer- _PolKit__busZremove_signal_receiver_PolKit__signal_receiver_PolKit__interface)clsnameZ old_ownerZ new_ownerrrr_on_name_owner_changeds zPolKit._on_name_owner_changedcCs0tjs*tjt_tjj|jdd|jdt_tjS)NZNameOwnerChangedzorg.freedesktop.DBus)Zhandler_functionZ signal_nameZdbus_interfaceZarg0)r-r/rZ SystemBusZadd_signal_receiverr4r.r0)r*rrr_buss  z PolKit._buscCstjs|jjt_tjS)N)r-_PolKit__bus_namer5Zget_unique_name)r*rrr _bus_names zPolKit._bus_namec CsFtjs@y"tj|jj|j|j|jt_Wntj k r>YnXtjS)N) r-r1r Interfacer5 get_objectr. _dbus_path_dbus_interfacer)r*rrr _interfaces  zPolKit._interfacecCs t|jS)N)boolr<)r*rrr_polkit_presentszPolKit._polkit_presentc Cs>|jjdd}tj|d}y|j|}Wnd}YnX|S)Nzorg.freedesktop.DBusz/org/freedesktop/DBus)r5r9rr8ZGetConnectionUnixUser)r*system_bus_nameZ bus_objectZ bus_interfaceZuidrrrZ__dbus_system_bus_name_uids  z!PolKit.__dbus_system_bus_name_uidcCs6|js dS|jjdd|jif|idd\}}}|p4|S)NTzsystem-bus-namer3r)r>r<CheckAuthorizationr7)r*Z authorization is_authorized is_challengedetailsrrrZ__authorization_is_obtainables  z$PolKit.__authorization_is_obtainablecs8js dSt|tttfs |f}tfdd|d}|S)NTcs|o j|S)N)$_PolKit__authorization_is_obtainable)xy)r*rrsz4PolKit.AreAuthorizationsObtainable..)r> isinstancetuplelistsetr)r*authorizationsZ obtainabler)r*rr s z"PolKit.AreAuthorizationsObtainableTc sd|js |dkp|j|dkSd}|r0|dO}fdd}|jjdd|if|||d||tddS) Nrrcs|\}}}|dS)Nr)argsrBrCrD) reply_handlerrrreply_cb s z7PolKit.IsSystemBusNameAuthorizedAsync..reply_cbzsystem-bus-namer3r@)rO error_handlerZtimeout)r>!_PolKit__dbus_system_bus_name_uidr<rAr) r*r?rrOrQ challengerDflagsrPr)rOrr s   z%PolKit.IsSystemBusNameAuthorizedAsync)rrrr+r.r:r;r1r/r6r0 classmethodr4propertyr5r7r<r>rRrEr r rrrrr-s"     r-cCs tj|S)N)__polkitr )rMrrrr sTcCstj||||||S)N)rWr )r?rrOrQrSrDrrrr s )r+Z __future__r collectionsrr functoolsrZ constantsr__all__rrobjectr rrr r-rWr r rrrrs(     Wodbus/__pycache__/polkit.cpython-36.pyc000064400000017503147204717450013662 0ustar003 uAcI$@sdZddlmZddlZddlZddlmZddlmZddlm Z dd d d d d gZ ddZ dZ Gdd d e Zdeddfdd ZGdd d ejZGddde ZeZdd Zdifdd ZdS)zmThis module contains convenience decorators and functions for using PolicyKit with dbus services and clients.)absolute_importN) decorator)reduce)method_call_no_timeout require_auth enable_proxyAUTHFAIL_DONTCATCHNotAuthorizedExceptionAreAuthorizationsObtainableIsSystemBusNameAuthorizedAsynccsfdd}|S)uDecorator for DBus service methods. Specify that a user needs a specific PolicyKit authorization `polkit_auth´ to execute it.cst|dstt|d|S)NZ_dbus_is_methodZ_slip_polkit_auth_required)hasattrAssertionErrorsetattr)method) polkit_auth/usr/lib/python3.6/polkit.pyrequire_auth_decorator/s z,require_auth..require_auth_decoratorr)rrr)rrr)s zBorg.fedoraproject.slip.dbus.service.PolKit.NotAuthorizedException.c@s eZdZdS)r N)__name__ __module__ __qualname__rrrrr <scs|dkst|tjstdtfks0dks0tdksHttjsHtdks^tts^tfdd|dk rt|Sfdd}|SdS)uDecorator for DBus proxy methods. Let's you (optionally) specify either a result value or an exception type and a callback which is returned, thrown or called respectively if a PolicyKit authorization doesn't exist or can't be obtained in the DBus mechanism, i.e. an appropriate DBus exception is thrown. An exception constructor may and a callback must accept an `action_id´ parameter which will be set to the id of the PolicyKit action for which authorization could not be obtained. Examples: 1) Return `False´ in the event of an authorization problem, and call `error_handler´: def error_handler(action_id=None): print "Authorization problem:", action_id class MyProxy(object): @polkit.enable_proxy(authfail_result=False, authfail_callback=error_handler) def some_method(self, ...): ... 2) Throw a `MyAuthError´ instance in the event of an authorization problem: class MyAuthError(Exception): def __init__(self, *args, **kwargs): action_id = kwargs.pop("action_id") super(MyAuthError, self).__init__(*args, **kwargs) self.action_id = action_id class MyProxy(object): @polkit.enable_proxy(authfail_exception=MyAuthError) def some_method(self, ...): ...Ncsy |||Stjk r}zr|j}|jts2|ttd}dk rT|ddk ry|d}Wn}YnX|tkrSd}~XnXdS)N) action_id)dbus DBusExceptionZ get_dbus_name startswithAUTH_EXC_PREFIXlenr )funcpkeZexc_namerZaf_exc)authfail_callbackauthfail_exceptionauthfail_resultrr _enable_proxyvs$    z#enable_proxy.._enable_proxycs t|S)N)r)r)r%rrdecorateszenable_proxy..decorate) isinstance collectionsCallablerr issubclass Exceptionr)rr$r#r"r&r)r%r"r#r$rr@s*    cs$eZdZdZdZfddZZS)r zqException which a DBus service method throws if an authorization required for executing it can't be obtained.zAorg.fedoraproject.slip.dbus.service.PolKit.NotAuthorizedExceptioncs(|jjd||_tt|j||dS)N.) __class___dbus_error_namesuperr __init__)selfrrr )r-rrr0s zNotAuthorizedException.__init__)rrr__doc__r.r0 __classcell__rr)r-rr sc@seZdZdZdZdZdZdZdZdZ dZ e ddZ e dd Ze d d Ze d d Ze ddZddZddZddZdifddZdS)PolKitz"Convenience wrapper around polkit.zorg.freedesktop.PolicyKit1z%/org/freedesktop/PolicyKit1/Authorityz$org.freedesktop.PolicyKit1.AuthorityNcCs4||jkr0tjr0tjjtjdt_dt_dt_dS)N) _dbus_namer4 _PolKit__busZremove_signal_receiver_PolKit__signal_receiver_PolKit__interface)clsnameZ old_ownerZ new_ownerrrr_on_name_owner_changeds zPolKit._on_name_owner_changedcCs0tjs*tjt_tjj|jdd|jdt_tjS)NZNameOwnerChangedzorg.freedesktop.DBus)Zhandler_functionZ signal_nameZdbus_interfaceZarg0)r4r6rZ SystemBusZadd_signal_receiverr;r5r7)r1rrr_buss  z PolKit._buscCstjs|jjt_tjS)N)r4_PolKit__bus_namer<Zget_unique_name)r1rrr _bus_names zPolKit._bus_namec CsFtjs@y"tj|jj|j|j|jt_Wntj k r>YnXtjS)N) r4r8r Interfacer< get_objectr5 _dbus_path_dbus_interfacer)r1rrr _interfaces  zPolKit._interfacecCs t|jS)N)boolrC)r1rrr_polkit_presentszPolKit._polkit_presentc Cs>|jjdd}tj|d}y|j|}Wnd}YnX|S)Nzorg.freedesktop.DBusz/org/freedesktop/DBus)r<r@rr?ZGetConnectionUnixUser)r1system_bus_nameZ bus_objectZ bus_interfaceZuidrrrZ__dbus_system_bus_name_uids  z!PolKit.__dbus_system_bus_name_uidcCs6|js dS|jjdd|jif|idd\}}}|p4|S)NTzsystem-bus-namer:r)rErCCheckAuthorizationr>)r1Z authorization is_authorized is_challengedetailsrrrZ__authorization_is_obtainables  z$PolKit.__authorization_is_obtainablecs8js dSt|tttfs |f}tfdd|d}|S)NTcs|o j|S)N)$_PolKit__authorization_is_obtainable)xy)r1rrsz4PolKit.AreAuthorizationsObtainable..)rEr'tuplelistsetr)r1authorizationsZ obtainabler)r1rr s z"PolKit.AreAuthorizationsObtainableTc sd|js |dkp|j|dkSd}|r0|dO}fdd}|jjdd|if|||d||tddS) Nrrcs|\}}}|dS)Nr)argsrIrJrK) reply_handlerrrreply_cb s z7PolKit.IsSystemBusNameAuthorizedAsync..reply_cbzsystem-bus-namer:rG)rU error_handlerZtimeout)rE!_PolKit__dbus_system_bus_name_uidrCrHr) r1rFrrUrW challengerKflagsrVr)rUrr s   z%PolKit.IsSystemBusNameAuthorizedAsync)rrrr2r5rArBr8r6r=r7 classmethodr;propertyr<r>rCrErXrLr r rrrrr4s"     r4cCs tj|S)N)__polkitr )rSrrrr sTcCstj||||||S)N)r]r )rFrrUrWrYrKrrrr s )r2Z __future__rr(rr functoolsrZ constantsr__all__rrobjectr rrr r4r]r r rrrrs(     Wodbus/__pycache__/proxies.cpython-36.opt-1.pyc000064400000002345147204717450015006 0ustar003 uAc`@sPdZddlmZddlZddlmZGdddejjZGdd d ejj Z dS) z{This module contains D-Bus proxy classes which implement the default timeout of the augmented bus classes in slip.dbus.bus.)absolute_importN) constantsc@s$eZdZiZeddZddZdS) _ProxyMethodcCsB|j|jkr6t|jjdd}|dkr*tj}||j|j<|j|jS)Ndefault_timeout)Z _connection_connections_default_timeoutsgetattr_proxyZ_busrZmethod_call_no_timeout)selfZdtr /usr/lib/python3.6/proxies.pyr&s   z_ProxyMethod.default_timeoutcOs.|jddkr|j|d<tjjj|f||S)NZtimeout)getrdbusproxiesr__call__)r argskwargsr r r r/s z_ProxyMethod.__call__N)__name__ __module__ __qualname__rpropertyrrr r r r r"s rc@seZdZeZdS) ProxyObjectN)rrrrZProxyMethodClassr r r r r6sr) __doc__Z __future__rZ dbus.proxiesrrrrrr r r r s   dbus/__pycache__/proxies.cpython-36.pyc000064400000002345147204717450014047 0ustar003 uAc`@sPdZddlmZddlZddlmZGdddejjZGdd d ejj Z dS) z{This module contains D-Bus proxy classes which implement the default timeout of the augmented bus classes in slip.dbus.bus.)absolute_importN) constantsc@s$eZdZiZeddZddZdS) _ProxyMethodcCsB|j|jkr6t|jjdd}|dkr*tj}||j|j<|j|jS)Ndefault_timeout)Z _connection_connections_default_timeoutsgetattr_proxyZ_busrZmethod_call_no_timeout)selfZdtr /usr/lib/python3.6/proxies.pyr&s   z_ProxyMethod.default_timeoutcOs.|jddkr|j|d<tjjj|f||S)NZtimeout)getrdbusproxiesr__call__)r argskwargsr r r r/s z_ProxyMethod.__call__N)__name__ __module__ __qualname__rpropertyrrr r r r r"s rc@seZdZeZdS) ProxyObjectN)rrrrZProxyMethodClassr r r r r6sr) __doc__Z __future__rZ dbus.proxiesrrrrrr r r r s   dbus/__pycache__/service.cpython-36.opt-1.pyc000064400000012352147204717450014754 0ustar003 uAc@sdZddlmZddlZddlZddlmZddlmZ ddl m Z d d d gZ da d d Zeadd ZddZddZdadaddZGdd d ejjZGdd d eeejjZdS)zMThis module contains convenience functions for using dbus-activated services.)absolute_importN)with_metaclass)_glib)polkitObject InterfaceType set_mainloopcCs tjdS)N) __mainloop__quitr r /usr/lib/python3.6/service.py__glib_quit_cb__)srcCs|adS)N)r )Zmainloopr r rr 4scCs|adS)N) __quit_cb__)quit_cbr r r set_quit_cb9srcCs tdS)N)rr r r rr>srZ__slip_dbus_service_sender____slip_dbus_service_reply_cb____slip_dbus_service_error_cb__csjdk rjdntdjdk r4jdntd fdd}xLddtDD]6}|dkr|_ql|dkr|_qlt||t|qlWj|_|S) NFTcsj }|dk rVddr4 =rLd=d=j|t dtdd|dk rr fdd}fdd}tj|||d n f}j|SdS) NrrZ_slip_polkit_auth_requireddefault_polkit_auth_requiredcs|rrfqd}yf}Wn&tk rX}z |}WYdd}~XnX|rh|q|dkrxq|ntjjdS)N) ExceptionrZNotAuthorizedExceptiontimeout_restart)Zis_autherrorresulte) action_iderror_cbkmethodmethod_is_asyncpreply_cbselfr r reply_handlerqs  z:wrap_method..wrapped_method..reply_handlercs|jdS)N)r)r)rr"r r error_handlersz:wrap_method..wrapped_method..error_handler)r#r$)get sender_seengetattrrZIsSystemBusNameAuthorizedAsyncr)r"r rsenderr#r$Zretval)async_callbackshide_async_callbackshide_sender_keywordrrsender_keyword)rrrr r!r"rwrapped_method[s,       " z#wrap_method..wrapped_methodcss"|]}|dddkr|VqdS)NZ_dbus_r ).0xr r r szwrap_method.._dbus_sender_keyword_dbus_async_callbacks)r2SENDER_KEYWORDr3ASYNC_CALLBACKSdirsetattrr'__name__)rr-attrr )r)r*r+rrr,r wrap_methodHs(  Er:cseZdZfddZZS)r csDx,|jD] \}}t|ddr t|||<q Wtt|j||||S)NZ_dbus_is_methodF)itemsr'r:superr __new__)clsnamebasesZdctZattrnamer9) __class__r rr=s zInterfaceType.__new__)r8 __module__ __qualname__r= __classcell__r r )rArr scsbeZdZdZdZeZdZeZiZ iZ dZ dfdd Z ddZ dd Zdd d Zd d ZZS)rFNcs2tt|j||||dkr(|jj|_n||_dS)N)r<r__init__rA persistent)r"connZ object_pathZbus_namerG)rAr rrFs zObject.__init__cCs2|j r ttjdkr tdSdt_|jt_dS)NrF)rGlenrsendersrcurrent_sourcedefault_durationduration)r"r r r _timeout_cbs zObject._timeout_cbcCs|j}| r||ftjkrtjj||ftj|j|ttj|dkrjtj|jtj|=tj|=|j rttjdkrtjdkrt dS)Nr) connectionrrJremoveconnections_sendersrIconnections_smobjsrGrKr)r"r?Z old_ownerZ new_ownerrHr r r_name_owner_changeds zObject._name_owner_changedcCsf|s |jj}tj s|tjkr$|t_|j s:ttjdkrbtjrLtj tjtj tjd|j t_dS)Nri) rArLrrMrGrIrJrKGLibZ source_removeZ timeout_addrN)r"rMr r rrs  zObject.timeout_restartcCsp||jftjkrltjj||jf|jtjkrZttj|j<|jj|jdd|dtj|j<tj|jj|dS)NZNameOwnerChangedzorg.freedesktop.DBus)Zhandler_functionZ signal_nameZdbus_interfaceZarg1) rOrrJaddrQsetZadd_signal_receiverrSrR)r"r(r r rr&s zObject.sender_seen)NNNN)N)r8rBrCrGrLrMrKrVrJrQrRrrFrNrSrr&rDr r )rArrs  )rr)__doc__Z __future__rZdbusZ dbus.serviceZsixrZ _wrappersrrTr__all__r rrr rrr4r5r:Zservicer rr r r rs&     g dbus/__pycache__/service.cpython-36.pyc000064400000012352147204717450014015 0ustar003 uAc@sdZddlmZddlZddlZddlmZddlmZ ddl m Z d d d gZ da d d Zeadd ZddZddZdadaddZGdd d ejjZGdd d eeejjZdS)zMThis module contains convenience functions for using dbus-activated services.)absolute_importN)with_metaclass)_glib)polkitObject InterfaceType set_mainloopcCs tjdS)N) __mainloop__quitr r /usr/lib/python3.6/service.py__glib_quit_cb__)srcCs|adS)N)r )Zmainloopr r rr 4scCs|adS)N) __quit_cb__)quit_cbr r r set_quit_cb9srcCs tdS)N)rr r r rr>srZ__slip_dbus_service_sender____slip_dbus_service_reply_cb____slip_dbus_service_error_cb__csjdk rjdntdjdk r4jdntd fdd}xLddtDD]6}|dkr|_ql|dkr|_qlt||t|qlWj|_|S) NFTcsj }|dk rVddr4 =rLd=d=j|t dtdd|dk rr fdd}fdd}tj|||d n f}j|SdS) NrrZ_slip_polkit_auth_requireddefault_polkit_auth_requiredcs|rrfqd}yf}Wn&tk rX}z |}WYdd}~XnX|rh|q|dkrxq|ntjjdS)N) ExceptionrZNotAuthorizedExceptiontimeout_restart)Zis_autherrorresulte) action_iderror_cbkmethodmethod_is_asyncpreply_cbselfr r reply_handlerqs  z:wrap_method..wrapped_method..reply_handlercs|jdS)N)r)r)rr"r r error_handlersz:wrap_method..wrapped_method..error_handler)r#r$)get sender_seengetattrrZIsSystemBusNameAuthorizedAsyncr)r"r rsenderr#r$Zretval)async_callbackshide_async_callbackshide_sender_keywordrrsender_keyword)rrrr r!r"rwrapped_method[s,       " z#wrap_method..wrapped_methodcss"|]}|dddkr|VqdS)NZ_dbus_r ).0xr r r szwrap_method.._dbus_sender_keyword_dbus_async_callbacks)r2SENDER_KEYWORDr3ASYNC_CALLBACKSdirsetattrr'__name__)rr-attrr )r)r*r+rrr,r wrap_methodHs(  Er:cseZdZfddZZS)r csDx,|jD] \}}t|ddr t|||<q Wtt|j||||S)NZ_dbus_is_methodF)itemsr'r:superr __new__)clsnamebasesZdctZattrnamer9) __class__r rr=s zInterfaceType.__new__)r8 __module__ __qualname__r= __classcell__r r )rArr scsbeZdZdZdZeZdZeZiZ iZ dZ dfdd Z ddZ dd Zdd d Zd d ZZS)rFNcs2tt|j||||dkr(|jj|_n||_dS)N)r<r__init__rA persistent)r"connZ object_pathZbus_namerG)rAr rrFs zObject.__init__cCs2|j r ttjdkr tdSdt_|jt_dS)NrF)rGlenrsendersrcurrent_sourcedefault_durationduration)r"r r r _timeout_cbs zObject._timeout_cbcCs|j}| r||ftjkrtjj||ftj|j|ttj|dkrjtj|jtj|=tj|=|j rttjdkrtjdkrt dS)Nr) connectionrrJremoveconnections_sendersrIconnections_smobjsrGrKr)r"r?Z old_ownerZ new_ownerrHr r r_name_owner_changeds zObject._name_owner_changedcCsf|s |jj}tj s|tjkr$|t_|j s:ttjdkrbtjrLtj tjtj tjd|j t_dS)Nri) rArLrrMrGrIrJrKGLibZ source_removeZ timeout_addrN)r"rMr r rrs  zObject.timeout_restartcCsp||jftjkrltjj||jf|jtjkrZttj|j<|jj|jdd|dtj|j<tj|jj|dS)NZNameOwnerChangedzorg.freedesktop.DBus)Zhandler_functionZ signal_nameZdbus_interfaceZarg1) rOrrJaddrQsetZadd_signal_receiverrSrR)r"r(r r rr&s zObject.sender_seen)NNNN)N)r8rBrCrGrLrMrKrVrJrQrRrrFrNrSrr&rDr r )rArrs  )rr)__doc__Z __future__rZdbusZ dbus.serviceZsixrZ _wrappersrrTr__all__r rrr rrr4r5r:Zservicer rr r r rs&     g dbus/__init__.py000064400000000336147204717450007627 0ustar00# -*- coding: utf-8 -*- from __future__ import absolute_import from . import bus from .bus import SessionBus, SystemBus, StarterBus from . import proxies from . import service from . import polkit from . import mainloop dbus/bus.py000064400000002531147204717450006660 0ustar00# -*- coding: utf-8 -*- # slip.dbus.bus -- augmented dbus buses # # Copyright © 2009, 2011 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains functions which create monkey-patched/augmented D-Bus buses.""" from __future__ import absolute_import import dbus from . import proxies from . import constants for name in ("Bus", "SystemBus", "SessionBus", "StarterBus"): exec( """def %(name)s(*args, **kwargs): busobj = dbus.%(name)s(*args, **kwargs) busobj.ProxyObjectClass = proxies.ProxyObject busobj.default_timeout = %(default_timeout)s return busobj """ % { "name": name, "modname": __name__, "default_timeout": constants.method_call_no_timeout}) dbus/constants.py000064400000002700147204717450010101 0ustar00# -*- coding: utf-8 -*- # slip.dbus.constants -- constant values # # Copyright © 2011 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains some constant values.""" # The maximum value of a 32bit signed integer is the magic value to indicate an # infinite timeout for dbus. Unlike the C interface which deals with # milliseconds as integers, the python interface uses seconds as floats for the # timeout. Therefore we need to use the Python float (C double) value that # gives 0x7FFFFFFF if multiplied by 1000.0 and cast into an integer. # # This calculation should be precise enough to get a value of 0x7FFFFFFF on the # C side. If not, it will still amount to a very long time (not quite 25 days) # which should be enough for all intents and purposes. method_call_no_timeout = 0x7FFFFFFF / 1000.0 dbus/introspection.py000064400000010330147204717450010763 0ustar00# -*- coding: utf-8 -*- # slip.dbus.introspection -- access dbus introspection data # # Copyright © 2011 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """Classes and functions to easily access DBus introspection data.""" from __future__ import absolute_import from xml.etree.ElementTree import ElementTree from io import StringIO from six import with_metaclass class IElemMeta(type): """Metaclass for introspection elements. Sets elemname class member automatically from class name if not set explicitly. Registers classes for their element names.""" elemnames_to_classes = {} @classmethod def clsname_to_elemname(cls, clsname): elemname = "" for c in clsname: c_lower = c.lower() if c_lower != c: if len(elemname): elemname += "_" elemname += c_lower return elemname def __new__(cls, name, bases, dct): if name == "IElem": return type.__new__(cls, name, bases, dct) if 'elemname' not in dct: if not name.startswith("IElem"): raise TypeError( "Class '%s' needs to set elemname (or be called " "'IElem...'))" % name) dct['elemname'] = IElemMeta.clsname_to_elemname(name[5:]) elemname = dct['elemname'] if elemname in IElemMeta.elemnames_to_classes: raise TypeError( "Class '%s' tries to register duplicate elemname '%s'" % (name, elemname)) kls = type.__new__(cls, name, bases, dct) IElemMeta.elemnames_to_classes[elemname] = kls return kls class IElem(with_metaclass(IElemMeta, object)): """Base class for introspection elements.""" def __new__(cls, elem, parent=None): kls = IElemMeta.elemnames_to_classes.get( elem.tag, IElemMeta.elemnames_to_classes[None]) return super(IElem, cls).__new__(kls, elem, parent) def __init__(self, elem, parent=None): self.elem = elem self.parent = parent self.child_elements = [IElem(c, parent=self) for c in elem] def __str__(self): s = "%s %r" % (self.elemname if self.elemname else "unknown:%s" % self.elem.tag, self.attrib) for c in self.child_elements: for cc in str(c).split("\n"): s += "\n %s" % (cc) return s @property def attrib(self): return self.elem.attrib class IElemUnknown(IElem): """Catch-all for unknown introspection elements.""" elemname = None class IElemNameMixin(object): """Mixin for introspection elements with names.""" @property def name(self): return self.attrib['name'] class IElemNode(IElem, IElemNameMixin): """Introspection node.""" def __init__(self, elem, parent=None): super(IElemNode, self).__init__(elem, parent) self.child_nodes = [ c for c in self.child_elements if isinstance(c, IElemNode)] class IElemInterface(IElem): """Introspection interface.""" class IElemMethod(IElem): """Introspection interface method.""" class IElemArg(IElem): """Introspection method argument.""" class IElemSignal(IElem, IElemNameMixin): """Introspection interface signal.""" def introspect(string_or_file): tree = ElementTree() # assume string if read() method doesn't exist, works for string, unicode, # dbus.String if not hasattr(string_or_file, "read"): string_or_file = StringIO(string_or_file) xml_root = tree.parse(string_or_file) elem_root = IElem(xml_root) return elem_root dbus/mainloop.py000064400000006443147204717450007713 0ustar00# -*- coding: utf-8 -*- # slip.dbus.mainloop -- mainloop wrappers # # Copyright © 2009, 2012 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains mainloop wrappers. Currently only glib main loops are supported.""" from __future__ import absolute_import __all__ = ("MainLoop", "set_type") class MainLoop(object): """An abstract main loop wrapper class and factory. Use MainLoop() to get a main loop wrapper object for a main loop type previously registered with set_type(). Defaults to glib main loops. Actual main loop wrapper classes are derived from this class.""" __mainloop_class = None def __new__(cls, *args, **kwargs): global _mainloop_class if MainLoop._mainloop_class is None: MainLoop.set_type("glib") return super(MainLoop, cls).__new__( MainLoop.__mainloop_class, *args, **kwargs) @classmethod def set_type(cls, mltype): """Set a main loop type for non-blocking interfaces. mltype: "glib" (currently only glib main loops are supported)""" if MainLoop.__mainloop_class is not None: raise RuntimeError("The main loop type can only be set once.") ml_type_class = {"glib": GlibMainLoop} if mltype in ml_type_class: MainLoop.__mainloop_class = ml_type_class[mltype] else: raise ValueError( "'%s' is not one of the valid main loop types:\n%s" % (mltype, ", ".join(ml_type_class))) def pending(self): """Returns if there are pending events.""" raise NotImplementedError() def iterate(self): """Iterates over one pending event.""" raise NotImplementedError() def iterate_over_pending_events(self): """Iterates over all pending events.""" while self.pending(): self.iterate() def run(self): """Runs the main loop.""" raise NotImplementedError() def quit(self): """Quits the main loop.""" raise NotImplementedError() class GlibMainLoop(MainLoop): def __init__(self): from .._wrappers import _glib ml = _glib.MainLoop() ctx = ml.get_context() self._mainloop = ml self.pending = ctx.pending self.iterate = ctx.iteration self.run = ml.run self.quit = ml.quit def set_type(mltype): """Set a main loop type for non-blocking interfaces. mltype: "glib" (currently only glib main loops are supported) Deprecated, use MainLoop.set_type() instead.""" from warnings import warn warn("use MainLoop.set_type() instead", DeprecationWarning) MainLoop.set_type(mltype) dbus/polkit.py000064400000022111147204717450007365 0ustar00# -*- coding: utf-8 -*- # slip.dbus.polkit -- convenience decorators and functions for using PolicyKit # with dbus services and clients # # Copyright © 2008, 2009, 2012, 2013, 2015 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains convenience decorators and functions for using PolicyKit with dbus services and clients.""" from __future__ import absolute_import import collections import dbus from decorator import decorator from functools import reduce from .constants import method_call_no_timeout __all__ = ["require_auth", "enable_proxy", "AUTHFAIL_DONTCATCH", "NotAuthorizedException", "AreAuthorizationsObtainable", "IsSystemBusNameAuthorizedAsync"] def require_auth(polkit_auth): """Decorator for DBus service methods. Specify that a user needs a specific PolicyKit authorization `polkit_auth´ to execute it.""" def require_auth_decorator(method): assert hasattr(method, "_dbus_is_method") setattr(method, "_slip_polkit_auth_required", polkit_auth) return method return require_auth_decorator AUTH_EXC_PREFIX = \ "org.fedoraproject.slip.dbus.service.PolKit.NotAuthorizedException." class AUTHFAIL_DONTCATCH(object): pass def enable_proxy( func=None, authfail_result=AUTHFAIL_DONTCATCH, authfail_exception=None, authfail_callback=None): """Decorator for DBus proxy methods. Let's you (optionally) specify either a result value or an exception type and a callback which is returned, thrown or called respectively if a PolicyKit authorization doesn't exist or can't be obtained in the DBus mechanism, i.e. an appropriate DBus exception is thrown. An exception constructor may and a callback must accept an `action_id´ parameter which will be set to the id of the PolicyKit action for which authorization could not be obtained. Examples: 1) Return `False´ in the event of an authorization problem, and call `error_handler´: def error_handler(action_id=None): print "Authorization problem:", action_id class MyProxy(object): @polkit.enable_proxy(authfail_result=False, authfail_callback=error_handler) def some_method(self, ...): ... 2) Throw a `MyAuthError´ instance in the event of an authorization problem: class MyAuthError(Exception): def __init__(self, *args, **kwargs): action_id = kwargs.pop("action_id") super(MyAuthError, self).__init__(*args, **kwargs) self.action_id = action_id class MyProxy(object): @polkit.enable_proxy(authfail_exception=MyAuthError) def some_method(self, ...): ...""" assert(func is None or isinstance(func, collections.Callable)) assert( authfail_result in (None, AUTHFAIL_DONTCATCH) or authfail_exception is None) assert( authfail_callback is None or isinstance(authfail_callback, collections.Callable)) assert( authfail_exception is None or issubclass(authfail_exception, Exception)) def _enable_proxy(func, *p, **k): try: return func(*p, **k) except dbus.DBusException as e: exc_name = e.get_dbus_name() if not exc_name.startswith(AUTH_EXC_PREFIX): raise action_id = exc_name[len(AUTH_EXC_PREFIX):] if authfail_callback is not None: authfail_callback(action_id=action_id) if authfail_exception is not None: try: af_exc = authfail_exception(action_id=action_id) except: af_exc = authfail_exception() raise af_exc if authfail_result is AUTHFAIL_DONTCATCH: raise return authfail_result if func is not None: return decorator(_enable_proxy, func) else: def decorate(func): return decorator(_enable_proxy, func) return decorate class NotAuthorizedException(dbus.DBusException): """Exception which a DBus service method throws if an authorization required for executing it can't be obtained.""" _dbus_error_name = \ "org.fedoraproject.slip.dbus.service.PolKit.NotAuthorizedException" def __init__(self, action_id, *p, **k): self._dbus_error_name = self.__class__._dbus_error_name + "." +\ action_id super(NotAuthorizedException, self).__init__(*p, **k) class PolKit(object): """Convenience wrapper around polkit.""" _dbus_name = 'org.freedesktop.PolicyKit1' _dbus_path = '/org/freedesktop/PolicyKit1/Authority' _dbus_interface = 'org.freedesktop.PolicyKit1.Authority' __interface = None __bus = None __bus_name = None __signal_receiver = None @classmethod def _on_name_owner_changed(cls, name, old_owner, new_owner): if name == cls._dbus_name and PolKit.__bus: PolKit.__bus.remove_signal_receiver(PolKit.__signal_receiver) PolKit.__bus = None PolKit.__signal_receiver = None PolKit.__interface = None @property def _bus(self): if not PolKit.__bus: PolKit.__bus = dbus.SystemBus() PolKit.__signal_receiver = PolKit.__bus.add_signal_receiver( handler_function=self._on_name_owner_changed, signal_name='NameOwnerChanged', dbus_interface='org.freedesktop.DBus', arg0=self._dbus_name) return PolKit.__bus @property def _bus_name(self): if not PolKit.__bus_name: PolKit.__bus_name = self._bus.get_unique_name() return PolKit.__bus_name @property def _interface(self): if not PolKit.__interface: try: PolKit.__interface = dbus.Interface(self._bus.get_object( self._dbus_name, self._dbus_path), self._dbus_interface) except dbus.DBusException: pass return PolKit.__interface @property def _polkit_present(self): return bool(self._interface) def __dbus_system_bus_name_uid(self, system_bus_name): bus_object = self._bus.get_object( 'org.freedesktop.DBus', '/org/freedesktop/DBus') bus_interface = dbus.Interface(bus_object, 'org.freedesktop.DBus') try: uid = bus_interface.GetConnectionUnixUser(system_bus_name) except: uid = None return uid def __authorization_is_obtainable(self, authorization): if not self._polkit_present: return True (is_authorized, is_challenge, details) = \ self._interface.CheckAuthorization( ("system-bus-name", {"name": self._bus_name}), authorization, {}, 0, "") return is_authorized or is_challenge def AreAuthorizationsObtainable(self, authorizations): if not self._polkit_present: return True if not isinstance(authorizations, (tuple, list, set)): authorizations = (authorizations,) obtainable = \ reduce( lambda x, y: x and self.__authorization_is_obtainable(y), authorizations, True) return obtainable def IsSystemBusNameAuthorizedAsync( self, system_bus_name, action_id, reply_handler, error_handler, challenge=True, details={}): if not self._polkit_present: return reply_handler(action_id is None or self.__dbus_system_bus_name_uid(system_bus_name) == 0) flags = 0 if challenge: flags |= 0x1 def reply_cb(args): (is_authorized, is_challenge, details) = args reply_handler(is_authorized) self._interface.CheckAuthorization( ("system-bus-name", {"name": system_bus_name}), action_id, details, flags, "", reply_handler=reply_cb, error_handler=error_handler, timeout=method_call_no_timeout) __polkit = PolKit() def AreAuthorizationsObtainable(authorizations): return __polkit.AreAuthorizationsObtainable(authorizations) def IsSystemBusNameAuthorizedAsync( system_bus_name, action_id, reply_handler, error_handler, challenge=True, details={}): return __polkit.IsSystemBusNameAuthorizedAsync( system_bus_name, action_id, reply_handler, error_handler, challenge, details) dbus/proxies.py000064400000003540147204717450007561 0ustar00# -*- coding: utf-8 -*- # slip.dbus.proxies -- slightly augmented dbus proxy classes # # Copyright © 2005-2007 Collabora Ltd. # Copyright © 2009, 2011 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen """This module contains D-Bus proxy classes which implement the default timeout of the augmented bus classes in slip.dbus.bus.""" from __future__ import absolute_import import dbus.proxies from . import constants class _ProxyMethod(dbus.proxies._ProxyMethod): _connections_default_timeouts = {} @property def default_timeout(self): if self._connection not in self._connections_default_timeouts: dt = getattr(self._proxy._bus, "default_timeout", None) if dt is None: dt = constants.method_call_no_timeout self._connections_default_timeouts[self._connection] = dt return self._connections_default_timeouts[self._connection] def __call__(self, *args, **kwargs): if kwargs.get('timeout') is None: kwargs["timeout"] = self.default_timeout return dbus.proxies._ProxyMethod.__call__(self, *args, **kwargs) class ProxyObject(dbus.proxies.ProxyObject): ProxyMethodClass = _ProxyMethod dbus/service.py000064400000017640147204717450007536 0ustar00# -*- coding: utf-8 -*- # slip.dbus.service -- convenience functions for using dbus-activated # services # # Copyright © 2008, 2009, 2015 Red Hat, Inc. # # 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, see . # # Authors: # Nils Philippsen "This module contains convenience functions for using dbus-activated services." from __future__ import absolute_import import dbus import dbus.service from six import with_metaclass from .._wrappers import _glib as GLib from . import polkit __all__ = ["Object", "InterfaceType", "set_mainloop"] __mainloop__ = None def __glib_quit_cb__(): global __mainloop__ # assume a Glib mainloop __mainloop__.quit() __quit_cb__ = __glib_quit_cb__ def set_mainloop(mainloop): global __mainloop__ __mainloop__ = mainloop def set_quit_cb(quit_cb): global __quit_cb__ __quit_cb__ = quit_cb def quit_cb(): global __quit_cb__ __quit_cb__() SENDER_KEYWORD = "__slip_dbus_service_sender__" ASYNC_CALLBACKS = ("__slip_dbus_service_reply_cb__", "__slip_dbus_service_error_cb__") def wrap_method(method): global SENDER_KEYWORD global ASYNC_CALLBACKS if method._dbus_sender_keyword is not None: sender_keyword = method._dbus_sender_keyword hide_sender_keyword = False else: sender_keyword = SENDER_KEYWORD hide_sender_keyword = True if method._dbus_async_callbacks is not None: async_callbacks = method._dbus_async_callbacks method_is_async = True else: async_callbacks = ASYNC_CALLBACKS method_is_async = False hide_async_callbacks = not method_is_async def wrapped_method(self, *p, **k): sender = k.get(sender_keyword) if sender is not None: # i.e. called over the bus, not locally reply_cb = k[async_callbacks[0]] error_cb = k[async_callbacks[1]] if hide_sender_keyword: del k[sender_keyword] if hide_async_callbacks: del k[async_callbacks[0]] del k[async_callbacks[1]] self.sender_seen(sender) action_id = getattr(method, "_slip_polkit_auth_required", getattr(self, "default_polkit_auth_required", None)) if sender is not None and action_id: def reply_handler(is_auth): if is_auth: if method_is_async: # k contains async callbacks, simply pass on reply_cb # and error_cb method(self, *p, **k) else: # execute the synchronous method ... error = None try: result = method(self, *p, **k) except Exception as e: error = e # ... and call the reply or error callback if error: error_cb(error) else: # reply_cb((None,)) != reply_cb() if result is None: reply_cb() else: reply_cb(result) else: error_cb(polkit.NotAuthorizedException(action_id)) self.timeout_restart() def error_handler(error): error_cb(error) self.timeout_restart() polkit.IsSystemBusNameAuthorizedAsync( sender, action_id, reply_handler=reply_handler, error_handler=error_handler) else: # no action id, or run locally, no need to do anything fancy retval = method(self, *p, **k) self.timeout_restart() return retval for attr in (x for x in dir(method) if x[:6] == "_dbus_"): if attr == "_dbus_sender_keyword": wrapped_method._dbus_sender_keyword = sender_keyword elif attr == "_dbus_async_callbacks": wrapped_method._dbus_async_callbacks = async_callbacks else: setattr(wrapped_method, attr, getattr(method, attr)) # delattr (method, attr) wrapped_method.__name__ = method.__name__ return wrapped_method class InterfaceType(dbus.service.InterfaceType): def __new__(cls, name, bases, dct): for (attrname, attr) in dct.items(): if getattr(attr, "_dbus_is_method", False): dct[attrname] = wrap_method(attr) return super(InterfaceType, cls).__new__(cls, name, bases, dct) class Object(with_metaclass(InterfaceType, dbus.service.Object)): # timeout & persistence persistent = False default_duration = 5 duration = default_duration current_source = None senders = set() connections_senders = {} connections_smobjs = {} # PolicyKit default_polkit_auth_required = None def __init__( self, conn=None, object_path=None, bus_name=None, persistent=None): super(Object, self).__init__(conn, object_path, bus_name) if persistent is None: self.persistent = self.__class__.persistent else: self.persistent = persistent def _timeout_cb(self): if not self.persistent and len(Object.senders) == 0: quit_cb() return False Object.current_source = None Object.duration = self.default_duration return False def _name_owner_changed(self, name, old_owner, new_owner): conn = self.connection if not new_owner and (old_owner, conn) in Object.senders: Object.senders.remove((old_owner, conn)) Object.connections_senders[conn].remove(old_owner) if len(Object.connections_senders[conn]) == 0: Object.connections_smobjs[conn].remove() del Object.connections_senders[conn] del Object.connections_smobjs[conn] if not self.persistent and len(Object.senders) == 0 and \ Object.current_source is None: quit_cb() def timeout_restart(self, duration=None): if not duration: duration = self.__class__.default_duration if not Object.duration or duration > Object.duration: Object.duration = duration if not self.persistent or len(Object.senders) == 0: if Object.current_source: GLib.source_remove(Object.current_source) Object.current_source = \ GLib.timeout_add(Object.duration * 1000, self._timeout_cb) def sender_seen(self, sender): if (sender, self.connection) not in Object.senders: Object.senders.add((sender, self.connection)) if self.connection not in Object.connections_senders: Object.connections_senders[self.connection] = set() Object.connections_smobjs[self.connection] = \ self.connection.add_signal_receiver( handler_function=self._name_owner_changed, signal_name='NameOwnerChanged', dbus_interface='org.freedesktop.DBus', arg1=sender) Object.connections_senders[self.connection].add(sender)