summaryrefslogtreecommitdiffstats
path: root/daemon/file.c
diff options
context:
space:
mode:
authorRichard W.M. Jones <rjones@redhat.com>2009-07-21 11:00:47 +0100
committerRichard W.M. Jones <rjones@redhat.com>2009-07-21 11:18:34 +0100
commite315e0723ec8c2f84809f06d7f2ede4955dd6c67 (patch)
tree6ab1add695fea97184a3aa0680084c4f2c220a1b /daemon/file.c
parentf6eb8d44942c3d550c72933c406905f2cb86278d (diff)
downloadlibguestfs-e315e0723ec8c2f84809f06d7f2ede4955dd6c67.tar.gz
libguestfs-e315e0723ec8c2f84809f06d7f2ede4955dd6c67.tar.xz
libguestfs-e315e0723ec8c2f84809f06d7f2ede4955dd6c67.zip
Generator: Implement RBufferOut and "read-file" call.
This commit implements the RBufferOut type for returning arbitrary 8 bit data from calls. We also implement the guestfs_read_file call to read a whole file that can contain any 8 bit content, but up to a limit of ~ 2 MB.
Diffstat (limited to 'daemon/file.c')
-rw-r--r--daemon/file.c59
1 files changed, 59 insertions, 0 deletions
diff --git a/daemon/file.c b/daemon/file.c
index 851d9e7c..66b3d125 100644
--- a/daemon/file.c
+++ b/daemon/file.c
@@ -323,6 +323,65 @@ do_write_file (char *path, char *content, int size)
return 0;
}
+char *
+do_read_file (char *path, size_t *size_r)
+{
+ int fd;
+ struct stat statbuf;
+ char *r;
+
+ NEED_ROOT (NULL);
+ ABS_PATH (path, NULL);
+
+ CHROOT_IN;
+ fd = open (path, O_RDONLY);
+ CHROOT_OUT;
+
+ if (fd == -1) {
+ reply_with_perror ("open: %s", path);
+ return NULL;
+ }
+
+ if (fstat (fd, &statbuf) == -1) {
+ reply_with_perror ("fstat: %s", path);
+ close (fd);
+ return NULL;
+ }
+
+ *size_r = statbuf.st_size;
+ /* The actual limit on messages is smaller than this. This
+ * check just limits the amount of memory we'll try and allocate
+ * here. If the message is larger than the real limit, that will
+ * be caught later when we try to serialize the message.
+ */
+ if (*size_r >= GUESTFS_MESSAGE_MAX) {
+ reply_with_error ("read_file: %s: file is too large for the protocol, use gusetfs_download instead", path);
+ close (fd);
+ return NULL;
+ }
+ r = malloc (*size_r);
+ if (r == NULL) {
+ reply_with_perror ("malloc");
+ close (fd);
+ return NULL;
+ }
+
+ if (xread (fd, r, *size_r) == -1) {
+ reply_with_perror ("read: %s", path);
+ close (fd);
+ free (r);
+ return NULL;
+ }
+
+ if (close (fd) == -1) {
+ reply_with_perror ("close: %s", path);
+ free (r);
+ return NULL;
+ }
+
+ return r;
+}
+
/* This runs the 'file' command. */
char *
do_file (char *path)