mirror of
https://github.com/ostreedev/ostree.git
synced 2024-12-25 01:34:34 +03:00
6bf4b3e1d8
SPDX License List is a list of (common) open source licenses that can be referred to by a “short identifier”. It has several advantages compared to the common "license header texts" usually found in source files. Some of the advantages: * It is precise; there is no ambiguity due to variations in license header text * It is language neutral * It is easy to machine process * It is concise * It is simple and can be used without much cost in interpreted environments like java Script, etc. * An SPDX license identifier is immutable. * It provides simple guidance for developers who want to make sure the license for their code is respected See http://spdx.org for further reading. Signed-off-by: Marcus Folkesson <marcus.folkesson@gmail.com> Closes: #1439 Approved by: cgwalters
402 lines
11 KiB
C
402 lines
11 KiB
C
/*
|
||
* Copyright © 2017 Endless Mobile, Inc.
|
||
*
|
||
* SPDX-License-Identifier: LGPL-2.0+
|
||
*
|
||
* This library is free software; you can redistribute it and/or
|
||
* modify it under the terms of the GNU Lesser General Public
|
||
* License as published by the Free Software Foundation; either
|
||
* version 2 of the License, or (at your option) any later version.
|
||
*
|
||
* This library 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
|
||
* Lesser General Public License for more details.
|
||
*
|
||
* You should have received a copy of the GNU Lesser General Public
|
||
* License along with this library; if not, write to the
|
||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||
* Boston, MA 02111-1307, USA.
|
||
*
|
||
* Authors:
|
||
* - Philip Withnall <withnall@endlessm.com>
|
||
*/
|
||
|
||
#include "config.h"
|
||
|
||
#include <gio/gio.h>
|
||
#include <glib.h>
|
||
#include <glib-object.h>
|
||
#include <libglnx.h>
|
||
|
||
#include "test-mock-gio.h"
|
||
|
||
/**
|
||
* SECTION:mock-gio
|
||
* @title: Mock GIO volume interfaces
|
||
* @short_description: Mock implementations of GIO volume, mount and drive
|
||
* interfaces
|
||
* @stability: Unstable
|
||
* @include: tests/test-mock-gio.h
|
||
*
|
||
* A set of classes implementing GIO interfaces for volumes, mounts, drives
|
||
* and volume monitoring, which return mock data to the caller when used. These
|
||
* are designed for use in unit tests, to mock up removable drives when testing
|
||
* code which monitors such drives being added and removed and then queries
|
||
* properties of them.
|
||
*
|
||
* By returning mock drive locations to the caller, for example, the contents of
|
||
* a removable drive may be mocked up using temporary files.
|
||
*
|
||
* Currently, all the mock data returned by these classes to callers is static,
|
||
* set at construction time.
|
||
*
|
||
* Since: 2017.8
|
||
*/
|
||
|
||
/* Mock volume monitor class. This returns a static set of data to the caller,
|
||
* which it was initialised with. */
|
||
struct _OstreeMockVolumeMonitor
|
||
{
|
||
GVolumeMonitor parent_instance;
|
||
|
||
GList *mounts; /* (element-type OstreeMockMount) */
|
||
GList *volumes; /* (element-type OstreeMockVolume) */
|
||
};
|
||
|
||
G_DEFINE_TYPE (OstreeMockVolumeMonitor, ostree_mock_volume_monitor, G_TYPE_VOLUME_MONITOR)
|
||
|
||
static GList *
|
||
ostree_mock_volume_monitor_get_mounts (GVolumeMonitor *monitor)
|
||
{
|
||
OstreeMockVolumeMonitor *self = OSTREE_MOCK_VOLUME_MONITOR (monitor);
|
||
return g_list_copy_deep (self->mounts, (GCopyFunc) g_object_ref, NULL);
|
||
}
|
||
|
||
static GList *
|
||
ostree_mock_volume_monitor_get_volumes (GVolumeMonitor *monitor)
|
||
{
|
||
OstreeMockVolumeMonitor *self = OSTREE_MOCK_VOLUME_MONITOR (monitor);
|
||
return g_list_copy_deep (self->volumes, (GCopyFunc) g_object_ref, NULL);
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_monitor_init (OstreeMockVolumeMonitor *self)
|
||
{
|
||
/* Nothing to see here. */
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_monitor_dispose (GObject *object)
|
||
{
|
||
OstreeMockVolumeMonitor *self = OSTREE_MOCK_VOLUME_MONITOR (object);
|
||
|
||
g_list_free_full (self->volumes, g_object_unref);
|
||
self->volumes = NULL;
|
||
|
||
g_list_free_full (self->mounts, g_object_unref);
|
||
self->mounts = NULL;
|
||
|
||
G_OBJECT_CLASS (ostree_mock_volume_monitor_parent_class)->dispose (object);
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_monitor_class_init (OstreeMockVolumeMonitorClass *klass)
|
||
{
|
||
GObjectClass *object_class = G_OBJECT_CLASS (klass);
|
||
GVolumeMonitorClass *monitor_class = G_VOLUME_MONITOR_CLASS (klass);
|
||
|
||
object_class->dispose = ostree_mock_volume_monitor_dispose;
|
||
|
||
monitor_class->get_mounts = ostree_mock_volume_monitor_get_mounts;
|
||
monitor_class->get_volumes = ostree_mock_volume_monitor_get_volumes;
|
||
}
|
||
|
||
/**
|
||
* ostree_mock_volume_monitor_new:
|
||
* @mounts: (element-type GMount) (transfer none): list of current #GMounts
|
||
* @volumes: (element-type GVolume) (transfer none): list of current #GVolumes
|
||
*
|
||
* Create a new mock #GVolumeMonitor which will return the given static lists of
|
||
* #GMounts and #GVolumes to any caller of g_volume_monitor_get_mounts() or
|
||
* g_volume_monitor_get_volumes().
|
||
*
|
||
* Typically, the elements of @mounts will be #OstreeMockMount objects and the
|
||
* elements of @volumes will be #OstreeMockVolume objects; but this does not
|
||
* have to be the case.
|
||
*
|
||
* Returns: (transfer full): a new #GVolumeMonitor object
|
||
* Since: 2017.8
|
||
*/
|
||
GVolumeMonitor *
|
||
ostree_mock_volume_monitor_new (GList *mounts,
|
||
GList *volumes)
|
||
{
|
||
g_autoptr(OstreeMockVolumeMonitor) monitor = NULL;
|
||
|
||
monitor = g_object_new (OSTREE_TYPE_MOCK_VOLUME_MONITOR, NULL);
|
||
monitor->mounts = g_list_copy_deep (mounts, (GCopyFunc) g_object_ref, NULL);
|
||
monitor->volumes = g_list_copy_deep (volumes, (GCopyFunc) g_object_ref, NULL);
|
||
|
||
return g_steal_pointer (&monitor);
|
||
}
|
||
|
||
/* Mock volume class. This returns a static set of data to the caller, which it
|
||
* was initialised with. */
|
||
struct _OstreeMockVolume
|
||
{
|
||
GObject parent_instance;
|
||
|
||
gchar *name;
|
||
GDrive *drive; /* (owned) (nullable) */
|
||
GMount *mount; /* (owned) (nullable) */
|
||
};
|
||
|
||
static void ostree_mock_volume_iface_init (GVolumeIface *iface);
|
||
|
||
G_DEFINE_TYPE_WITH_CODE (OstreeMockVolume, ostree_mock_volume, G_TYPE_OBJECT,
|
||
G_IMPLEMENT_INTERFACE (G_TYPE_VOLUME, ostree_mock_volume_iface_init))
|
||
|
||
static gchar *
|
||
ostree_mock_volume_get_name (GVolume *volume)
|
||
{
|
||
OstreeMockVolume *self = OSTREE_MOCK_VOLUME (volume);
|
||
return g_strdup (self->name);
|
||
}
|
||
|
||
static GDrive *
|
||
ostree_mock_volume_get_drive (GVolume *volume)
|
||
{
|
||
OstreeMockVolume *self = OSTREE_MOCK_VOLUME (volume);
|
||
return (self->drive != NULL) ? g_object_ref (self->drive) : NULL;
|
||
}
|
||
|
||
static GMount *
|
||
ostree_mock_volume_get_mount (GVolume *volume)
|
||
{
|
||
OstreeMockVolume *self = OSTREE_MOCK_VOLUME (volume);
|
||
return (self->mount != NULL) ? g_object_ref (self->mount) : NULL;
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_init (OstreeMockVolume *self)
|
||
{
|
||
/* Nothing to see here. */
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_dispose (GObject *object)
|
||
{
|
||
OstreeMockVolume *self = OSTREE_MOCK_VOLUME (object);
|
||
|
||
g_clear_pointer (&self->name, g_free);
|
||
g_clear_object (&self->drive);
|
||
g_clear_object (&self->mount);
|
||
|
||
G_OBJECT_CLASS (ostree_mock_volume_parent_class)->dispose (object);
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_class_init (OstreeMockVolumeClass *klass)
|
||
{
|
||
GObjectClass *object_class = G_OBJECT_CLASS (klass);
|
||
|
||
object_class->dispose = ostree_mock_volume_dispose;
|
||
}
|
||
|
||
static void
|
||
ostree_mock_volume_iface_init (GVolumeIface *iface)
|
||
{
|
||
iface->get_name = ostree_mock_volume_get_name;
|
||
iface->get_drive = ostree_mock_volume_get_drive;
|
||
iface->get_mount = ostree_mock_volume_get_mount;
|
||
}
|
||
|
||
/**
|
||
* ostree_mock_volume_new:
|
||
* @name: volume name
|
||
* @drive: (transfer none) (nullable): drive for the volume, or %NULL if none
|
||
* should be associated
|
||
* @mount: (transfer none) (nullable): mount for the volume, or %NULL if it’s
|
||
* not mounted
|
||
*
|
||
* Create a new mock #GVolume which will return the given static @name, @drive
|
||
* and @mount to any caller of its getter methods. There is currently no
|
||
* provision for changing these values dynamically. There is also currently no
|
||
* provision for mocking the other getters of #GVolume.
|
||
*
|
||
* Typically, @drive will be an #OstreeMockDrive object and @mount will be an
|
||
* #OstreeMockMount object; but this does not have to be the case.
|
||
*
|
||
* Returns: (transfer full): a new #GVolume object
|
||
* Since: 2017.8
|
||
*/
|
||
OstreeMockVolume *
|
||
ostree_mock_volume_new (const gchar *name,
|
||
GDrive *drive,
|
||
GMount *mount)
|
||
{
|
||
g_autoptr(OstreeMockVolume) volume = NULL;
|
||
|
||
volume = g_object_new (OSTREE_TYPE_MOCK_VOLUME, NULL);
|
||
volume->name = g_strdup (name);
|
||
volume->drive = (drive != NULL) ? g_object_ref (drive) : NULL;
|
||
volume->mount = (mount != NULL) ? g_object_ref (mount) : NULL;
|
||
|
||
return g_steal_pointer (&volume);
|
||
}
|
||
|
||
/* Mock drive class. This returns a static set of data to the caller, which it
|
||
* was initialised with. */
|
||
struct _OstreeMockDrive
|
||
{
|
||
GObject parent_instance;
|
||
|
||
gboolean is_removable;
|
||
};
|
||
|
||
static void ostree_mock_drive_iface_init (GDriveIface *iface);
|
||
|
||
G_DEFINE_TYPE_WITH_CODE (OstreeMockDrive, ostree_mock_drive, G_TYPE_OBJECT,
|
||
G_IMPLEMENT_INTERFACE (G_TYPE_DRIVE, ostree_mock_drive_iface_init))
|
||
|
||
#if GLIB_CHECK_VERSION(2, 50, 0)
|
||
static gboolean
|
||
ostree_mock_drive_is_removable (GDrive *drive)
|
||
{
|
||
OstreeMockDrive *self = OSTREE_MOCK_DRIVE (drive);
|
||
return self->is_removable;
|
||
}
|
||
#endif
|
||
|
||
static void
|
||
ostree_mock_drive_init (OstreeMockDrive *self)
|
||
{
|
||
/* Nothing to see here. */
|
||
}
|
||
|
||
static void
|
||
ostree_mock_drive_class_init (OstreeMockDriveClass *klass)
|
||
{
|
||
/* Nothing to see here. */
|
||
}
|
||
|
||
static void
|
||
ostree_mock_drive_iface_init (GDriveIface *iface)
|
||
{
|
||
#if GLIB_CHECK_VERSION(2, 50, 0)
|
||
iface->is_removable = ostree_mock_drive_is_removable;
|
||
#endif
|
||
}
|
||
|
||
/**
|
||
* ostree_mock_drive_new:
|
||
* @is_removable: %TRUE if the drive is removable; %FALSE otherwise
|
||
*
|
||
* Create a new mock #GDrive which will return the given static @is_removable to
|
||
* any caller of its getter methods. There is currently no provision for mocking
|
||
* the other getters of #GDrive.
|
||
*
|
||
* Returns: (transfer full): a new #GDrive object
|
||
* Since: 2017.8
|
||
*/
|
||
OstreeMockDrive *
|
||
ostree_mock_drive_new (gboolean is_removable)
|
||
{
|
||
g_autoptr(OstreeMockDrive) drive = NULL;
|
||
|
||
drive = g_object_new (OSTREE_TYPE_MOCK_DRIVE, NULL);
|
||
drive->is_removable = is_removable;
|
||
|
||
return g_steal_pointer (&drive);
|
||
}
|
||
|
||
/* Mock mount class. This returns a static set of data to the caller, which it
|
||
* was initialised with. */
|
||
struct _OstreeMockMount
|
||
{
|
||
GObject parent_instance;
|
||
|
||
gchar *name; /* (owned) */
|
||
GFile *root; /* (owned) */
|
||
};
|
||
|
||
static void ostree_mock_mount_iface_init (GMountIface *iface);
|
||
|
||
G_DEFINE_TYPE_WITH_CODE (OstreeMockMount, ostree_mock_mount, G_TYPE_OBJECT,
|
||
G_IMPLEMENT_INTERFACE (G_TYPE_MOUNT, ostree_mock_mount_iface_init))
|
||
|
||
static gchar *
|
||
ostree_mock_mount_get_name (GMount *mount)
|
||
{
|
||
OstreeMockMount *self = OSTREE_MOCK_MOUNT (mount);
|
||
return g_strdup (self->name);
|
||
}
|
||
|
||
static GFile *
|
||
ostree_mock_mount_get_root (GMount *mount)
|
||
{
|
||
OstreeMockMount *self = OSTREE_MOCK_MOUNT (mount);
|
||
return g_object_ref (self->root);
|
||
}
|
||
|
||
static void
|
||
ostree_mock_mount_init (OstreeMockMount *self)
|
||
{
|
||
/* Nothing to see here. */
|
||
}
|
||
|
||
static void
|
||
ostree_mock_mount_dispose (GObject *object)
|
||
{
|
||
OstreeMockMount *self = OSTREE_MOCK_MOUNT (object);
|
||
|
||
g_clear_pointer (&self->name, g_free);
|
||
g_clear_object (&self->root);
|
||
|
||
G_OBJECT_CLASS (ostree_mock_mount_parent_class)->dispose (object);
|
||
}
|
||
|
||
static void
|
||
ostree_mock_mount_class_init (OstreeMockMountClass *klass)
|
||
{
|
||
GObjectClass *object_class = G_OBJECT_CLASS (klass);
|
||
|
||
object_class->dispose = ostree_mock_mount_dispose;
|
||
}
|
||
|
||
static void
|
||
ostree_mock_mount_iface_init (GMountIface *iface)
|
||
{
|
||
iface->get_name = ostree_mock_mount_get_name;
|
||
iface->get_root = ostree_mock_mount_get_root;
|
||
}
|
||
|
||
/**
|
||
* ostree_mock_mount_new:
|
||
* @name: mount name
|
||
* @root: (transfer none): root path for the mounted file system
|
||
*
|
||
* Create a new mock #GMount which will return the given static @name and @root
|
||
* to any caller of its getter methods. There is currently no provision for
|
||
* mocking the other getters of #GMount.
|
||
*
|
||
* Typically, @root will point to a temporary directory where a mocked file
|
||
* system is present; but this does not have to be the case.
|
||
*
|
||
* Returns: (transfer full): a new #GMount object
|
||
* Since: 2017.8
|
||
*/
|
||
OstreeMockMount *
|
||
ostree_mock_mount_new (const gchar *name,
|
||
GFile *root)
|
||
{
|
||
g_autoptr(OstreeMockMount) mount = NULL;
|
||
|
||
mount = g_object_new (OSTREE_TYPE_MOCK_MOUNT, NULL);
|
||
mount->name = g_strdup (name);
|
||
mount->root = g_object_ref (root);
|
||
|
||
return g_steal_pointer (&mount);
|
||
}
|