svn commit: samba r10583 - in branches/tmp/vl-cluster/source: lib
torture
vlendec at samba.org
vlendec at samba.org
Wed Sep 28 15:15:22 GMT 2005
Author: vlendec
Date: 2005-09-28 15:15:22 +0000 (Wed, 28 Sep 2005)
New Revision: 10583
WebSVN: http://websvn.samba.org/cgi-bin/viewcvs.cgi?view=rev&root=samba&rev=10583
Log:
Commit a checkpoint to proceed from: This implements the fallback to the
dispatch socket if the direct non-blocking send fails with EAGAIN. However,
the central daemon now seems to hit a bug in the linux kernel where select
says a unix *dgram* socket is writable but the subsequent send/write block.
BTW, if you want a perfect backup of your data, post to linux-kernel. Google
for the string 'select "unix dgram socket"' and see on how many mailing list
archives the corresponding message by "Koblinger Egmont" shows up...
Volker
Modified:
branches/tmp/vl-cluster/source/lib/messages.c
branches/tmp/vl-cluster/source/torture/msgtest.c
Changeset:
Modified: branches/tmp/vl-cluster/source/lib/messages.c
===================================================================
--- branches/tmp/vl-cluster/source/lib/messages.c 2005-09-28 14:42:04 UTC (rev 10582)
+++ branches/tmp/vl-cluster/source/lib/messages.c 2005-09-28 15:15:22 UTC (rev 10583)
@@ -110,6 +110,13 @@
return False;
}
+ if (set_blocking(socket_fd, False) < 0) {
+ DEBUG(0, ("set_blocking failed: %s\n", strerror(errno)));
+ close(socket_fd);
+ socket_fd = -1;
+ return False;
+ }
+
return True;
}
@@ -205,11 +212,13 @@
size_t packet_len = sizeof(struct message_rec) + len;
struct sockaddr_un sunaddr;
ssize_t sent;
+ int attempts;
+ BOOL result = False;
packet = data_blob(NULL, packet_len);
if (packet.data == NULL) {
DEBUG(0, ("malloc failed\n"));
- return False;
+ goto done;
}
hdr = (struct message_rec *)packet.data;
@@ -226,32 +235,71 @@
ZERO_STRUCT(sunaddr);
sunaddr.sun_family = AF_UNIX;
-#if 0
strncpy(sunaddr.sun_path, message_path(&pid),
sizeof(sunaddr.sun_path)-1);
- sent = sendto(socket_fd, packet.data, packet.length, 0,
- (struct sockaddr *)&sunaddr, sizeof(sunaddr));
- if (sent != packet.length) {
- DEBUG(3, ("Could not send %d bytes to Unix domain socket %s: "
- "%s\n", packet.length, sunaddr.sun_path,
+
+ for (attempts = 0; attempts < 10; attempts++) {
+ sent = sendto(socket_fd, packet.data, packet.length, 0,
+ (struct sockaddr *)&sunaddr, sizeof(sunaddr));
+ if ((sent < 0) && (errno == EINTR)) {
+ continue;
+ }
+ break;
+ }
+
+ if (sent == packet.length) {
+ result = True;
+ goto done;
+ }
+
+ if (sent > 0) {
+ DEBUG(0, ("tried to send %d bytes, send returned %d ?? \n",
+ packet.length, sent));
+ goto done;
+ }
+
+ if ((errno != EAGAIN) && (errno != EWOULDBLOCK)) {
+ DEBUG(3, ("Could not send %d bytes to Unix domain "
+ "socket %s: %s\n", packet.length,
+ sunaddr.sun_path, strerror(errno)));
+ goto done;
+ }
+
+ DEBUG(10, ("sending directly would block -- sending to dispatcher in "
+ "blocking mode\n"));
+
+ if (set_blocking(socket_fd, True) < 0) {
+ DEBUG(3, ("Could not set socket to blocking mode: %s\n",
strerror(errno)));
- SAFE_FREE(packet.data);
- return False;
+ goto done;
}
-#endif
-
+
strncpy(sunaddr.sun_path, dispatch_socket_name(),
sizeof(sunaddr.sun_path)-1);
- sent = sendto(socket_fd, packet.data, packet.length, 0,
- (struct sockaddr *)&sunaddr, sizeof(sunaddr));
+
+ for (attempts = 0; attempts < 10; attempts++) {
+ sent = sendto(socket_fd, packet.data, packet.length, 0,
+ (struct sockaddr *)&sunaddr, sizeof(sunaddr));
+ if ((sent < 0) && (errno == EINTR)) {
+ continue;
+ }
+ break;
+ }
if (sent != packet.length) {
DEBUG(3, ("Could not send %d bytes to dispatch socket %s: "
"%s\n", packet.length, sunaddr.sun_path,
strerror(errno)));
- SAFE_FREE(packet.data);
- return False;
}
+ if (set_blocking(socket_fd, False) < 0) {
+ DEBUG(3, ("Could not set socket to non-blocking mode: %s\n",
+ strerror(errno)));
+ }
+
+ result = True;
+
+ done:
+
SAFE_FREE(packet.data);
return True;
}
@@ -824,11 +872,13 @@
talloc_set_destructor(result, messaging_client_destr);
+#if 0
if (set_blocking(result->fd, False) < 0) {
DEBUG(5, ("set_blocking() failed: %s\n", strerror(errno)));
talloc_free(result);
return NULL;
}
+#endif
sunaddr.sun_family = AF_UNIX;
strncpy(sunaddr.sun_path, message_path(pid),
@@ -946,7 +996,7 @@
DEBUG(10, ("dispatching to client %s\n",
procid_str_static(&client->pid)));
- sent = send(client->fd, msg->data.data, msg->data.length, 0);
+ sent = write(client->fd, msg->data.data, msg->data.length);
if (sent < 0) {
if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) {
Modified: branches/tmp/vl-cluster/source/torture/msgtest.c
===================================================================
--- branches/tmp/vl-cluster/source/torture/msgtest.c 2005-09-28 14:42:04 UTC (rev 10582)
+++ branches/tmp/vl-cluster/source/torture/msgtest.c 2005-09-28 15:15:22 UTC (rev 10583)
@@ -43,27 +43,46 @@
lp_load(dyn_CONFIGFILE,False,False,False);
- message_init();
-
- if (argc != 3) {
- fprintf(stderr, "%s: Usage - %s pid count\n", argv[0], argv[0]);
+ if ((argc < 3) || (argc > 4)) {
+ fprintf(stderr, "%s: Usage - %s pid count [conffile]\n",
+ argv[0], argv[0]);
exit(1);
}
- pid = atoi(argv[1]);
+ if (strcmp(argv[1], "self") == 0) {
+ pid = getpid();
+ } else {
+ pid = atoi(argv[1]);
+ }
n = atoi(argv[2]);
+ if (argc == 4) {
+ lp_load(argv[3],False,False,False);
+ }
+
+ sec_init();
+ if (!message_init()) {
+ exit(1);
+ }
+
message_register(MSG_PONG, pong_message);
for (i=0;i<n;i++) {
message_send_pid(pid_to_procid(pid), MSG_PING, NULL, 0, True);
}
+ system("/bin/sleep 60");
+
while (pong_count < i) {
+ fd_set rfds;
+ struct timeval tv = timeval_set(1,0);
+ FD_ZERO(&rfds);
+ FD_SET(message_socket(), &rfds);
+ select(message_socket()+1, &rfds, NULL, NULL, &tv);
message_dispatch();
- smb_msleep(1);
}
+#if 0
/* Now test that the duplicate filtering code works. */
pong_count = 0;
@@ -85,6 +104,7 @@
fprintf(stderr, "Duplicate filter failed (%d).\n", pong_count);
exit(1);
}
+#endif
return (0);
}
More information about the samba-cvs
mailing list