aboutsummaryrefslogtreecommitdiff
path: root/osdep.c
diff options
context:
space:
mode:
authorPaolo Bonzini <pbonzini@redhat.com>2011-09-17 16:27:59 +0200
committerPaolo Bonzini <pbonzini@redhat.com>2011-12-21 15:00:24 +0100
commit993295fedc5fefaefee9ac80e057d8bf08026ef4 (patch)
treeeb86d435a10c80c9b02084decd4a4dc5d1834c7b /osdep.c
parent3799ce4ab64f578eb818689a276e4f0c73d01fb5 (diff)
add qemu_send_full and qemu_recv_full
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Diffstat (limited to 'osdep.c')
-rw-r--r--osdep.c67
1 files changed, 67 insertions, 0 deletions
diff --git a/osdep.c b/osdep.c
index 56e6963f15..70bad27f6e 100644
--- a/osdep.c
+++ b/osdep.c
@@ -166,3 +166,70 @@ int qemu_accept(int s, struct sockaddr *addr, socklen_t *addrlen)
return ret;
}
+
+/*
+ * A variant of send(2) which handles partial write.
+ *
+ * Return the number of bytes transferred, which is only
+ * smaller than `count' if there is an error.
+ *
+ * This function won't work with non-blocking fd's.
+ * Any of the possibilities with non-bloking fd's is bad:
+ * - return a short write (then name is wrong)
+ * - busy wait adding (errno == EAGAIN) to the loop
+ */
+ssize_t qemu_send_full(int fd, const void *buf, size_t count, int flags)
+{
+ ssize_t ret = 0;
+ ssize_t total = 0;
+
+ while (count) {
+ ret = send(fd, buf, count, flags);
+ if (ret < 0) {
+ if (errno == EINTR) {
+ continue;
+ }
+ break;
+ }
+
+ count -= ret;
+ buf += ret;
+ total += ret;
+ }
+
+ return total;
+}
+
+/*
+ * A variant of recv(2) which handles partial write.
+ *
+ * Return the number of bytes transferred, which is only
+ * smaller than `count' if there is an error.
+ *
+ * This function won't work with non-blocking fd's.
+ * Any of the possibilities with non-bloking fd's is bad:
+ * - return a short write (then name is wrong)
+ * - busy wait adding (errno == EAGAIN) to the loop
+ */
+ssize_t qemu_recv_full(int fd, void *buf, size_t count, int flags)
+{
+ ssize_t ret = 0;
+ ssize_t total = 0;
+
+ while (count) {
+ ret = qemu_recv(fd, buf, count, flags);
+ if (ret <= 0) {
+ if (ret < 0 && errno == EINTR) {
+ continue;
+ }
+ break;
+ }
+
+ count -= ret;
+ buf += ret;
+ total += ret;
+ }
+
+ return total;
+}
+