Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 2 Jul 2014 14:54:42 +0000 (UTC)
From:      Marcel Moolenaar <marcel@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-10@freebsd.org
Subject:   svn commit: r268161 - in stable/10/usr.bin: . mkimg
Message-ID:  <201407021454.s62Esg64009007@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: marcel
Date: Wed Jul  2 14:54:41 2014
New Revision: 268161
URL: http://svnweb.freebsd.org/changeset/base/268161

Log:
  MFC mkimg(1) -- revisions 268159, 268134, 266556, 266514, 266513,
  	266512, 266511, 266510, 266509, 266176, 265468, 265467,
  	265462, 265170, 263926, 263924, 263923, 263919 and 263918.
  
  Revision 267182 changed mkimg.1 alongside other unrelated manpages.
  The change to mkimg.1 has been applied without registering a merge
  of the revision. This allows a future merge of r267182 to happen.
  
  Relnotes: yes

Added:
  stable/10/usr.bin/mkimg/
     - copied from r263918, head/usr.bin/mkimg/
  stable/10/usr.bin/mkimg/format.c
     - copied unchanged from r266176, head/usr.bin/mkimg/format.c
  stable/10/usr.bin/mkimg/format.h
     - copied unchanged from r266176, head/usr.bin/mkimg/format.h
  stable/10/usr.bin/mkimg/image.c
     - copied, changed from r266176, head/usr.bin/mkimg/image.c
  stable/10/usr.bin/mkimg/image.h
     - copied unchanged from r266176, head/usr.bin/mkimg/image.h
  stable/10/usr.bin/mkimg/raw.c
     - copied unchanged from r266176, head/usr.bin/mkimg/raw.c
  stable/10/usr.bin/mkimg/vmdk.c
     - copied unchanged from r266176, head/usr.bin/mkimg/vmdk.c
Modified:
  stable/10/usr.bin/Makefile
  stable/10/usr.bin/mkimg/Makefile   (contents, props changed)
  stable/10/usr.bin/mkimg/apm.c
  stable/10/usr.bin/mkimg/bsd.c
  stable/10/usr.bin/mkimg/ebr.c
  stable/10/usr.bin/mkimg/gpt.c
  stable/10/usr.bin/mkimg/mbr.c
  stable/10/usr.bin/mkimg/mkimg.1   (contents, props changed)
  stable/10/usr.bin/mkimg/mkimg.c   (contents, props changed)
  stable/10/usr.bin/mkimg/mkimg.h
  stable/10/usr.bin/mkimg/pc98.c
  stable/10/usr.bin/mkimg/scheme.c   (contents, props changed)
  stable/10/usr.bin/mkimg/scheme.h   (contents, props changed)
  stable/10/usr.bin/mkimg/vtoc8.c
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/usr.bin/Makefile
==============================================================================
--- stable/10/usr.bin/Makefile	Wed Jul  2 14:47:48 2014	(r268160)
+++ stable/10/usr.bin/Makefile	Wed Jul  2 14:54:41 2014	(r268161)
@@ -106,6 +106,7 @@ SUBDIR=	alias \
 	mkdep \
 	${_mkesdb} \
 	mkfifo \
+	mkimg \
 	mklocale \
 	mktemp \
 	mkulzma \

Modified: stable/10/usr.bin/mkimg/Makefile
==============================================================================
--- head/usr.bin/mkimg/Makefile	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/Makefile	Wed Jul  2 14:54:41 2014	(r268161)
@@ -1,11 +1,16 @@
 # $FreeBSD$
 
 PROG=	mkimg
-SRCS=	mkimg.c scheme.c
+SRCS=	format.c image.c mkimg.c scheme.c
 MAN=	mkimg.1
 
 CFLAGS+=-DSPARSE_WRITE
 
+# List of formats to support
+SRCS+= \
+	raw.c \
+	vmdk.c
+
 # List of schemes to support
 SRCS+=	\
 	apm.c \

Modified: stable/10/usr.bin/mkimg/apm.c
==============================================================================
--- head/usr.bin/mkimg/apm.c	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/apm.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -35,11 +35,17 @@ __FBSDID("$FreeBSD$");
 #include <string.h>
 #include <unistd.h>
 
+#include "image.h"
 #include "mkimg.h"
 #include "scheme.h"
 
+#ifndef APM_ENT_TYPE_FREEBSD_NANDFS
+#define	APM_ENT_TYPE_FREEBSD_NANDFS	"FreeBSD-nandfs"
+#endif
+
 static struct mkimg_alias apm_aliases[] = {
     {	ALIAS_FREEBSD, ALIAS_PTR2TYPE(APM_ENT_TYPE_FREEBSD) },
+    {	ALIAS_FREEBSD_BOOT, ALIAS_PTR2TYPE(APM_ENT_TYPE_APPLE_BOOT) },
     {	ALIAS_FREEBSD_NANDFS, ALIAS_PTR2TYPE(APM_ENT_TYPE_FREEBSD_NANDFS) },
     {	ALIAS_FREEBSD_SWAP, ALIAS_PTR2TYPE(APM_ENT_TYPE_FREEBSD_SWAP) },
     {	ALIAS_FREEBSD_UFS, ALIAS_PTR2TYPE(APM_ENT_TYPE_FREEBSD_UFS) },
@@ -58,13 +64,12 @@ apm_metadata(u_int where)
 }
 
 static int
-apm_write(int fd __unused, lba_t imgsz __unused, void *bootcode __unused)
+apm_write(lba_t imgsz, void *bootcode __unused)
 {
 	u_char *buf;
 	struct apm_ddr *ddr;
 	struct apm_ent *ent;
 	struct part *part;
-	ssize_t nbytes;
 	int error;
 
 	buf = calloc(nparts + 2, secsz);
@@ -81,8 +86,8 @@ apm_write(int fd __unused, lba_t imgsz _
 	be32enc(&ent->ent_pmblkcnt, nparts + 1);
 	be32enc(&ent->ent_start, 1);
 	be32enc(&ent->ent_size, nparts + 1);
-	strcpy(ent->ent_type, APM_ENT_TYPE_SELF);
-	strcpy(ent->ent_name, "Apple");
+	strncpy(ent->ent_type, APM_ENT_TYPE_SELF, sizeof(ent->ent_type));
+	strncpy(ent->ent_name, "Apple", sizeof(ent->ent_name));
 
 	STAILQ_FOREACH(part, &partlist, link) {
 		ent = (void *)(buf + (part->index + 2) * secsz);
@@ -90,17 +95,14 @@ apm_write(int fd __unused, lba_t imgsz _
 		be32enc(&ent->ent_pmblkcnt, nparts + 1);
 		be32enc(&ent->ent_start, part->block);
 		be32enc(&ent->ent_size, part->size);
-		strcpy(ent->ent_type, ALIAS_TYPE2PTR(part->type));
+		strncpy(ent->ent_type, ALIAS_TYPE2PTR(part->type),
+		    sizeof(ent->ent_type));
 		if (part->label != NULL)
-			strcpy(ent->ent_name, part->label);
+			strncpy(ent->ent_name, part->label,
+			    sizeof(ent->ent_name));
 	}
 
-	error = mkimg_seek(fd, 0);
-	if (error == 0) {
-		nbytes = (nparts + 2) * secsz;
-		if (write(fd, buf, nbytes) != nbytes)
-			error = errno;
-	}
+	error = image_write(0, buf, nparts + 2);
 	free(buf);
 	return (error);
 }

Modified: stable/10/usr.bin/mkimg/bsd.c
==============================================================================
--- head/usr.bin/mkimg/bsd.c	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/bsd.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -35,9 +35,14 @@ __FBSDID("$FreeBSD$");
 #include <string.h>
 #include <unistd.h>
 
+#include "image.h"
 #include "mkimg.h"
 #include "scheme.h"
 
+#ifndef FS_NANDFS
+#define	FS_NANDFS	30
+#endif
+
 static struct mkimg_alias bsd_aliases[] = {
     {	ALIAS_FREEBSD_NANDFS, ALIAS_INT2TYPE(FS_NANDFS) },
     {	ALIAS_FREEBSD_SWAP, ALIAS_INT2TYPE(FS_SWAP) },
@@ -57,7 +62,7 @@ bsd_metadata(u_int where)
 }
 
 static int
-bsd_write(int fd, lba_t imgsz, void *bootcode)
+bsd_write(lba_t imgsz, void *bootcode)
 {
 	u_char *buf, *p;
 	struct disklabel *d;
@@ -75,8 +80,12 @@ bsd_write(int fd, lba_t imgsz, void *boo
 	} else
 		memset(buf, 0, BBSIZE);
 
-	imgsz = ncyls * nheads * nsecs;
-	ftruncate(fd, imgsz * secsz);
+	imgsz = (lba_t)ncyls * nheads * nsecs;
+	error = image_set_size(imgsz);
+	if (error) {
+		free(buf);
+		return (error);
+	}
 
 	d = (void *)(buf + secsz);
 	le32enc(&d->d_magic, DISKMAGIC);
@@ -107,11 +116,7 @@ bsd_write(int fd, lba_t imgsz, void *boo
 		checksum ^= le16dec(p);
 	le16enc(&d->d_checksum, checksum);
 
-	error = mkimg_seek(fd, 0);
-	if (error == 0) {
-		if (write(fd, buf, BBSIZE) != BBSIZE)
-			error = errno;
-	}
+	error = image_write(0, buf, BBSIZE / secsz);
 	free(buf);
 	return (error);
 }

Modified: stable/10/usr.bin/mkimg/ebr.c
==============================================================================
--- head/usr.bin/mkimg/ebr.c	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/ebr.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -35,9 +35,14 @@ __FBSDID("$FreeBSD$");
 #include <string.h>
 #include <unistd.h>
 
+#include "image.h"
 #include "mkimg.h"
 #include "scheme.h"
 
+#ifndef DOSPTYP_FAT32
+#define	DOSPTYP_FAT32	0x0b
+#endif
+
 static struct mkimg_alias ebr_aliases[] = {
     {	ALIAS_FAT32, ALIAS_INT2TYPE(DOSPTYP_FAT32) },
     {	ALIAS_FREEBSD, ALIAS_INT2TYPE(DOSPTYP_386BSD) },
@@ -63,7 +68,7 @@ ebr_chs(u_char *cyl, u_char *hd, u_char 
 }
 
 static int
-ebr_write(int fd, lba_t imgsz __unused, void *bootcode __unused)
+ebr_write(lba_t imgsz __unused, void *bootcode __unused)
 {
 	u_char *ebr;
 	struct dos_partition *dp;
@@ -100,11 +105,7 @@ ebr_write(int fd, lba_t imgsz __unused, 
 			le32enc(&dp->dp_size, next->size + nsecs);
 		}
 
-		error = mkimg_seek(fd, block);
-		if (error == 0) {
-			if (write(fd, ebr, secsz) != (ssize_t)secsz)
-				error = errno;
-		}
+		error = image_write(block, ebr, 1);
 		if (error)
 			break;
 

Copied: stable/10/usr.bin/mkimg/format.c (from r266176, head/usr.bin/mkimg/format.c)
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ stable/10/usr.bin/mkimg/format.c	Wed Jul  2 14:54:41 2014	(r268161, copy of r266176, head/usr.bin/mkimg/format.c)
@@ -0,0 +1,91 @@
+/*-
+ * Copyright (c) 2014 Juniper Networks, Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+
+#include <sys/types.h>
+#include <sys/linker_set.h>
+#include <sys/queue.h>
+#include <sys/stat.h>
+#include <err.h>
+#include <errno.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "image.h"
+#include "format.h"
+#include "mkimg.h"
+
+static struct mkimg_format *format;
+
+int
+format_resize(lba_t end)
+{
+
+	if (format == NULL)
+		return (ENOSYS);
+	return (format->resize(end));
+}
+
+int
+format_select(const char *spec)
+{
+	struct mkimg_format *f, **iter;
+
+	SET_FOREACH(iter, formats) {
+		f = *iter;
+		if (strcasecmp(spec, f->name) == 0) {
+			format = f;
+			return (0);
+		}
+	}
+	return (EINVAL);
+}
+
+struct mkimg_format *
+format_selected(void)
+{
+
+	return (format);
+}
+
+int
+format_write(int fd)
+{
+	lba_t size;
+	int error;
+
+	if (format == NULL)
+		return (ENOSYS);
+	size = image_get_size();
+	error = format->resize(size);
+	if (!error)
+		error = format->write(fd);
+	return (error);
+}

Copied: stable/10/usr.bin/mkimg/format.h (from r266176, head/usr.bin/mkimg/format.h)
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ stable/10/usr.bin/mkimg/format.h	Wed Jul  2 14:54:41 2014	(r268161, copy of r266176, head/usr.bin/mkimg/format.h)
@@ -0,0 +1,49 @@
+/*-
+ * Copyright (c) 2014 Juniper Networks, Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+#ifndef _MKIMG_FORMAT_H_
+#define	_MKIMG_FORMAT_H_
+
+#include <sys/linker_set.h>
+
+struct mkimg_format {
+	const char	*name;
+	const char	*description;
+	int		(*resize)(lba_t);
+	int		(*write)(int);
+};
+
+SET_DECLARE(formats, struct mkimg_format);
+#define	FORMAT_DEFINE(nm)	DATA_SET(formats, nm)
+
+int	format_resize(lba_t);
+int	format_select(const char *);
+struct mkimg_format *format_selected(void);
+int	format_write(int);
+
+#endif /* _MKIMG_FORMAT_H_ */

Modified: stable/10/usr.bin/mkimg/gpt.c
==============================================================================
--- head/usr.bin/mkimg/gpt.c	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/gpt.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -39,9 +39,15 @@ __FBSDID("$FreeBSD$");
 #include <unistd.h>
 #include <uuid.h>
 
+#include "image.h"
 #include "mkimg.h"
 #include "scheme.h"
 
+#ifndef GPT_ENT_TYPE_FREEBSD_NANDFS
+#define	GPT_ENT_TYPE_FREEBSD_NANDFS	\
+    {0x74ba7dd9,0xa689,0x11e1,0xbd,0x04,{0x00,0xe0,0x81,0x28,0x6a,0xcf}}
+#endif
+
 static uuid_t gpt_uuid_efi = GPT_ENT_TYPE_EFI;
 static uuid_t gpt_uuid_freebsd = GPT_ENT_TYPE_FREEBSD;
 static uuid_t gpt_uuid_freebsd_boot = GPT_ENT_TYPE_FREEBSD_BOOT;
@@ -123,6 +129,21 @@ crc32(const void *buf, size_t sz)
 	return (crc ^ ~0U);
 }
 
+static void
+gpt_uuid_enc(void *buf, const uuid_t *uuid)
+{
+	uint8_t *p = buf;
+	int i;
+
+	le32enc(p, uuid->time_low);
+	le16enc(p + 4, uuid->time_mid);
+	le16enc(p + 6, uuid->time_hi_and_version);
+	p[8] = uuid->clock_seq_hi_and_reserved;
+	p[9] = uuid->clock_seq_low;
+	for (i = 0; i < _UUID_NODE_LEN; i++)
+		p[10 + i] = uuid->node[i];
+}
+
 static u_int
 gpt_tblsz(void)
 {
@@ -146,20 +167,7 @@ gpt_metadata(u_int where)
 }
 
 static int
-gpt_filewrite(int fd, lba_t blk, void *buf, ssize_t bufsz)
-{
-	int error;
-
-	error = mkimg_seek(fd, blk);
-	if (error == 0) {
-		if (write(fd, buf, bufsz) != bufsz)
-			error = errno;
-	}
-	return (error);
-}
-
-static int
-gpt_write_pmbr(int fd, lba_t blks, void *bootcode)
+gpt_write_pmbr(lba_t blks, void *bootcode)
 {
 	u_char *pmbr;
 	uint32_t secs;
@@ -183,7 +191,7 @@ gpt_write_pmbr(int fd, lba_t blks, void 
 	le32enc(pmbr + DOSPARTOFF + 8, 1);
 	le32enc(pmbr + DOSPARTOFF + 12, secs);
 	le16enc(pmbr + DOSMAGICOFFSET, DOSMAGIC);
-	error = gpt_filewrite(fd, 0, pmbr, secsz);
+	error = image_write(0, pmbr, 1);
 	free(pmbr);
 	return (error);
 }
@@ -202,9 +210,9 @@ gpt_mktbl(u_int tblsz)
 
 	STAILQ_FOREACH(part, &partlist, link) {
 		ent = tbl + part->index;
-		uuid_enc_le(&ent->ent_type, ALIAS_TYPE2PTR(part->type));
+		gpt_uuid_enc(&ent->ent_type, ALIAS_TYPE2PTR(part->type));
 		uuidgen(&uuid, 1);
-		uuid_enc_le(&ent->ent_uuid, &uuid);
+		gpt_uuid_enc(&ent->ent_uuid, &uuid);
 		le64enc(&ent->ent_lba_start, part->block);
 		le64enc(&ent->ent_lba_end, part->block + part->size - 1);
 		if (part->label != NULL) {
@@ -219,8 +227,7 @@ gpt_mktbl(u_int tblsz)
 }
 
 static int
-gpt_write_hdr(int fd, struct gpt_hdr *hdr, uint64_t self, uint64_t alt,
-    uint64_t tbl)
+gpt_write_hdr(struct gpt_hdr *hdr, uint64_t self, uint64_t alt, uint64_t tbl)
 {
 	uint32_t crc;
 
@@ -230,11 +237,11 @@ gpt_write_hdr(int fd, struct gpt_hdr *hd
 	hdr->hdr_crc_self = 0;
 	crc = crc32(hdr, offsetof(struct gpt_hdr, padding));
 	le64enc(&hdr->hdr_crc_self, crc);
-	return (gpt_filewrite(fd, self, hdr, secsz));
+	return (image_write(self, hdr, 1));
 }
 
 static int
-gpt_write(int fd, lba_t imgsz, void *bootcode)
+gpt_write(lba_t imgsz, void *bootcode)
 {
 	uuid_t uuid;
 	struct gpt_ent *tbl;
@@ -244,7 +251,7 @@ gpt_write(int fd, lba_t imgsz, void *boo
 	int error;
 
 	/* PMBR */
-	error = gpt_write_pmbr(fd, imgsz, bootcode);
+	error = gpt_write_pmbr(imgsz, bootcode);
 	if (error)
 		return (error);
 
@@ -253,10 +260,10 @@ gpt_write(int fd, lba_t imgsz, void *boo
 	tbl = gpt_mktbl(tblsz);
 	if (tbl == NULL)
 		return (errno);
-	error = gpt_filewrite(fd, 2, tbl, tblsz * secsz);
+	error = image_write(2, tbl, tblsz);
 	if (error)
 		goto out;
-	error = gpt_filewrite(fd, imgsz - (tblsz + 1), tbl, tblsz * secsz);
+	error = image_write(imgsz - (tblsz + 1), tbl, tblsz);
 	if (error)
 		goto out;
 
@@ -273,14 +280,14 @@ gpt_write(int fd, lba_t imgsz, void *boo
 	le64enc(&hdr->hdr_lba_start, 2 + tblsz);
 	le64enc(&hdr->hdr_lba_end, imgsz - tblsz - 2);
 	uuidgen(&uuid, 1);
-	uuid_enc_le(&hdr->hdr_uuid, &uuid);
+	gpt_uuid_enc(&hdr->hdr_uuid, &uuid);
 	le32enc(&hdr->hdr_entries, nparts);
 	le32enc(&hdr->hdr_entsz, sizeof(struct gpt_ent));
 	crc = crc32(tbl, nparts * sizeof(struct gpt_ent));
 	le32enc(&hdr->hdr_crc_table, crc);
-	error = gpt_write_hdr(fd, hdr, 1, imgsz - 1, 2);
+	error = gpt_write_hdr(hdr, 1, imgsz - 1, 2);
 	if (!error)
-		error = gpt_write_hdr(fd, hdr, imgsz - 1, 1, imgsz - tblsz - 1);
+		error = gpt_write_hdr(hdr, imgsz - 1, 1, imgsz - tblsz - 1);
 	free(hdr);
 
  out:

Copied and modified: stable/10/usr.bin/mkimg/image.c (from r266176, head/usr.bin/mkimg/image.c)
==============================================================================
--- head/usr.bin/mkimg/image.c	Thu May 15 19:19:57 2014	(r266176, copy source)
+++ stable/10/usr.bin/mkimg/image.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -30,6 +30,9 @@ __FBSDID("$FreeBSD$");
 #include <sys/types.h>
 #include <assert.h>
 #include <errno.h>
+#include <limits.h>
+#include <paths.h>
+#include <stdio.h>
 #include <stdlib.h>
 #include <unistd.h>
 
@@ -38,7 +41,7 @@ __FBSDID("$FreeBSD$");
 
 #define	BUFFER_SIZE	(1024*1024)
 
-static char image_tmpfile[] = "/tmp/mkimg-XXXXXX";
+static char image_tmpfile[PATH_MAX];
 static int image_fd = -1;
 static lba_t image_size;
 
@@ -98,11 +101,11 @@ image_copyout(int fd)
 
 	ofs = lseek(fd, 0L, SEEK_CUR);
 
+	if (lseek(image_fd, 0, SEEK_SET) != 0)
+		return (errno);
 	buffer = malloc(BUFFER_SIZE);
 	if (buffer == NULL)
 		return (errno);
-	if (lseek(image_fd, 0, SEEK_SET) != 0)
-		return (errno);
 	error = 0;
 	while (1) {
 		rdsz = read(image_fd, buffer, BUFFER_SIZE);
@@ -119,8 +122,12 @@ image_copyout(int fd)
 		}
 	}
 	free(buffer);
+	if (error)
+		return (error);
 	ofs = lseek(fd, 0L, SEEK_CUR);
-	ftruncate(fd, ofs);
+	if (ofs == -1)
+		return (errno);
+	error = (ftruncate(fd, ofs) == -1) ? errno : 0;
 	return (error);
 }
 
@@ -157,9 +164,14 @@ image_write(lba_t blk, void *buf, ssize_
 int
 image_init(void)
 {
+	const char *tmpdir;
 
 	if (atexit(cleanup) == -1)
 		return (errno);
+	if ((tmpdir = getenv("TMPDIR")) == NULL || *tmpdir == '\0')
+		tmpdir = _PATH_TMP;
+	snprintf(image_tmpfile, sizeof(image_tmpfile), "%s/mkimg-XXXXXX",
+	    tmpdir);
 	image_fd = mkstemp(image_tmpfile);
 	if (image_fd == -1)
 		return (errno);

Copied: stable/10/usr.bin/mkimg/image.h (from r266176, head/usr.bin/mkimg/image.h)
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ stable/10/usr.bin/mkimg/image.h	Wed Jul  2 14:54:41 2014	(r268161, copy of r266176, head/usr.bin/mkimg/image.h)
@@ -0,0 +1,41 @@
+/*-
+ * Copyright (c) 2014 Juniper Networks, Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+#ifndef _MKIMG_IMAGE_H_
+#define	_MKIMG_IMAGE_H_
+
+typedef int64_t lba_t;
+
+int image_copyin(lba_t blk, int fd, uint64_t *sizep);
+int image_copyout(int fd);
+lba_t image_get_size(void);
+int image_init(void);
+int image_set_size(lba_t blk);
+int image_write(lba_t blk, void *buf, ssize_t len);
+
+#endif /* _MKIMG_IMAGE_H_ */

Modified: stable/10/usr.bin/mkimg/mbr.c
==============================================================================
--- head/usr.bin/mkimg/mbr.c	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/mbr.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -35,9 +35,14 @@ __FBSDID("$FreeBSD$");
 #include <string.h>
 #include <unistd.h>
 
+#include "image.h"
 #include "mkimg.h"
 #include "scheme.h"
 
+#ifndef DOSPTYP_FAT32
+#define	DOSPTYP_FAT32	0x0b
+#endif
+
 static struct mkimg_alias mbr_aliases[] = {
     {	ALIAS_EBR, ALIAS_INT2TYPE(DOSPTYP_EXT) },
     {	ALIAS_FAT32, ALIAS_INT2TYPE(DOSPTYP_FAT32) },
@@ -64,7 +69,7 @@ mbr_chs(u_char *cyl, u_char *hd, u_char 
 }
 
 static int
-mbr_write(int fd, lba_t imgsz __unused, void *bootcode)
+mbr_write(lba_t imgsz __unused, void *bootcode)
 {
 	u_char *mbr;
 	struct dos_partition *dpbase, *dp;
@@ -92,11 +97,7 @@ mbr_write(int fd, lba_t imgsz __unused, 
 		le32enc(&dp->dp_start, part->block);
 		le32enc(&dp->dp_size, part->size);
 	}
-	error = mkimg_seek(fd, 0);
-	if (error == 0) {
-		if (write(fd, mbr, secsz) != (ssize_t)secsz)
-			error = errno;
-	}
+	error = image_write(0, mbr, 1);
 	free(mbr);
 	return (error);
 }

Modified: stable/10/usr.bin/mkimg/mkimg.1
==============================================================================
--- head/usr.bin/mkimg/mkimg.1	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/mkimg.1	Wed Jul  2 14:54:41 2014	(r268161)
@@ -24,7 +24,7 @@
 .\"
 .\" $FreeBSD$
 .\"
-.Dd March 27, 2014
+.Dd July 2, 2014
 .Dt MKIMG 1
 .Os
 .Sh NAME
@@ -37,6 +37,7 @@
 .Op Fl S Ar secsz
 .Op Fl T Ar tracksz
 .Op Fl b Ar bootcode
+.Op Fl f Ar format
 .Op Fl o Ar outfile
 .Op Fl v
 .Fl s Ar scheme
@@ -56,6 +57,10 @@ The disk image is written to
 by default or the file specified with the
 .Ar outfile
 argument.
+The image file is a raw disk image by default, but the format of the
+image file can be specified with the
+.Ar format
+argument.
 .Pp
 The disk image can be made bootable by specifying the scheme-specific boot
 block contents with the
@@ -106,10 +111,16 @@ option increases the level of output tha
 .Nm
 utility prints.
 .Pp
-For a complete list of supported partitioning schemes or for a detailed
-description of how to specify partitions, run the
+For a complete list of supported partitioning schemes or supported output
+format, or for a detailed description of how to specify partitions, run the
 .Nm
 utility without any arguments.
+.Sh ENVIRONMENT
+.Bl -tag -width "TMPDIR" -compact
+.It Ev TMPDIR
+Directory to put temporary files in; default is
+.Pa /tmp .
+.El
 .Sh EXAMPLES
 To create a bootable disk image that is partitioned using the GPT scheme and
 containing a root file system that was previously created using
@@ -121,6 +132,14 @@ utility as follows:
 -p freebsd-ufs:=root-file-system.ufs -p freebsd-swap::1G \
 -o gpt.img
 .Pp
+The command line given above results in a raw image file.
+This is because no output format was given.
+To create a VMDK image for example, add the
+.Fl f Ar vmdk
+argument to the
+.Nm
+utility and name the output file accordingly.
+.Pp
 A nested partitioning scheme is created by running the
 .Nm
 utility twice.
@@ -154,8 +173,8 @@ In the following example the file system
 .Sh HISTORY
 The
 .Nm
-utility appeared in
-.Fx 11.0
+utility first appeared in
+.Fx 10.1 .
 .Sh AUTHORS
 The
 .Nm

Modified: stable/10/usr.bin/mkimg/mkimg.c
==============================================================================
--- head/usr.bin/mkimg/mkimg.c	Sat Mar 29 19:03:10 2014	(r263918)
+++ stable/10/usr.bin/mkimg/mkimg.c	Wed Jul  2 14:54:41 2014	(r268161)
@@ -42,15 +42,11 @@ __FBSDID("$FreeBSD$");
 #include <sysexits.h>
 #include <unistd.h>
 
+#include "image.h"
+#include "format.h"
 #include "mkimg.h"
 #include "scheme.h"
 
-#if !defined(SPARSE_WRITE)
-#define	sparse_write	write
-#endif
-
-#define	BUFFER_SIZE	(1024*1024)
-
 struct partlisthead partlist = STAILQ_HEAD_INITIALIZER(partlist);
 u_int nparts = 0;
 
@@ -62,31 +58,18 @@ u_int nsecs = 1;
 u_int secsz = 512;
 u_int blksz = 0;
 
-static int bcfd = -1;
-static int outfd = 0;
-static int tmpfd = -1;
-
-static char tmpfname[] = "/tmp/mkimg-XXXXXX";
-
-static void
-cleanup(void)
-{
-
-	if (tmpfd != -1)
-		close(tmpfd);
-	unlink(tmpfname);
-}
-
 static void
 usage(const char *why)
 {
-	struct mkimg_scheme *s, **iter;
+	struct mkimg_format *f, **f_iter;
+	struct mkimg_scheme *s, **s_iter;
 
 	warnx("error: %s", why);
 	fprintf(stderr, "\nusage: %s <options>\n", getprogname());
 
 	fprintf(stderr, "    options:\n");
 	fprintf(stderr, "\t-b <file>\t-  file containing boot code\n");
+	fprintf(stderr, "\t-f <format>\n");
 	fprintf(stderr, "\t-o <file>\t-  file to write image into\n");
 	fprintf(stderr, "\t-p <partition>\n");
 	fprintf(stderr, "\t-s <scheme>\n");
@@ -95,13 +78,19 @@ usage(const char *why)
 	fprintf(stderr, "\t-S <num>\t-  logical sector size\n");
 	fprintf(stderr, "\t-T <num>\t-  number of tracks to simulate\n");
 
-	fprintf(stderr, "    schemes:\n");
-	SET_FOREACH(iter, schemes) {
-		s = *iter;
+	fprintf(stderr, "\n    formats:\n");
+	SET_FOREACH(f_iter, formats) {
+		f = *f_iter;
+		fprintf(stderr, "\t%s\t-  %s\n", f->name, f->description);
+	}
+
+	fprintf(stderr, "\n    schemes:\n");
+	SET_FOREACH(s_iter, schemes) {
+		s = *s_iter;
 		fprintf(stderr, "\t%s\t-  %s\n", s->name, s->description);
 	}
 
-	fprintf(stderr, "    partition specification:\n");
+	fprintf(stderr, "\n    partition specification:\n");
 	fprintf(stderr, "\t<t>[/<l>]::<size>\t-  empty partition of given "
 	    "size\n");
 	fprintf(stderr, "\t<t>[/<l>]:=<file>\t-  partition content and size "
@@ -228,14 +217,15 @@ parse_part(const char *spec)
 }
 
 #if defined(SPARSE_WRITE)
-static ssize_t
-sparse_write(int fd, const char *buf, size_t sz)
+ssize_t
+sparse_write(int fd, const void *ptr, size_t sz)
 {
-	const char *p;
+	const char *buf, *p;
 	off_t ofs;
 	size_t len;
 	ssize_t wr, wrsz;
 
+	buf = ptr;
 	wrsz = 0;
 	p = memchr(buf, 0, sz);
 	while (sz > 0) {
@@ -268,53 +258,8 @@ sparse_write(int fd, const char *buf, si
 }
 #endif /* SPARSE_WRITE */
 
-static int
-fdcopy(int src, int dst, uint64_t *count)
-{
-	char *buffer;
-	off_t ofs;
-	ssize_t rdsz, wrsz;
-
-	/* A return value of -1 means that we can't write a sparse file. */
-	ofs = lseek(dst, 0L, SEEK_CUR);
-
-	if (count != NULL)
-		*count = 0;
-
-	buffer = malloc(BUFFER_SIZE);
-	if (buffer == NULL)
-		return (errno);
-	while (1) {
-		rdsz = read(src, buffer, BUFFER_SIZE);
-		if (rdsz <= 0) {
-			free(buffer);
-			return ((rdsz < 0) ? errno : 0);
-		}
-		if (count != NULL)
-			*count += rdsz;
-		wrsz = (ofs == -1) ?
-		    write(dst, buffer, rdsz) :
-		    sparse_write(dst, buffer, rdsz);
-		if (wrsz < 0)
-			break;
-	}
-	free(buffer);
-	return (errno);
-}
-
-int
-mkimg_seek(int fd, lba_t blk)
-{
-	off_t off;
-
-	off = blk * secsz;
-	if (lseek(fd, off, SEEK_SET) != off)
-		return (errno);
-	return (0);
-}
-
 static void
-mkimg(int bfd)
+mkimg(void)
 {
 	FILE *fp;
 	struct part *part;
@@ -322,10 +267,6 @@ mkimg(int bfd)
 	off_t bytesize;
 	int error, fd;
 
-	error = scheme_bootcode(bfd);
-	if (error)
-		errc(EX_DATAERR, error, "boot code");
-
 	/* First check partition information */
 	STAILQ_FOREACH(part, &partlist, link) {
 		error = scheme_check_part(part);
@@ -340,7 +281,6 @@ mkimg(int bfd)
 			fprintf(stderr, "partition %d: starting block %llu "
 			    "... ", part->index + 1, (long long)block);
 		part->block = block;
-		error = mkimg_seek(tmpfd, block);
 		switch (part->kind) {
 		case PART_KIND_SIZE:
 			if (expand_number(part->contents, &bytesize) == -1)
@@ -349,7 +289,7 @@ mkimg(int bfd)
 		case PART_KIND_FILE:
 			fd = open(part->contents, O_RDONLY, 0);
 			if (fd != -1) {
-				error = fdcopy(fd, tmpfd, &bytesize);
+				error = image_copyin(block, fd, &bytesize);
 				close(fd);
 			} else
 				error = errno;
@@ -357,7 +297,8 @@ mkimg(int bfd)
 		case PART_KIND_PIPE:
 			fp = popen(part->contents, "r");
 			if (fp != NULL) {
-				error = fdcopy(fileno(fp), tmpfd, &bytesize);
+				fd = fileno(fp);
+				error = image_copyin(block, fd, &bytesize);
 				pclose(fp);
 			} else
 				error = errno;
@@ -376,15 +317,27 @@ mkimg(int bfd)
 	}
 
 	block = scheme_metadata(SCHEME_META_IMG_END, block);
-	error = (scheme_write(tmpfd, block));
+	error = image_set_size(block);
+	if (!error)
+		error = format_resize(block);
+	if (error)
+		errc(EX_IOERR, error, "image sizing");
+	block = image_get_size();
+	ncyls = block / (nsecs * nheads);
+	error = (scheme_write(block));
+	if (error)
+		errc(EX_IOERR, error, "writing metadata");
 }
 
 int
 main(int argc, char *argv[])
 {
+	int bcfd, outfd;
 	int c, error;
 
-	while ((c = getopt(argc, argv, "b:o:p:s:vH:P:S:T:")) != -1) {
+	bcfd = -1;
+	outfd = 1;	/* Write to stdout by default */
+	while ((c = getopt(argc, argv, "b:f:o:p:s:vH:P:S:T:")) != -1) {
 		switch (c) {
 		case 'b':	/* BOOT CODE */
 			if (bcfd != -1)
@@ -393,8 +346,15 @@ main(int argc, char *argv[])
 			if (bcfd == -1)
 				err(EX_UNAVAILABLE, "%s", optarg);
 			break;
+		case 'f':	/* OUTPUT FORMAT */
+			if (format_selected() != NULL)
+				usage("multiple formats given");
+			error = format_select(optarg);
+			if (error)
+				errc(EX_DATAERR, error, "format");
+			break;
 		case 'o':	/* OUTPUT FILE */
-			if (outfd != 0)
+			if (outfd != 1)
 				usage("multiple output files given");
 			outfd = open(optarg, O_WRONLY | O_CREAT | O_TRUNC,
 			    S_IWUSR | S_IRUSR | S_IRGRP | S_IROTH);
@@ -467,35 +427,43 @@ main(int argc, char *argv[])
 		errx(EX_DATAERR, "%d partitions supported; %d given",
 		    scheme_max_parts(), nparts);
 
-	if (outfd == 0) {
-		if (atexit(cleanup) == -1)
-			err(EX_OSERR, "cannot register cleanup function");
-		outfd = 1;
-		tmpfd = mkstemp(tmpfname);
-		if (tmpfd == -1)
-			err(EX_OSERR, "cannot create temporary file");
-	} else
-		tmpfd = outfd;
+	if (format_selected() == NULL)
+		format_select("raw");
+
+	if (bcfd != -1) {
+		error = scheme_bootcode(bcfd);
+		close(bcfd);
+		if (error)
+			errc(EX_DATAERR, error, "boot code");
+	}
 
 	if (verbose) {
 		fprintf(stderr, "Logical sector size: %u\n", secsz);
 		fprintf(stderr, "Physical block size: %u\n", blksz);
 		fprintf(stderr, "Sectors per track:   %u\n", nsecs);
 		fprintf(stderr, "Number of heads:     %u\n", nheads);
+		fputc('\n', stderr);
+		fprintf(stderr, "Partitioning scheme: %s\n",
+		    scheme_selected()->name);
+		fprintf(stderr, "Output file format:  %s\n",
+		    format_selected()->name);
+		fputc('\n', stderr);
 	}
 
-	mkimg(bcfd);
+	error = image_init();
+	if (error)
+		errc(EX_OSERR, error, "cannot initialize");
 
-	if (verbose)
-		fprintf(stderr, "Number of cylinders: %u\n", ncyls);
+	mkimg();
 
-	if (tmpfd != outfd) {
-		error = mkimg_seek(tmpfd, 0);
-		if (error == 0)
-			error = fdcopy(tmpfd, outfd, NULL);
-		if (error)
-			errc(EX_IOERR, error, "writing to stdout");
+	if (verbose) {
+		fputc('\n', stderr);
+		fprintf(stderr, "Number of cylinders: %u\n", ncyls);
 	}

*** DIFF OUTPUT TRUNCATED AT 1000 LINES ***



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201407021454.s62Esg64009007>