summaryrefslogtreecommitdiff
path: root/src/settings/plugins/keyfile/nms-keyfile-utils.c
diff options
context:
space:
mode:
authorThomas Haller <thaller@redhat.com>2021-02-03 15:25:56 +0100
committerThomas Haller <thaller@redhat.com>2021-02-04 09:45:55 +0100
commitac1a9e03e4d6674e1e60529b47b325a8f62e67b3 (patch)
treeef0445da3fd804e6cc5ee1e9c48a352dd348df1f /src/settings/plugins/keyfile/nms-keyfile-utils.c
parent97ed143e04e74323a59a0f24a965d36341233670 (diff)
downloadNetworkManager-ac1a9e03e4d6674e1e60529b47b325a8f62e67b3.tar.gz
all: move "src/" directory to "src/core/"
Currently "src/" mostly contains the source code of the daemon. I say mostly, because that is not true, there are also the device, settings, wwan, ppp plugins, the initrd generator, the pppd and dhcp helper, and probably more. Also we have source code under libnm-core/, libnm/, clients/, and shared/ directories. That is all confusing. We should have one "src" directory, that contains subdirectories. Those subdirectories should contain individual parts (libraries or applications), that possibly have dependencies on other subdirectories. There should be a flat hierarchy of directories under src/, which contains individual modules. As the name "src/" is already taken, that prevents any sensible restructuring of the code. As a first step, move "src/" to "src/core/". This gives space to reorganize the code better by moving individual components into "src/". For inspiration, look at systemd's "src/" directory. https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/743
Diffstat (limited to 'src/settings/plugins/keyfile/nms-keyfile-utils.c')
-rw-r--r--src/settings/plugins/keyfile/nms-keyfile-utils.c389
1 files changed, 0 insertions, 389 deletions
diff --git a/src/settings/plugins/keyfile/nms-keyfile-utils.c b/src/settings/plugins/keyfile/nms-keyfile-utils.c
deleted file mode 100644
index a62e0ae018..0000000000
--- a/src/settings/plugins/keyfile/nms-keyfile-utils.c
+++ /dev/null
@@ -1,389 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0-or-later */
-/*
- * Copyright (C) 2010 - 2018 Red Hat, Inc.
- */
-
-#include "nm-default.h"
-
-#include "nms-keyfile-utils.h"
-
-#include <stdlib.h>
-#include <sys/stat.h>
-
-#include "nm-glib-aux/nm-io-utils.h"
-#include "nm-keyfile/nm-keyfile-internal.h"
-#include "nm-utils.h"
-#include "nm-setting-wired.h"
-#include "nm-setting-wireless.h"
-#include "nm-setting-wireless-security.h"
-#include "nm-config.h"
-
-/*****************************************************************************/
-
-#define NMMETA_KF_GROUP_NAME_NMMETA "nmmeta"
-#define NMMETA_KF_KEY_NAME_NMMETA_UUID "uuid"
-#define NMMETA_KF_KEY_NAME_NMMETA_LOADED_PATH "loaded-path"
-#define NMMETA_KF_KEY_NAME_NMMETA_SHADOWED_STORAGE "shadowed-storage"
-
-/*****************************************************************************/
-
-const char *
-nms_keyfile_nmmeta_check_filename(const char *filename, guint *out_uuid_len)
-{
- const char *uuid;
- const char *s;
- gsize len;
-
- s = strrchr(filename, '/');
- if (s)
- filename = &s[1];
-
- len = strlen(filename);
- if (len <= NM_STRLEN(NM_KEYFILE_PATH_SUFFIX_NMMETA)
- || memcmp(&filename[len - NM_STRLEN(NM_KEYFILE_PATH_SUFFIX_NMMETA)],
- NM_KEYFILE_PATH_SUFFIX_NMMETA,
- NM_STRLEN(NM_KEYFILE_PATH_SUFFIX_NMMETA))
- != 0) {
- /* the filename does not have the right suffix. */
- return NULL;
- }
-
- len -= NM_STRLEN(NM_KEYFILE_PATH_SUFFIX_NMMETA);
-
- if (!NM_IN_SET(len, 36, 40)) {
- /* the remaining part of the filename has not the right length to
- * contain a UUID (according to nm_utils_is_uuid()). */
- return NULL;
- }
-
- uuid = nm_strndup_a(100, filename, len, NULL);
- if (!nm_utils_is_uuid(uuid))
- return NULL;
-
- NM_SET_OUT(out_uuid_len, len);
- return filename;
-}
-
-char *
-nms_keyfile_nmmeta_filename(const char *dirname, const char *uuid, gboolean temporary)
-{
- char filename[250];
- char *s;
-
- nm_assert(dirname && dirname[0] == '/');
- nm_assert(nm_utils_is_uuid(uuid) && !strchr(uuid, '/'));
-
- if (g_snprintf(filename,
- sizeof(filename),
- "%s%s%s",
- uuid,
- NM_KEYFILE_PATH_SUFFIX_NMMETA,
- temporary ? "~" : "")
- >= sizeof(filename)) {
- /* valid uuids are limited in length (nm_utils_is_uuid). The buffer should always
- * be large enough. */
- nm_assert_not_reached();
- }
-
- s = g_build_filename(dirname, filename, NULL);
-
- nm_assert(nm_keyfile_utils_ignore_filename(s, FALSE));
-
- return s;
-}
-
-gboolean
-nms_keyfile_nmmeta_read(const char * dirname,
- const char * filename,
- char ** out_full_filename,
- char ** out_uuid,
- char ** out_loaded_path,
- char ** out_shadowed_storage,
- struct stat *out_st)
-{
- const char * uuid;
- guint uuid_len;
- gs_free char *full_filename = NULL;
- gs_free char *loaded_path = NULL;
- gs_free char *shadowed_storage = NULL;
- struct stat st_stack;
- struct stat * st = out_st ?: &st_stack;
-
- nm_assert(dirname && dirname[0] == '/');
- nm_assert(filename && filename[0] && !strchr(filename, '/'));
-
- uuid = nms_keyfile_nmmeta_check_filename(filename, &uuid_len);
- if (!uuid)
- return FALSE;
-
- full_filename = g_build_filename(dirname, filename, NULL);
-
- if (!nms_keyfile_utils_check_file_permissions(NMS_KEYFILE_FILETYPE_NMMETA,
- full_filename,
- st,
- NULL))
- return FALSE;
-
- if (S_ISREG(st->st_mode)) {
- nm_auto_unref_keyfile GKeyFile *kf = NULL;
- gs_free char * v_uuid = NULL;
-
- kf = g_key_file_new();
-
- if (!g_key_file_load_from_file(kf, full_filename, G_KEY_FILE_NONE, NULL))
- return FALSE;
-
- v_uuid = g_key_file_get_string(kf,
- NMMETA_KF_GROUP_NAME_NMMETA,
- NMMETA_KF_KEY_NAME_NMMETA_UUID,
- NULL);
- if (!nm_streq0(v_uuid, uuid))
- return FALSE;
-
- loaded_path = g_key_file_get_string(kf,
- NMMETA_KF_GROUP_NAME_NMMETA,
- NMMETA_KF_KEY_NAME_NMMETA_LOADED_PATH,
- NULL);
- shadowed_storage = g_key_file_get_string(kf,
- NMMETA_KF_GROUP_NAME_NMMETA,
- NMMETA_KF_KEY_NAME_NMMETA_SHADOWED_STORAGE,
- NULL);
-
- if (!loaded_path && !shadowed_storage) {
- /* if there is no useful information in the file, it is the same as if
- * the file is not present. Signal failure. */
- return FALSE;
- }
-
- } else {
- loaded_path = nm_utils_read_link_absolute(full_filename, NULL);
- if (!loaded_path)
- return FALSE;
- }
-
- NM_SET_OUT(out_uuid, g_strndup(uuid, uuid_len));
- NM_SET_OUT(out_full_filename, g_steal_pointer(&full_filename));
- NM_SET_OUT(out_loaded_path, g_steal_pointer(&loaded_path));
- NM_SET_OUT(out_shadowed_storage, g_steal_pointer(&shadowed_storage));
- return TRUE;
-}
-
-gboolean
-nms_keyfile_nmmeta_read_from_file(const char *full_filename,
- char ** out_dirname,
- char ** out_filename,
- char ** out_uuid,
- char ** out_loaded_path,
- char ** out_shadowed_storage)
-{
- gs_free char *dirname = NULL;
- gs_free char *filename = NULL;
-
- nm_assert(full_filename && full_filename[0] == '/');
-
- filename = g_path_get_basename(full_filename);
- dirname = g_path_get_dirname(full_filename);
-
- if (!nms_keyfile_nmmeta_read(dirname,
- filename,
- NULL,
- out_uuid,
- out_loaded_path,
- out_shadowed_storage,
- NULL))
- return FALSE;
-
- NM_SET_OUT(out_dirname, g_steal_pointer(&dirname));
- NM_SET_OUT(out_filename, g_steal_pointer(&filename));
- return TRUE;
-}
-
-int
-nms_keyfile_nmmeta_write(const char *dirname,
- const char *uuid,
- const char *loaded_path,
- gboolean loaded_path_allow_relative,
- const char *shadowed_storage,
- char ** out_full_filename)
-{
- gs_free char *full_filename_tmp = NULL;
- gs_free char *full_filename = NULL;
- int errsv;
-
- nm_assert(dirname && dirname[0] == '/');
- nm_assert(nm_utils_is_uuid(uuid) && !strchr(uuid, '/'));
- nm_assert(!loaded_path || loaded_path[0] == '/');
- nm_assert(!shadowed_storage || loaded_path);
-
- full_filename_tmp = nms_keyfile_nmmeta_filename(dirname, uuid, TRUE);
-
- nm_assert(g_str_has_suffix(full_filename_tmp, "~"));
- nm_assert(nm_utils_file_is_in_path(full_filename_tmp, dirname));
-
- (void) unlink(full_filename_tmp);
-
- if (!loaded_path) {
- full_filename_tmp[strlen(full_filename_tmp) - 1] = '\0';
- errsv = 0;
- if (unlink(full_filename_tmp) != 0) {
- errsv = -NM_ERRNO_NATIVE(errno);
- if (errsv == -ENOENT)
- errsv = 0;
- }
- NM_SET_OUT(out_full_filename, g_steal_pointer(&full_filename_tmp));
- return errsv;
- }
-
- if (loaded_path_allow_relative) {
- const char *f;
-
- f = nm_utils_file_is_in_path(loaded_path, dirname);
- if (f) {
- /* @loaded_path points to a file directly in @dirname.
- * Don't use absolute paths. */
- loaded_path = f;
- }
- }
-
- full_filename = g_strndup(full_filename_tmp, strlen(full_filename_tmp) - 1);
-
- if (shadowed_storage) {
- nm_auto_unref_keyfile GKeyFile *kf = NULL;
- gs_free char * contents = NULL;
- gsize length;
-
- kf = g_key_file_new();
-
- g_key_file_set_string(kf,
- NMMETA_KF_GROUP_NAME_NMMETA,
- NMMETA_KF_KEY_NAME_NMMETA_UUID,
- uuid);
- g_key_file_set_string(kf,
- NMMETA_KF_GROUP_NAME_NMMETA,
- NMMETA_KF_KEY_NAME_NMMETA_LOADED_PATH,
- loaded_path);
- g_key_file_set_string(kf,
- NMMETA_KF_GROUP_NAME_NMMETA,
- NMMETA_KF_KEY_NAME_NMMETA_SHADOWED_STORAGE,
- shadowed_storage);
-
- contents = g_key_file_to_data(kf, &length, NULL);
-
- if (!nm_utils_file_set_contents(full_filename, contents, length, 0600, &errsv, NULL)) {
- NM_SET_OUT(out_full_filename, g_steal_pointer(&full_filename_tmp));
- return -NM_ERRNO_NATIVE(errsv);
- }
- } else {
- /* we only have the "loaded_path" to store. That is commonly used for the tombstones to
- * link to /dev/null. A symlink is sufficient to store that amount of information.
- * No need to bother with a keyfile. */
- if (symlink(loaded_path, full_filename_tmp) != 0) {
- errsv = -NM_ERRNO_NATIVE(errno);
- full_filename_tmp[strlen(full_filename_tmp) - 1] = '\0';
- NM_SET_OUT(out_full_filename, g_steal_pointer(&full_filename_tmp));
- return errsv;
- }
-
- if (rename(full_filename_tmp, full_filename) != 0) {
- errsv = -NM_ERRNO_NATIVE(errno);
- (void) unlink(full_filename_tmp);
- NM_SET_OUT(out_full_filename, g_steal_pointer(&full_filename));
- return errsv;
- }
- }
-
- NM_SET_OUT(out_full_filename, g_steal_pointer(&full_filename));
- return 0;
-}
-
-/*****************************************************************************/
-
-gboolean
-nms_keyfile_utils_check_file_permissions_stat(NMSKeyfileFiletype filetype,
- const struct stat *st,
- GError ** error)
-{
- g_return_val_if_fail(st, FALSE);
-
- if (filetype == NMS_KEYFILE_FILETYPE_KEYFILE) {
- if (!S_ISREG(st->st_mode)) {
- g_set_error_literal(error,
- NM_SETTINGS_ERROR,
- NM_SETTINGS_ERROR_INVALID_CONNECTION,
- "file is not a regular file");
- return FALSE;
- }
- } else if (filetype == NMS_KEYFILE_FILETYPE_NMMETA) {
- if (!S_ISLNK(st->st_mode) && !S_ISREG(st->st_mode)) {
- g_set_error_literal(error,
- NM_SETTINGS_ERROR,
- NM_SETTINGS_ERROR_INVALID_CONNECTION,
- "file is neither a symlink nor a regular file");
- return FALSE;
- }
- } else
- g_return_val_if_reached(FALSE);
-
- if (!NM_FLAGS_HAS(nm_utils_get_testing(), NM_UTILS_TEST_NO_KEYFILE_OWNER_CHECK)) {
- if (st->st_uid != 0) {
- g_set_error(error,
- NM_SETTINGS_ERROR,
- NM_SETTINGS_ERROR_INVALID_CONNECTION,
- "File owner (%lld) is insecure",
- (long long) st->st_uid);
- return FALSE;
- }
-
- if (S_ISREG(st->st_mode) && (st->st_mode & 0077)) {
- g_set_error(error,
- NM_SETTINGS_ERROR,
- NM_SETTINGS_ERROR_INVALID_CONNECTION,
- "File permissions (%03o) are insecure",
- st->st_mode);
- return FALSE;
- }
- }
-
- return TRUE;
-}
-
-gboolean
-nms_keyfile_utils_check_file_permissions(NMSKeyfileFiletype filetype,
- const char * filename,
- struct stat * out_st,
- GError ** error)
-{
- struct stat st;
- int errsv;
-
- g_return_val_if_fail(filename && filename[0] == '/', FALSE);
-
- if (filetype == NMS_KEYFILE_FILETYPE_KEYFILE) {
- if (stat(filename, &st) != 0) {
- errsv = errno;
- g_set_error(error,
- NM_SETTINGS_ERROR,
- NM_SETTINGS_ERROR_INVALID_CONNECTION,
- "cannot access file: %s",
- nm_strerror_native(errsv));
- return FALSE;
- }
- } else if (filetype == NMS_KEYFILE_FILETYPE_NMMETA) {
- if (lstat(filename, &st) != 0) {
- errsv = errno;
- g_set_error(error,
- NM_SETTINGS_ERROR,
- NM_SETTINGS_ERROR_INVALID_CONNECTION,
- "cannot access file: %s",
- nm_strerror_native(errsv));
- return FALSE;
- }
- } else
- g_return_val_if_reached(FALSE);
-
- if (!nms_keyfile_utils_check_file_permissions_stat(filetype, &st, error))
- return FALSE;
-
- NM_SET_OUT(out_st, st);
- return TRUE;
-}