/*
- * Copyright (C) 2004 Daniel Walsh
+ * libudev - interface to udev device information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation version 2 of the License.
- *
- * This program 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
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * Copyright (C) 2008 Kay Sievers <kay.sievers@vrfy.org>
*
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-#include "config.h"
-
-#include <stdlib.h>
#include <stdio.h>
+#include <stdlib.h>
#include <stddef.h>
+#include <stdarg.h>
#include <unistd.h>
-#include <string.h>
-#include <fcntl.h>
-#include <ctype.h>
-#include <limits.h>
-#include <errno.h>
-#include <sys/stat.h>
#include <selinux/selinux.h>
#include "udev.h"
-#include "udev_selinux.h"
-
-static security_context_t prev_scontext = NULL;
-
-static int is_selinux_running(void)
-{
- static int selinux_enabled = -1;
- if (selinux_enabled == -1)
- selinux_enabled = (is_selinux_enabled() > 0);
+static int selinux_enabled;
+security_context_t selinux_prev_scontext;
- dbg("selinux=%i\n", selinux_enabled);
- return selinux_enabled;
-}
-
-static char *get_media(const char *devname, int mode)
+void selinux_init(struct udev *udev)
{
- FILE *fp;
- char procfile[PATH_MAX];
- char mediabuf[256];
- int size;
- char *media = NULL;
-
- if (!(mode & S_IFBLK))
- return NULL;
-
- snprintf(procfile, PATH_MAX, "/proc/ide/%s/media", devname);
- procfile[PATH_MAX-1] = '\0';
-
- fp = fopen(procfile, "r");
- if (!fp)
- goto out;
-
- if (fgets(mediabuf, sizeof(mediabuf), fp) == NULL)
- goto close_out;
-
- size = strlen(mediabuf);
- while (size-- > 0) {
- if (isspace(mediabuf[size])) {
- mediabuf[size] = '\0';
- } else {
- break;
- }
+ /* record the present security context */
+ selinux_enabled = (is_selinux_enabled() > 0);
+ info(udev, "selinux=%i\n", selinux_enabled);
+ if (!selinux_enabled)
+ return;
+ matchpathcon_init_prefix(NULL, udev_get_dev_path(udev));
+ if (getfscreatecon(&selinux_prev_scontext) < 0) {
+ err(udev, "getfscreatecon failed\n");
+ selinux_prev_scontext = NULL;
}
-
- media = strdup(mediabuf);
- info("selinux_get_media(%s)='%s'\n", devname, media);
-
-close_out:
- fclose(fp);
-out:
- return media;
}
-void selinux_setfilecon(const char *file, const char *devname, unsigned int mode)
+void selinux_exit(struct udev *udev)
{
- if (is_selinux_running()) {
- security_context_t scontext = NULL;
- char *media;
- int ret = -1;
-
- if (devname) {
- media = get_media(devname, mode);
- if (media) {
- ret = matchmediacon(media, &scontext);
- free(media);
- }
- }
-
- if (ret < 0)
- if (matchpathcon(file, mode, &scontext) < 0) {
- err("matchpathcon(%s) failed\n", file);
- return;
- }
-
- if (lsetfilecon(file, scontext) < 0)
- err("setfilecon %s failed: %s\n", file, strerror(errno));
-
- freecon(scontext);
- }
+ if (!selinux_enabled)
+ return;
+ freecon(selinux_prev_scontext);
+ selinux_prev_scontext = NULL;
}
-void selinux_setfscreatecon(const char *file, const char *devname, unsigned int mode)
+void udev_selinux_lsetfilecon(struct udev *udev, const char *file, unsigned int mode)
{
- if (is_selinux_running()) {
- security_context_t scontext = NULL;
- char *media;
- int ret = -1;
-
- if (devname) {
- media = get_media(devname, mode);
- if (media) {
- ret = matchmediacon(media, &scontext);
- free(media);
- }
- }
-
- if (ret < 0)
- if (matchpathcon(file, mode, &scontext) < 0) {
- err("matchpathcon(%s) failed\n", file);
- return;
- }
-
- if (setfscreatecon(scontext) < 0)
- err("setfscreatecon %s failed: %s\n", file, strerror(errno));
-
- freecon(scontext);
- }
+ security_context_t scontext = NULL;
+
+ if (!selinux_enabled)
+ return;
+ if (matchpathcon(file, mode, &scontext) < 0) {
+ err(udev, "matchpathcon(%s) failed\n", file);
+ return;
+ }
+ if (lsetfilecon(file, scontext) < 0)
+ err(udev, "setfilecon %s failed: %m\n", file);
+ freecon(scontext);
}
-void selinux_resetfscreatecon(void)
+void udev_selinux_setfscreatecon(struct udev *udev, const char *file, unsigned int mode)
{
- if (is_selinux_running()) {
- if (setfscreatecon(prev_scontext) < 0)
- err("setfscreatecon failed: %s\n", strerror(errno));
- }
-}
+ security_context_t scontext = NULL;
-void selinux_init(void)
-{
- /*
- * record the present security context, for file-creation
- * restoration creation purposes.
- */
- if (is_selinux_running()) {
- if (!udev_root[0])
- err("selinux_init: udev_root not set\n");
- matchpathcon_init_prefix(NULL, udev_root);
- if (getfscreatecon(&prev_scontext) < 0) {
- err("getfscreatecon failed\n");
- prev_scontext = NULL;
- }
+ if (!selinux_enabled)
+ return;
+ if (matchpathcon(file, mode, &scontext) < 0) {
+ err(udev, "matchpathcon(%s) failed\n", file);
+ return;
}
+ if (setfscreatecon(scontext) < 0)
+ err(udev, "setfscreatecon %s failed: %m\n", file);
+ freecon(scontext);
}
-void selinux_exit(void)
+void udev_selinux_resetfscreatecon(struct udev *udev)
{
- if (is_selinux_running() && prev_scontext) {
- freecon(prev_scontext);
- prev_scontext = NULL;
- }
+ if (!selinux_enabled)
+ return;
+ if (setfscreatecon(selinux_prev_scontext) < 0)
+ err(udev, "setfscreatecon failed: %m\n");
}