File xs_weak_write.patch of Package xenstore-uvp

diff --git a/tools/xenstore/xenstore_client.c b/tools/xenstore/xenstore_client.c
index 94b82b9..0e03622 100644
--- a/tools/xenstore/xenstore_client.c
+++ b/tools/xenstore/xenstore_client.c
@@ -37,6 +37,7 @@ enum mode {
     MODE_rm,
     MODE_write,
     MODE_watch,
+    MODE_weakwrite,
 };
 
 static char *output_buf = NULL;
@@ -99,6 +100,9 @@ usage(enum mode mode, int incl_mode, const char *progname)
     case MODE_watch:
 	mstr = incl_mode ? "watch " : "";
 	errx(1, "Usage: %s %s[-h] [-n NR] key", progname, mstr);
+    case MODE_weakwrite:
+    mstr = incl_mode ? "weakwrite " : "";
+    errx(1, "Usage: %s %s[-h] [-s] key value [...]", progname, mstr);
     }
 }
 
@@ -335,6 +339,18 @@ perform(enum mode mode, int optind, int argc, char **argv, struct xs_handle *xsh
             }
             optind += 2;
         } break;
+        case MODE_weakwrite: {
+            static struct expanding_buffer ebuf;
+            char *val_spec = argv[optind + 1];
+            unsigned len;
+            expanding_buffer_ensure(&ebuf, strlen(val_spec)+1);
+            unsanitise_value(ebuf.buf, &len, val_spec);
+            if (!xs_weak_write(xsh, xth, argv[optind], ebuf.buf, len)) {
+                warnx("could not write path %s", argv[optind]);
+                return 1;
+            }
+            optind += 2;
+        } break;
         case MODE_rm: {
             /* Remove the specified path.  If the tidy flag is set, then also
                remove any containing directories that are both empty and have no
@@ -486,6 +502,8 @@ static enum mode lookup_mode(const char *m)
 	return MODE_read;
     else if (strcmp(m, "watch") == 0)
 	return MODE_watch;
+    else if (strcmp(m, "weakwrite") == 0)
+    return MODE_weakwrite;
 
     errx(1, "unknown mode %s\n", m);
     return 0;
@@ -618,6 +636,7 @@ main(int argc, char **argv)
 	break;
     case MODE_ls:
     case MODE_watch:
+    case MODE_weakwrite:
 	transaction = 0;
 	break;
     default:
diff --git a/tools/xenstore/xenstored_core.c b/tools/xenstore/xenstored_core.c
index 1749740..8de8e9c 100644
--- a/tools/xenstore/xenstored_core.c
+++ b/tools/xenstore/xenstored_core.c
@@ -112,6 +112,8 @@ static char *sockmsg_string(enum xsd_sockmsg_type type)
 	case XS_RELEASE: return "RELEASE";
 	case XS_GET_DOMAIN_PATH: return "GET_DOMAIN_PATH";
 	case XS_WRITE: return "WRITE";
+    case XS_WEAK_WRITE: return "WEAK_WRITE";
+    case XS_LINUX_WEAK_WRITE: return "LINUX_WEAK_WRITE";
 	case XS_MKDIR: return "MKDIR";
 	case XS_RM: return "RM";
 	case XS_SET_PERMS: return "SET_PERMS";
@@ -901,9 +903,31 @@ static void do_write(struct connection *conn, struct buffered_data *in)
 
 	add_change_node(conn->transaction, name, false);
 	fire_watches(conn, name, false);
+	if (XS_WEAK_WRITE == in->hdr.msg.type)
+        send_ack(conn, XS_WEAK_WRITE);
+    else if (XS_LINUX_WEAK_WRITE == in->hdr.msg.type)
+        send_ack(conn, XS_LINUX_WEAK_WRITE);
+    else
 	send_ack(conn, XS_WRITE);
 }
 
+static void do_weak_write(struct connection *conn, struct buffered_data *in)
+{
+    struct connection *connect, *next;
+    next = list_entry(connections.next, typeof(*conn), list);
+    while (&next->list != &connections) {
+        connect = next;
+        if (connect->transaction_started > 0)
+        {
+            send_error(conn, EAGAIN);
+            return;
+        } else {
+            next = list_entry(connect->list.next,
+                            typeof(*connect), list);
+        }
+    }
+    do_write (conn, in);
+}
 static void do_mkdir(struct connection *conn, const char *name)
 {
 	struct node *node;
@@ -1181,7 +1205,10 @@ static void process_message(struct connection *conn, struct buffered_data *in)
 	case XS_WRITE:
 		do_write(conn, in);
 		break;
-
+	case XS_WEAK_WRITE:
+    case XS_LINUX_WEAK_WRITE:  
+		do_weak_write(conn, in);
+		break;
 	case XS_MKDIR:
 		do_mkdir(conn, onearg(in));
 		break;
diff --git a/tools/xenstore/xs.c b/tools/xenstore/xs.c
index c72ea83..089b543 100644
--- a/tools/xenstore/xs.c
+++ b/tools/xenstore/xs.c
@@ -560,6 +560,24 @@ bool xs_write(struct xs_handle *h, xs_transaction_t t,
 				ARRAY_SIZE(iovec), NULL));
 }
 
+/* Write the value of a single file.
+ * Returns false on failure.
+ */
+bool xs_weak_write(struct xs_handle *h, xs_transaction_t t,
+	      const char *path, const void *data, unsigned int len)
+{
+	struct iovec iovec[2];
+
+	iovec[0].iov_base = (void *)path;
+	iovec[0].iov_len = strlen(path) + 1;
+	iovec[1].iov_base = (void *)data;
+	iovec[1].iov_len = len;
+    
+	return xs_bool(xs_talkv(h, t, XS_LINUX_WEAK_WRITE, iovec,
+				ARRAY_SIZE(iovec), NULL));
+}
+
+
 /* Create a new directory.
  * Returns false on failure, or success if it already exists.
  */
diff --git a/tools/xenstore/xs.h b/tools/xenstore/xs.h
index 1cbe255..888ff56 100644
--- a/tools/xenstore/xs.h
+++ b/tools/xenstore/xs.h
@@ -90,6 +90,12 @@ void *xs_read(struct xs_handle *h, xs_transaction_t t,
 bool xs_write(struct xs_handle *h, xs_transaction_t t,
 	      const char *path, const void *data, unsigned int len);
 
+/* Write the value of a single file.
+ * Returns false on failure.
+ */
+bool xs_weak_write(struct xs_handle *h, xs_transaction_t t,
+	      const char *path, const void *data, unsigned int len);
+
 /* Create a new directory.
  * Returns false on failure, or success if it already exists.
  */
diff --git a/xen/include/public/io/xs_wire.h b/xen/include/public/io/xs_wire.h
index e1debce..8da5eee 100644
--- a/xen/include/public/io/xs_wire.h
+++ b/xen/include/public/io/xs_wire.h
@@ -48,7 +48,9 @@ enum xsd_sockmsg_type
     XS_IS_DOMAIN_INTRODUCED,
     XS_RESUME,
     XS_SET_TARGET,
-    XS_RESTRICT
+    XS_RESTRICT,
+    XS_WEAK_WRITE,
+    XS_LINUX_WEAK_WRITE = 128
 };
 
 #define XS_WRITE_NONE "NONE"
openSUSE Build Service is sponsored by