import grp
import pwd
import threading
+import platform
from ganeti import constants
from ganeti import errors
_priv = None
_priv_lock = threading.Lock()
+#: Architecture information
+_arch = None
+
def GetUid(user, _getpwnam):
"""Retrieve the uid from the database.
@ivar masterd_gid: The resolved gid of the masterd group
@ivar confd_uid: The resolved uid of the confd user
@ivar confd_gid: The resolved gid of the confd group
+ @ivar luxid_uid: The resolved uid of the luxid user
+ @ivar luxid_gid: The resolved gid of the luxid group
@ivar rapi_uid: The resolved uid of the rapi user
@ivar rapi_gid: The resolved gid of the rapi group
@ivar noded_uid: The resolved uid of the noded user
-
@ivar daemons_gid: The resolved gid of the daemons group
@ivar admin_gid: The resolved gid of the admin group
+
"""
def __init__(self, _getpwnam=pwd.getpwnam, _getgrnam=grp.getgrnam):
"""Initialize the resolver.
self.confd_uid = GetUid(constants.CONFD_USER, _getpwnam)
self.confd_gid = GetGid(constants.CONFD_GROUP, _getgrnam)
+ self.luxid_uid = GetUid(constants.LUXID_USER, _getpwnam)
+ self.luxid_gid = GetGid(constants.LUXID_GROUP, _getgrnam)
+
self.rapi_uid = GetUid(constants.RAPI_USER, _getpwnam)
self.rapi_gid = GetGid(constants.RAPI_GROUP, _getgrnam)
self.noded_uid = GetUid(constants.NODED_USER, _getpwnam)
self.noded_gid = GetGid(constants.NODED_GROUP, _getgrnam)
+ self.mond_uid = GetUid(constants.MOND_USER, _getpwnam)
+ self.mond_gid = GetGid(constants.MOND_GROUP, _getgrnam)
+
# Misc Ganeti groups
self.daemons_gid = GetGid(constants.DAEMONS_GROUP, _getgrnam)
self.admin_gid = GetGid(constants.ADMIN_GROUP, _getgrnam)
self._uid2user = {
self.masterd_uid: constants.MASTERD_USER,
self.confd_uid: constants.CONFD_USER,
+ self.luxid_uid: constants.LUXID_USER,
self.rapi_uid: constants.RAPI_USER,
self.noded_uid: constants.NODED_USER,
+ self.mond_uid: constants.MOND_USER,
}
self._gid2group = {
self.masterd_gid: constants.MASTERD_GROUP,
self.confd_gid: constants.CONFD_GROUP,
+ self.luxid_gid: constants.LUXID_GROUP,
self.rapi_gid: constants.RAPI_GROUP,
self.noded_gid: constants.NODED_GROUP,
+ self.mond_gid: constants.MOND_GROUP,
self.daemons_gid: constants.DAEMONS_GROUP,
self.admin_gid: constants.ADMIN_GROUP,
}
"""Singleton wrapper around resolver instance.
As this method is accessed by multiple threads at the same time
- we need to take thread-safty carefully
+ we need to take thread-safety carefully.
"""
# We need to use the global keyword here
- global _priv # pylint: disable-msg=W0603
+ global _priv # pylint: disable=W0603
if not _priv:
_priv_lock.acquire()
try:
if not _priv:
# W0621: Redefine '_priv' from outer scope (used for singleton)
- _priv = resolver() # pylint: disable-msg=W0621
+ _priv = resolver() # pylint: disable=W0621
finally:
_priv_lock.release()
return _priv
+
+
+def InitArchInfo():
+ """Initialize architecture information.
+
+ We can assume this information never changes during the lifetime of a
+ process, therefore the information can easily be cached.
+
+ @note: This function uses C{platform.architecture} to retrieve the Python
+ binary architecture and does so by forking to run C{file} (see Python
+ documentation for more information). Therefore it must not be used in a
+ multi-threaded environment.
+
+ """
+ global _arch # pylint: disable=W0603
+
+ if _arch is not None:
+ raise errors.ProgrammerError("Architecture information can only be"
+ " initialized once")
+
+ _arch = (platform.architecture()[0], platform.machine())
+
+
+def GetArchInfo():
+ """Returns previsouly initialized architecture information.
+
+ """
+ if _arch is None:
+ raise errors.ProgrammerError("Architecture information hasn't been"
+ " initialized")
+
+ return _arch