Merge "Guestfs handle no passwd or group in image"

This commit is contained in:
Jenkins 2016-12-12 06:27:16 +00:00 committed by Gerrit Code Review
commit c6cb5cf1ba
3 changed files with 33 additions and 6 deletions

View File

@ -22,6 +22,7 @@ EVENT_TRACE = 0x4
class GuestFS(object): class GuestFS(object):
SUPPORT_CLOSE_ON_EXIT = True SUPPORT_CLOSE_ON_EXIT = True
SUPPORT_RETURN_DICT = True SUPPORT_RETURN_DICT = True
CAN_SET_OWNERSHIP = True
def __init__(self, **kwargs): def __init__(self, **kwargs):
if not self.SUPPORT_CLOSE_ON_EXIT and 'close_on_exit' in kwargs: if not self.SUPPORT_CLOSE_ON_EXIT and 'close_on_exit' in kwargs:
@ -164,6 +165,11 @@ class GuestFS(object):
if not self.auginit: if not self.auginit:
raise RuntimeError("Augeus not initialized") raise RuntimeError("Augeus not initialized")
if ((cfgpath.startswith("/files/etc/passwd") or
cfgpath.startswith("/files/etc/group")) and not
self.CAN_SET_OWNERSHIP):
raise RuntimeError("Node not found %s", cfgpath)
if cfgpath == "/files/etc/passwd/root/uid": if cfgpath == "/files/etc/passwd/root/uid":
return 0 return 0
elif cfgpath == "/files/etc/passwd/fred/uid": elif cfgpath == "/files/etc/passwd/fred/uid":

View File

@ -253,6 +253,20 @@ class VirtDiskVFSGuestFSTest(test.NoDBTestCase):
vfs.teardown() vfs.teardown()
def test_set_ownership_not_supported(self):
# NOTE(andreaf) Setting ownership relies on /etc/passwd and/or
# /etc/group being available in the image, which is not always the
# case - e.g. CirrOS image before boot.
vfs = vfsimpl.VFSGuestFS(self.qcowfile)
vfs.setup()
self.stub_out('nova.tests.unit.virt.disk.vfs.fakeguestfs.GuestFS.'
'CAN_SET_OWNERSHIP', False)
self.assertRaises(exception.NovaException, vfs.set_ownership,
"/some/file", "fred", None)
self.assertRaises(exception.NovaException, vfs.set_ownership,
"/some/file", None, "users")
def test_close_on_error(self): def test_close_on_error(self):
vfs = vfsimpl.VFSGuestFS(self.qcowfile) vfs = vfsimpl.VFSGuestFS(self.qcowfile)
vfs.setup() vfs.setup()

View File

@ -316,13 +316,20 @@ class VFSGuestFS(vfs.VFS):
uid = -1 uid = -1
gid = -1 gid = -1
if user is not None: def _get_item_id(id_path):
uid = int(self.handle.aug_get( try:
"/files/etc/passwd/" + user + "/uid")) return int(self.handle.aug_get("/files/etc/" + id_path))
if group is not None: except RuntimeError as e:
gid = int(self.handle.aug_get( msg = _("Error obtaining uid/gid for %(user)s/%(group)s: "
"/files/etc/group/" + group + "/gid")) " path %(id_path)s not found (%(e)s)") % {
'id_path': "/files/etc/" + id_path, 'user': user,
'group': group, 'e': e}
raise exception.NovaException(msg)
if user is not None:
uid = _get_item_id('passwd/' + user + '/uid')
if group is not None:
gid = _get_item_id('group/' + group + '/gid')
LOG.debug("chown uid=%(uid)d gid=%(gid)s", LOG.debug("chown uid=%(uid)d gid=%(gid)s",
{'uid': uid, 'gid': gid}) {'uid': uid, 'gid': gid})
self.handle.chown(uid, gid, path) self.handle.chown(uid, gid, path)