Files
s390-tools/zdev/src/udev.c
Vineeth Vijayan 07ff9e1da0 zdev: limit the derivation of ZDEV_SITE_ID
Currently ZDEV_SITE_ID is derived with the help of an additional
udev-rule, 40-zdev-id.rules. The sole purpose of this rule is to
determine the ZDEV_SITE_ID environment value with the help of zdev_id
binary. This solution is minimal, but this has some unwanted side-
effects. The zdev_id logic get executed for all the events, even
those completely unrelated to zdev/or site, and imports the unneeded
envionment values to the udev-db.

Instead of having an additional rule file, add this logic as part of
the udev-rule of those devices which are configured with site-support.
The logic will then be available on all those rules with the
site-supported devices only.

Signed-off-by: Vineeth Vijayan <vneethv@linux.ibm.com>
Reviewed-by: Peter Oberparleiter <oberpar@linux.ibm.com>
Signed-off-by: Jan Höppner <hoeppner@linux.ibm.com>
2023-11-07 14:13:38 +01:00

152 lines
3.1 KiB
C

/*
* zdev - Modify and display the persistent configuration of devices
*
* Copyright IBM Corp. 2016, 2017
*
* s390-tools is free software; you can redistribute it and/or modify
* it under the terms of the MIT license. See LICENSE for details.
*/
#include <ctype.h>
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "lib/util_path.h"
#include "lib/util_udev.h"
#include "attrib.h"
#include "ccw.h"
#include "device.h"
#include "misc.h"
#include "path.h"
#include "setting.h"
#include "udev.h"
#include "zdev_id.h"
int udev_need_settle = 0;
int udev_no_settle;
/* Check if a udev file does not contain any statements. */
bool udev_file_is_empty(struct util_udev_file *file)
{
struct util_udev_line_node *l;
if (!file)
return true;
util_list_iterate(&file->lines, l) {
if (l->line[0])
return false;
}
return true;
}
static bool get_ids_cb(const char *filename, void *data)
{
char *prefix = data;
if (strncmp(filename, prefix, strlen(prefix)) != 0)
return false;
if (!ends_with(filename, UDEV_SUFFIX))
return false;
return true;
}
/* Add the IDs for all devices of the specified subtype name for which a
* udev rule exists to strlist LIST. */
void udev_get_device_ids(const char *type, struct util_list *list,
bool autoconf)
{
char *path, *prefix;
struct util_list *files;
struct strlist_node *s;
size_t plen, len;
prefix = misc_asprintf("%s-%s-", UDEV_PREFIX, type);
plen = strlen(prefix);
path = path_get_udev_rules(autoconf);
files = strlist_new();
if (!misc_read_dir(path, files, get_ids_cb, prefix))
goto out;
util_list_iterate(files, s) {
/* 41-dasd-eckd-0.0.1234.rules */
len = strlen(s->str);
s->str[len - sizeof(UDEV_SUFFIX) + 1] = 0;
strlist_add(list, &s->str[plen]);
}
out:
strlist_free(files);
free(path);
free(prefix);
}
/* Remove UDEV rule for device. */
exit_code_t udev_remove_rule(const char *type, const char *id, bool autoconf)
{
char *path;
exit_code_t rc = EXIT_OK;
path = path_get_udev_rule(type, id, autoconf);
if (util_path_is_reg_file(path))
rc = remove_file(path);
free(path);
return rc;
}
/* Wait for all current udev events to finish. */
void udev_settle(void)
{
if (udev_no_settle)
return;
misc_system(err_ignore, "%s settle", PATH_UDEVADM);
}
/* Extract internal attribute settings from @entry and add to @list.
* Associate corresponding attribute if found in @attribs. */
void udev_add_internal_from_entry(struct setting_list *list,
struct util_udev_entry_node *entry,
struct attrib **attribs)
{
char *copy, *name, *end, *u;
struct attrib *a;
/* ENV{zdev_var}="1" */
copy = misc_strdup(entry->key);
/* Find attribute name start. */
name = strchr(copy, '{');
end = strrchr(copy, '}');
if (!name || !end)
goto out;
*end = 0;
name++;
/* zdev_ => zdev: */
u = strchr(name, '_');
if (u)
*u = ':';
a = attrib_find(attribs, name);
setting_list_apply_actual(list, a, name, entry->value);
out:
free(copy);
}
bool is_legacy_rule(struct util_udev_file *file)
{
struct util_udev_line_node *line;
util_list_iterate(&file->lines, line)
if (starts_with(line->line, SITE_BLOCK_START))
return false;
return true;
}