svn commit: r251577 - user/hrs/releng/usr.sbin/makevd
Hiroki Sato
hrs at FreeBSD.org
Sun Jun 9 15:17:40 UTC 2013
Author: hrs
Date: Sun Jun 9 15:17:38 2013
New Revision: 251577
URL: http://svnweb.freebsd.org/changeset/base/251577
Log:
- Fix VMDK and VHD header.
- Add chunksize and padding parameter to support aligned blocks in
rawcopy() and writebuf(). These are required for upcoming VDI support.
- Move uuid handling functions to common.c.
- Rename member variable names.
Modified:
user/hrs/releng/usr.sbin/makevd/common.c
user/hrs/releng/usr.sbin/makevd/common.h
user/hrs/releng/usr.sbin/makevd/raw.c
user/hrs/releng/usr.sbin/makevd/vhd.c
user/hrs/releng/usr.sbin/makevd/vmdk.c
Modified: user/hrs/releng/usr.sbin/makevd/common.c
==============================================================================
--- user/hrs/releng/usr.sbin/makevd/common.c Sun Jun 9 15:08:51 2013 (r251576)
+++ user/hrs/releng/usr.sbin/makevd/common.c Sun Jun 9 15:17:38 2013 (r251577)
@@ -33,14 +33,88 @@ __FBSDID("$FreeBSD$");
#include <sys/queue.h>
#include <err.h>
+#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
+#include <string.h>
#include <unistd.h>
#include "common.h"
-static int rawcopy(int, int);
-static int writebuf(int, void *, ssize_t);
+static int rawcopy(int, int, ssize_t, int);
+static int writebuf(int, void *, ssize_t, ssize_t, int);
+
+char *
+uuid_str2bin(void *dst, const void *src)
+{
+ const char *p;
+ char *q;
+ char buf[3];
+ ssize_t len;
+
+ p = src;
+ len = 0;
+#if _BYTE_ORDER == _BIG_ENDIAN
+ q = (char *)&dst + 16;
+#else
+ q = (char *)&dst;
+#endif
+ while (len < 16 && strlen(p) > 1) {
+ long digit;
+ char *endptr;
+
+ if (*p == '-') {
+ p++;
+ continue;
+ }
+ buf[0] = p[0];
+ buf[1] = p[1];
+ buf[2] = '\0';
+ errno = 0;
+ digit = strtol(buf, &endptr, 16);
+ if (errno == 0 && *endptr != '\0')
+ errno = EINVAL;
+ if (errno) {
+ warn("invalid UUID");
+ return (NULL);
+ }
+#if _BYTE_ORDER == _BIG_ENDIAN
+ *q-- = digit;
+#else
+ *q++ = digit;
+#endif
+ len++;
+ p += 2;
+ }
+#if 0
+ {
+ int i;
+
+ printf("uuid = ");
+ for (i = 0; i < 16; i++)
+ printf("%02x", uuid[i]);
+ printf("\n");
+ }
+#endif
+ return (dst);
+}
+
+char *
+uuid_bin2str(void *dst, const void *src)
+{
+ const char *p;
+ char *q;
+
+ p = src;
+ q = dst;
+ while (p - (char *)src < 16) {
+ snprintf(q, 3, "%02x", *p++);
+ q += 2;
+ }
+ q = '\0';
+
+ return (dst);
+}
int
dispatch_bl(int ofd, struct blhead_t *blhead)
@@ -52,11 +126,15 @@ dispatch_bl(int ofd, struct blhead_t *bl
printf("processing section: %s\n", bl->bl_name);
switch (bl->bl_type) {
case BL_RAWCOPY:
- error = rawcopy(ofd, bl->bl_tf.blf_fd);
+ error = rawcopy(ofd, bl->bl_tf.fd,
+ bl->bl_tf.chunksize,
+ bl->bl_tf.padding);
break;
case BL_RAWDATA:
- error = writebuf(ofd, bl->bl_tr.blr_data,
- bl->bl_tr.blr_len);
+ error = writebuf(ofd, bl->bl_tr.data,
+ bl->bl_tr.len,
+ bl->bl_tr.chunksize,
+ bl->bl_tr.padding);
break;
default:
error = 1;
@@ -69,40 +147,91 @@ dispatch_bl(int ofd, struct blhead_t *bl
}
static int
-rawcopy(int ofd, int ifd)
+rawcopy(int ofd, int ifd, ssize_t chunksize, int padding)
{
- ssize_t len0, len = 0;
- char buf[BUFSIZ];
-
+ ssize_t rlen, wlen, len;
+ size_t remain;
+ u_char buf[BUFSIZ];
+ u_char zero = 0;
+
+ if (chunksize == 0)
+ chunksize = sizeof(buf);
+ remain = chunksize;
for (;;) {
- len0 = read(ifd, buf, sizeof(buf));
- if (len0 == 0)
+ rlen = (remain < sizeof(buf)) ? remain : sizeof(buf);
+ len = read(ifd, buf, rlen);
+ if (len == 0)
break;
- if (len0 < 0) {
+ if (len < 0) {
warn("read error");
return (1);
}
- len = write(ofd, buf, len0);
+ wlen = len;
+ len = write(ofd, buf, wlen);
if (len < 0) {
warn("write error");
return (1);
}
+ remain -= rlen;
+ if (remain == 0)
+ remain = chunksize;
+ }
+ if (padding) {
+ lseek(ofd, remain - 1, SEEK_CUR);
+ len = write(ofd, &zero, 1);
+ if (len != 1) {
+ warn("write error");
+ return (1);
+ }
}
return (0);
}
static int
-writebuf(int ofd, void *buf, ssize_t len)
+writebuf(int ofd, void *buf, ssize_t len, ssize_t chunksize, int padding)
{
- ssize_t len0;
+ ssize_t len0, blks;
+ int i;
u_char *p;
+ u_char zero = 0;
+ if (chunksize == 0)
+ chunksize = len;
p = (u_char *)buf;
- len0 = write(ofd, p, len);
- if (len0 != len) {
- warn("write error");
- return (1);
- }
+ blks = (len + chunksize - 1)/ chunksize;
+
+ for (i = 0; i < blks; i++) {
+ int l;
+
+ fprintf(stderr, "Write %zd\n", chunksize);
+ fprintf(stderr, "Data:");
+ for (l = 0; l < chunksize; l++) {
+ fprintf(stderr, "%02x", *(p+l));
+ }
+ fprintf(stderr, "\n");
+ len0 = write(ofd, p, chunksize);
+ if (len0 != chunksize) {
+ warn("write error");
+ return (1);
+ }
+ p += chunksize;
+ }
+ if (0 < len % chunksize) {
+ len0 = write(ofd, p, len % chunksize);
+ if (len0 != len % chunksize) {
+ warn("write error");
+ return (1);
+ }
+ if (padding) {
+ lseek(ofd, chunksize - (len % chunksize) - 1,
+ SEEK_CUR);
+ len0 = write(ofd, &zero, 1);
+ if (len0 != 1) {
+ warn("write error");
+ return (1);
+ }
+ }
+ }
return (0);
}
Modified: user/hrs/releng/usr.sbin/makevd/common.h
==============================================================================
--- user/hrs/releng/usr.sbin/makevd/common.h Sun Jun 9 15:08:51 2013 (r251576)
+++ user/hrs/releng/usr.sbin/makevd/common.h Sun Jun 9 15:17:38 2013 (r251577)
@@ -32,12 +32,16 @@
#include <sys/queue.h>
struct blist_raw {
- size_t blr_len;
- void *blr_data;
+ size_t len;
+ void *data;
+ size_t chunksize;
+ int padding;
};
struct blist_fd {
- int blf_fd;
+ int fd;
+ size_t chunksize;
+ int padding;
};
struct blist {
@@ -60,5 +64,7 @@ struct blist {
TAILQ_HEAD(blhead_t, blist);
int dispatch_bl(int, struct blhead_t *);
+char *uuid_str2bin(void *, const void *);
+char *uuid_bin2str(void *, const void *);
#endif /* _COMMON_H */
Modified: user/hrs/releng/usr.sbin/makevd/raw.c
==============================================================================
--- user/hrs/releng/usr.sbin/makevd/raw.c Sun Jun 9 15:08:51 2013 (r251576)
+++ user/hrs/releng/usr.sbin/makevd/raw.c Sun Jun 9 15:17:38 2013 (r251577)
@@ -74,7 +74,7 @@ raw_makeim(struct iminfo *imi)
err(EX_OSERR, NULL);
bl->bl_type = BL_RAWCOPY;
bl->bl_name = "rawcopy";
- bl->bl_tf.blf_fd = ifd;
+ bl->bl_tf.fd = ifd;
TAILQ_INSERT_TAIL(&blhead, bl, bl_next);
Modified: user/hrs/releng/usr.sbin/makevd/vhd.c
==============================================================================
--- user/hrs/releng/usr.sbin/makevd/vhd.c Sun Jun 9 15:08:51 2013 (r251576)
+++ user/hrs/releng/usr.sbin/makevd/vhd.c Sun Jun 9 15:17:38 2013 (r251577)
@@ -63,9 +63,6 @@ vhd_makeim(struct iminfo *imi)
uint64_t sectors, heads, cylinders, imagesize;
uint8_t uuid[16];
char vhdfile[PATH_MAX + 10];
- char buf[BUFSIZ];
- char *p, *q;
- ssize_t len = 0;
int ifd, ofd;
TAILQ_INIT(&blhead);
@@ -73,51 +70,12 @@ vhd_makeim(struct iminfo *imi)
ifd = imi->imi_fd;
imagesize = imi->imi_size;
- memset(imh, 0, sizeof(*imh));
if (imi->imi_uuid == NULL)
errx(EX_USAGE, "-o uuid option must be specified.");
+ uuid_str2bin(&uuid, imi->imi_uuid);
+ if (uuid == NULL)
+ return (1);
- p = imi->imi_uuid;
-#if _BYTE_ORDER == _BIG_ENDIAN
- q = (uint8_t *)&uuid + 16;
-#else
- q = (uint8_t *)&uuid;
-#endif
- while (len < 16 && strlen(p) > 1) {
- long digit;
- char *endptr;
-
- if (*p == '-') {
- p++;
- continue;
- }
- buf[0] = p[0];
- buf[1] = p[1];
- buf[2] = '\0';
- errno = 0;
- digit = strtol(buf, &endptr, 16);
- if (errno == 0 && *endptr != '\0')
- errno = EINVAL;
- if (errno)
- errx(EX_DATAERR, "invalid UUID");
-#if _BYTE_ORDER == _BIG_ENDIAN
- *q-- = digit;
-#else
- *q++ = digit;
-#endif
- len++;
- p += 2;
- }
-#if 0
- {
- int i;
-
- printf("uuid = ");
- for (i = 0; i < 16; i++)
- printf("%02x", uuid[i]);
- printf("\n");
- }
-#endif
snprintf(vhdfile, sizeof(vhdfile), "%s.vhd", imi->imi_imagename);
ofd = open(vhdfile, O_WRONLY|O_CREAT|O_TRUNC,
S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH);
@@ -149,7 +107,7 @@ vhd_makeim(struct iminfo *imi)
err(EX_OSERR, NULL);
bl->bl_type = BL_RAWCOPY;
bl->bl_name = "Rawcopy";
- bl->bl_tf.blf_fd = ifd;
+ bl->bl_tf.fd = ifd;
TAILQ_INSERT_TAIL(&blhead, bl, bl_next);
bl = calloc(1, sizeof(*bl));
@@ -157,8 +115,8 @@ vhd_makeim(struct iminfo *imi)
err(EX_OSERR, NULL);
bl->bl_type = BL_RAWDATA;
bl->bl_name = "Hard Disk Footer";
- bl->bl_tr.blr_data = imh;
- bl->bl_tr.blr_len = sizeof(*imh);
+ bl->bl_tr.data = imh;
+ bl->bl_tr.len = sizeof(*imh);
TAILQ_INSERT_TAIL(&blhead, bl, bl_next);
return (dispatch_bl(ofd, &blhead));
Modified: user/hrs/releng/usr.sbin/makevd/vmdk.c
==============================================================================
--- user/hrs/releng/usr.sbin/makevd/vmdk.c Sun Jun 9 15:08:51 2013 (r251576)
+++ user/hrs/releng/usr.sbin/makevd/vmdk.c Sun Jun 9 15:17:38 2013 (r251577)
@@ -66,7 +66,6 @@ vmdk_makeim(struct iminfo *imi)
imh = &SEH;
imagesize = imi->imi_size;
- memset(imh, 0, sizeof(*imh));
memset(desc, 0, sizeof(desc));
if (imi->imi_uuid == NULL)
@@ -124,8 +123,8 @@ vmdk_makeim(struct iminfo *imi)
err(EX_OSERR, NULL);
bl->bl_type = BL_RAWDATA;
bl->bl_name = "Sparse Extent Header";
- bl->bl_tr.blr_data = imh;
- bl->bl_tr.blr_len = sizeof(*imh);
+ bl->bl_tr.data = imh;
+ bl->bl_tr.len = sizeof(*imh);
TAILQ_INSERT_TAIL(&blhead, bl, bl_next);
bl = calloc(1, sizeof(*bl));
@@ -133,8 +132,8 @@ vmdk_makeim(struct iminfo *imi)
err(EX_OSERR, NULL);
bl->bl_type = BL_RAWDATA;
bl->bl_name = "Embedded descriptor";
- bl->bl_tr.blr_data = &desc;
- bl->bl_tr.blr_len = sizeof(desc);
+ bl->bl_tr.data = &desc;
+ bl->bl_tr.len = sizeof(desc);
TAILQ_INSERT_TAIL(&blhead, bl, bl_next);
bl = calloc(1, sizeof(*bl));
@@ -142,7 +141,7 @@ vmdk_makeim(struct iminfo *imi)
err(EX_OSERR, NULL);
bl->bl_type = BL_RAWCOPY;
bl->bl_name = "Rawcopy";
- bl->bl_tf.blf_fd = imi->imi_fd;
+ bl->bl_tf.fd = imi->imi_fd;
TAILQ_INSERT_TAIL(&blhead, bl, bl_next);
return (dispatch_bl(ofd, &blhead));
More information about the svn-src-user
mailing list