Re: [Utopia] kernel -> dbus event delivery?
- From: Kay Sievers <kay sievers vrfy org>
- To: Robert Love <rml ximian com>
- Cc: utopia-list gnome org
- Subject: Re: [Utopia] kernel -> dbus event delivery?
- Date: Sun, 11 Jul 2004 14:20:33 +0200
On Fri, Jul 09, 2004 at 07:18:19PM +0200, Kay Sievers wrote:
> On Fri, Jul 09, 2004 at 01:39:54AM +0200, Kay Sievers wrote:
> > On Thu, Jul 08, 2004 at 10:34:18AM -0400, Robert Love wrote:
> > >
> > > I will be talking at OLS on the event system and D-BUS, so hopefully I
> > > can attract some attention.
> > >
> > > Anyhow, my latest patch is here:
> > >
> > > http://www.kernel.org/pub/linux/kernel/people/rml/events/
>
> I want to be able to send hotplug messages on a new group, so what is the
> best raw format to compose it. We need to pass several key value pairs, like
> we do in the environment of the hotplug call today. Should the strings be:
> 'KEY=value\0KEY2=value2\0', or should we use
> 'KEY:value\nKEY2:value2\n\n', like the mail header format?
> (As a proof of the concept, I will probably convert udevd to listen on the
> socket, instead of getting the message by the forked udevsend helper)
Ok, here we go. Attached is a experimental patch to udevd, which
switches from the forked udevsend helper to listen directly to the
netlink socket. It's only to proof the concept, the parsing code
is totally stupid :)
I have now 2 applications running kdbusd getting all broadcasts and
udevd getting only KMSG_HOTPLUG. Did I already mention it? Netlink
broadcast is soo cool. :)
It looks pretty nice, is blasting fast and 21th century!
Thanks,
Kay
===== Makefile 1.163 vs edited =====
--- 1.163/Makefile 2004-07-09 19:59:03 +02:00
+++ edited/Makefile 2004-07-11 13:16:40 +02:00
@@ -165,7 +165,7 @@
WARNINGS += -Wshadow -Wstrict-prototypes -Wmissing-prototypes -Wmissing-declarations
CRT0 =
LIBC =
- CFLAGS += $(WARNINGS) -I$(GCCINCDIR)
+ CFLAGS += $(WARNINGS) -I ../linux.pm/include -I$(GCCINCDIR)
LIB_OBJS = -lc
LDFLAGS =
endif
===== udevd.c 1.33 vs edited =====
--- 1.33/udevd.c 2004-06-07 02:50:03 +02:00
+++ edited/udevd.c 2004-07-11 14:04:19 +02:00
@@ -31,7 +31,9 @@
#include <sys/time.h>
#include <sys/types.h>
#include <sys/socket.h>
-#include <sys/un.h>
+#include <sys/user.h>
+#include <linux/netlink.h>
+#include <linux/kmessage.h>
#include <fcntl.h>
#include "klibc_fixups.h"
#include <sys/sysinfo.h>
@@ -43,6 +45,11 @@
#include "udevd.h"
#include "logging.h"
+#define SENDER_HEADER "From: "
+#define SIGNAL_HEADER "Signal: "
+#define DEVPATH_HEADER "Devpath: "
+#define SEQNUM_HEADER "Seqnum: "
+
static int pipefds[2];
static int expected_seqnum = 0;
volatile static int children_waiting;
@@ -247,11 +254,9 @@
{
struct hotplug_msg *msg;
int retval;
- struct msghdr smsg;
- struct cmsghdr *cmsg;
- struct iovec iov;
- struct ucred *cred;
- char cred_msg[CMSG_SPACE(sizeof(struct ucred))];
+ char buf[PAGE_SIZE];
+ char *string;
+ char *pos;
msg = msg_create();
if (msg == NULL) {
@@ -259,38 +264,60 @@
return;
}
- iov.iov_base = msg;
- iov.iov_len = sizeof(struct hotplug_msg);
-
- memset(&smsg, 0x00, sizeof(struct msghdr));
- smsg.msg_iov = &iov;
- smsg.msg_iovlen = 1;
- smsg.msg_control = cred_msg;
- smsg.msg_controllen = sizeof(cred_msg);
-
- retval = recvmsg(sock, &smsg, 0);
+ retval = recv(sock, &buf, sizeof(buf), 0);
if (retval < 0) {
if (errno != EINTR)
dbg("unable to receive message");
return;
}
- cmsg = CMSG_FIRSTHDR(&smsg);
- cred = (struct ucred *) CMSG_DATA(cmsg);
- if (cmsg == NULL || cmsg->cmsg_type != SCM_CREDENTIALS) {
- dbg("no sender credentials received, message ignored");
+ /* STUPID-TEST-ONLY: HARD CODED MESSAGE PARSING */
+
+ pos = buf;
+
+ string = strsep(&pos, "\n");
+ if (string == NULL)
+ goto skip;
+
+ /* expecting sending object */
+ if (strncmp(string, SENDER_HEADER, strlen(SENDER_HEADER)) != 0) {
+ dbg("missing " SENDER_HEADER);
goto skip;
}
+ string = strsep(&pos, "\n");
+ if (string == NULL)
+ goto skip;
- if (cred->uid != 0) {
- dbg("sender uid=%i, message ignored", cred->uid);
+ /* expecting name of signal, emitted from object */
+ if (strncmp(string, SIGNAL_HEADER, strlen(SIGNAL_HEADER)) != 0) {
+ dbg("missing " SIGNAL_HEADER);
goto skip;
}
+ strfieldcpy(msg->action, &string[strlen(SIGNAL_HEADER)]);
+ dbg("action '%s'", msg->action);
+ string = strsep(&pos, "\n");
+ if (string == NULL)
+ goto skip;
- if (strncmp(msg->magic, UDEV_MAGIC, sizeof(UDEV_MAGIC)) != 0 ) {
- dbg("message magic '%s' doesn't match, ignore it", msg->magic);
+ /* expecting devpath */
+ if (strncmp(string, DEVPATH_HEADER, strlen(DEVPATH_HEADER)) != 0) {
+ dbg("missing " DEVPATH_HEADER);
goto skip;
}
+ strfieldcpy(msg->devpath, &string[strlen(DEVPATH_HEADER)]);
+ dbg("devpath '%s'", msg->devpath);
+ string = strsep(&pos, "\n");
+ if (string == NULL)
+ goto skip;
+
+ /* expecting sequence */
+ if (strncmp(string, SEQNUM_HEADER, strlen(SEQNUM_HEADER)) != 0) {
+ dbg("missing " SEQNUM_HEADER);
+ goto skip;
+ }
+ msg->seqnum = atoi(&string[strlen(SEQNUM_HEADER)]);
+ dbg("seqnum '%i'", msg->seqnum);
+
/* if no seqnum is given, we move straight to exec queue */
if (msg->seqnum == -1) {
@@ -393,10 +420,8 @@
int main(int argc, char *argv[])
{
int ssock, maxsockplus;
- struct sockaddr_un saddr;
- socklen_t addrlen;
+ struct sockaddr_nl snl;
int retval;
- const int on = 1;
struct sigaction act;
fd_set readfds;
@@ -436,27 +461,22 @@
sigaction(SIGALRM, &act, NULL);
sigaction(SIGCHLD, &act, NULL);
- memset(&saddr, 0x00, sizeof(saddr));
- saddr.sun_family = AF_LOCAL;
- /* use abstract namespace for socket path */
- strcpy(&saddr.sun_path[1], UDEVD_SOCK_PATH);
- addrlen = offsetof(struct sockaddr_un, sun_path) + strlen(saddr.sun_path+1) + 1;
+ memset(&snl, 0x00, sizeof(snl));
+ snl.nl_family = AF_NETLINK;
+ snl.nl_pid = getpid();
+ snl.nl_groups = 0xffff; //1 << KMSG_HOTPLUG;
- ssock = socket(AF_LOCAL, SOCK_DGRAM, 0);
+ ssock = socket(PF_NETLINK, SOCK_DGRAM, NETLINK_KMESSAGE);
if (ssock == -1) {
dbg("error getting socket, exit");
exit(1);
}
- /* the bind takes care of ensuring only one copy running */
- retval = bind(ssock, (struct sockaddr *) &saddr, addrlen);
+ retval = bind(ssock, (struct sockaddr *) &snl, sizeof(snl));
if (retval < 0) {
dbg("bind failed, exit");
goto exit;
}
-
- /* enable receiving of the sender credentials */
- setsockopt(ssock, SOL_SOCKET, SO_PASSCRED, &on, sizeof(on));
/* possible override of udev binary, used for testing */
udev_bin = getenv("UDEV_BIN");
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]