- added support for converting flat to growing mode images
- TODO: rewrite bximage / bxcommit stuff and use hdimage C++ classes to support more commit / conversion types and to get rid of this code duplication.
This commit is contained in:
parent
e2c49cf534
commit
f8075e0ed2
@ -35,6 +35,9 @@ Changes in 2.6.1 (not released yet):
|
|||||||
- Graphics snapshot feature rewritten to support all kinds of graphics modes
|
- Graphics snapshot feature rewritten to support all kinds of graphics modes
|
||||||
- wx: starting a second simulation without closing Bochs now almost possible
|
- wx: starting a second simulation without closing Bochs now almost possible
|
||||||
|
|
||||||
|
- Tools
|
||||||
|
- bxcommit: added support for converting flat to growing mode images
|
||||||
|
|
||||||
-------------------------------------------------------------------------
|
-------------------------------------------------------------------------
|
||||||
Changes in 2.6 (September 2, 2012):
|
Changes in 2.6 (September 2, 2012):
|
||||||
|
|
||||||
|
@ -8602,20 +8602,23 @@ For an example of the usage, refer to <xref linkend="diskimagehowto">.
|
|||||||
This tool can commit redologs into flat images.
|
This tool can commit redologs into flat images.
|
||||||
</para>
|
</para>
|
||||||
<para>
|
<para>
|
||||||
For now, only "undoable" and "growing" redologs to flat image commits are
|
For now, only "undoable" redologs to flat image commits and "growing" to flat
|
||||||
supported. Sparse disk image commits may be added in the future.
|
image conversion (and vice versa) are supported. Commiting / converting other
|
||||||
|
disk image types may be added in the future.
|
||||||
</para>
|
</para>
|
||||||
<para>
|
<para>
|
||||||
This tool is completely interactive if no command line arguments are used.
|
This tool is completely interactive if no command line arguments are used.
|
||||||
Then bxcommit asks for the operation mode, the flat image name, the redolog name,
|
Then bxcommit asks for the operation mode, the flat image name, the redolog name,
|
||||||
and whether to remove to redolog file after the commit is done. It can be switched
|
and whether to remove the source file after the commit or conversion is done.
|
||||||
to a non-interactive mode if all required parameters are given in the command line.
|
It can be switched to a non-interactive mode if all required parameters are
|
||||||
|
given in the command line.
|
||||||
<screen>
|
<screen>
|
||||||
bxcommit [options] [flat filename] [redolog filename]
|
bxcommit [options] [flat filename] [redolog filename]
|
||||||
|
|
||||||
Supported options:
|
Supported options:
|
||||||
-mode=undoable commit undoable redolog to flat file
|
-mode=commit-undoable commit undoable redolog to flat file
|
||||||
-mode=growing create flat disk image from growing disk image
|
-mode=growing-to-flat create flat disk image from growing disk image
|
||||||
|
-mode=flat-to-growing create growing disk image from flat disk image
|
||||||
-d delete redolog file after commit
|
-d delete redolog file after commit
|
||||||
-q quiet mode (don't prompt for user input)
|
-q quiet mode (don't prompt for user input)
|
||||||
--help display this help and exit
|
--help display this help and exit
|
||||||
@ -8630,16 +8633,24 @@ Session example :
|
|||||||
$ ./bxcommit
|
$ ./bxcommit
|
||||||
========================================================================
|
========================================================================
|
||||||
bxcommit
|
bxcommit
|
||||||
Undoable Disk Image Commit Tool for Bochs
|
Growing / Undoable Disk Image Commit Tool for Bochs
|
||||||
========================================================================
|
========================================================================
|
||||||
|
|
||||||
|
1. Commit 'undoable' redolog to 'flat' file
|
||||||
|
2. Create 'flat' disk image from 'growing' disk image
|
||||||
|
3. Create 'growing' disk image from 'flat' disk image
|
||||||
|
|
||||||
|
0. Quit
|
||||||
|
|
||||||
|
Please choose one [0] 1
|
||||||
|
|
||||||
What is the flat image name?
|
What is the flat image name?
|
||||||
[c.img] myfile.img
|
[c.img] myfile.img
|
||||||
|
|
||||||
What is the redolog name?
|
What is the redolog name?
|
||||||
[myfile.img.redolog] toapply.redolog
|
[myfile.img.redolog] toapply.redolog
|
||||||
|
|
||||||
Shall I remove the redolog afterwards?
|
Should the redolog been removed afterwards?
|
||||||
[yes]
|
[yes]
|
||||||
</screen>
|
</screen>
|
||||||
</para>
|
</para>
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
.\"Document Author: Christophe Bothamy - cbothamy@free.fr"
|
.\"Document Author: Christophe Bothamy - cbothamy@free.fr"
|
||||||
.TH bxcommit 1 "28 Oct 2012" "bxcommit" "The Bochs Project"
|
.TH bxcommit 1 "7 Apr 2013" "bxcommit" "The Bochs Project"
|
||||||
.\"SKIP_SECTION"
|
.\"SKIP_SECTION"
|
||||||
.SH NAME
|
.SH NAME
|
||||||
bxcommit \- Interactive Tool to Commit Redologs into flat Disk Images for Bochs
|
bxcommit \- Interactive Tool to Commit Redologs into flat Disk Images for Bochs
|
||||||
@ -24,12 +24,15 @@ When you run bxcommit without one of the following options,
|
|||||||
it will appear in interactive mode and ask for all
|
it will appear in interactive mode and ask for all
|
||||||
required parameters to do the commit.
|
required parameters to do the commit.
|
||||||
.TP
|
.TP
|
||||||
.BI \-mode=undoable
|
.BI \-mode=commit-undoable
|
||||||
commit undoable redolog to flat file
|
commit undoable redolog to flat file
|
||||||
.TP
|
.TP
|
||||||
.BI \-mode=growing
|
.BI \-mode=growing-to-flat
|
||||||
create flat disk image from growing disk image
|
create flat disk image from growing disk image
|
||||||
.TP
|
.TP
|
||||||
|
.BI \-mode=flat-to-growing
|
||||||
|
create growing disk image from flat disk image
|
||||||
|
.TP
|
||||||
.BI \-d
|
.BI \-d
|
||||||
delete redolog file after commit
|
delete redolog file after commit
|
||||||
.TP
|
.TP
|
||||||
|
@ -1,11 +1,26 @@
|
|||||||
/*
|
/*
|
||||||
* misc/bximage.c
|
|
||||||
* $Id$
|
* $Id$
|
||||||
*
|
*
|
||||||
* Commits a redolog file in a flat file for bochs images.
|
* Copyright (C) 2003-2013 The Bochs Project
|
||||||
*
|
*
|
||||||
|
* This library is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU Lesser General Public
|
||||||
|
* License as published by the Free Software Foundation; either
|
||||||
|
* version 2 of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This library is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* Lesser General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU Lesser General Public
|
||||||
|
* License along with this library; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/* Commits a redolog file in a flat file for bochs images. */
|
||||||
|
/* Converts growing mode image to flat and vice versa */
|
||||||
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
@ -51,12 +66,30 @@ int snprintf(char *s, size_t maxlen, const char *format, ...)
|
|||||||
|
|
||||||
#define BXCOMMIT_MODE_COMMIT_UNDOABLE 1
|
#define BXCOMMIT_MODE_COMMIT_UNDOABLE 1
|
||||||
#define BXCOMMIT_MODE_GROWING_TO_FLAT 2
|
#define BXCOMMIT_MODE_GROWING_TO_FLAT 2
|
||||||
|
#define BXCOMMIT_MODE_FLAT_TO_GROWING 3
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
int fd;
|
||||||
|
redolog_header_t header;
|
||||||
|
Bit32u *catalog;
|
||||||
|
Bit8u *bitmap;
|
||||||
|
bx_bool bitmap_update;
|
||||||
|
Bit32u extent_index;
|
||||||
|
Bit32u extent_offset;
|
||||||
|
Bit32u extent_next;
|
||||||
|
|
||||||
|
Bit32u bitmap_blocks;
|
||||||
|
Bit32u extent_blocks;
|
||||||
|
|
||||||
|
Bit64s imagepos;
|
||||||
|
} redolog_t;
|
||||||
|
|
||||||
int bxcommit_mode;
|
int bxcommit_mode;
|
||||||
int bx_remove;
|
int bx_remove;
|
||||||
int bx_interactive;
|
int bx_interactive;
|
||||||
char bx_flat_filename[256];
|
char bx_flat_filename[256];
|
||||||
char bx_redolog_name[256];
|
char bx_redolog_name[256];
|
||||||
|
Bit8u null_sector[512];
|
||||||
|
|
||||||
char *EOF_ERR = "ERROR: End of input";
|
char *EOF_ERR = "ERROR: End of input";
|
||||||
char *svnid = "$Id$";
|
char *svnid = "$Id$";
|
||||||
@ -65,6 +98,7 @@ const char *main_menu_prompt =
|
|||||||
"\n"
|
"\n"
|
||||||
"1. Commit 'undoable' redolog to 'flat' file\n"
|
"1. Commit 'undoable' redolog to 'flat' file\n"
|
||||||
"2. Create 'flat' disk image from 'growing' disk image\n"
|
"2. Create 'flat' disk image from 'growing' disk image\n"
|
||||||
|
"3. Create 'growing' disk image from 'flat' disk image\n"
|
||||||
"\n"
|
"\n"
|
||||||
"0. Quit\n"
|
"0. Quit\n"
|
||||||
"\n"
|
"\n"
|
||||||
@ -227,6 +261,264 @@ int ask_string(const char *prompt, char *the_default, char *out)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* helper functions */
|
||||||
|
int bx_read_image(int fd, Bit64s offset, void *buf, int count)
|
||||||
|
{
|
||||||
|
if (lseek(fd, offset, SEEK_SET) == -1) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return read(fd, buf, count);
|
||||||
|
}
|
||||||
|
|
||||||
|
int bx_write_image(int fd, Bit64s offset, void *buf, int count)
|
||||||
|
{
|
||||||
|
if (lseek(fd, offset, SEEK_SET) == -1) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return write(fd, buf, count);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Create a suited redolog header */
|
||||||
|
void redolog_make_header(redolog_header_t *header, const char* type, Bit64u size)
|
||||||
|
{
|
||||||
|
Bit32u entries, extent_size, bitmap_size;
|
||||||
|
Bit64u maxsize;
|
||||||
|
|
||||||
|
// Set standard header values
|
||||||
|
strcpy((char*)header->standard.magic, STANDARD_HEADER_MAGIC);
|
||||||
|
strcpy((char*)header->standard.type, REDOLOG_TYPE);
|
||||||
|
strcpy((char*)header->standard.subtype, type);
|
||||||
|
header->standard.version = htod32(STANDARD_HEADER_VERSION);
|
||||||
|
header->standard.header = htod32(STANDARD_HEADER_SIZE);
|
||||||
|
|
||||||
|
entries = 512;
|
||||||
|
bitmap_size = 1;
|
||||||
|
|
||||||
|
// Compute #entries and extent size values
|
||||||
|
do {
|
||||||
|
static Bit32u flip=0;
|
||||||
|
|
||||||
|
extent_size = 8 * bitmap_size * 512;
|
||||||
|
|
||||||
|
header->specific.catalog = htod32(entries);
|
||||||
|
header->specific.bitmap = htod32(bitmap_size);
|
||||||
|
header->specific.extent = htod32(extent_size);
|
||||||
|
|
||||||
|
maxsize = (Bit64u)entries * (Bit64u)extent_size;
|
||||||
|
|
||||||
|
flip++;
|
||||||
|
|
||||||
|
if(flip&0x01) bitmap_size *= 2;
|
||||||
|
else entries *= 2;
|
||||||
|
} while (maxsize < size);
|
||||||
|
|
||||||
|
header->specific.disk = htod64(size);
|
||||||
|
}
|
||||||
|
|
||||||
|
int flat_image_read_sector(int fd, Bit8u *buffer, Bit64u offset)
|
||||||
|
{
|
||||||
|
if (bx_read_image(fd, offset, buffer, 512) < 0)
|
||||||
|
return 0;
|
||||||
|
if (memcmp(buffer, null_sector, 512) == 0)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
Bit64s redolog_lseek(redolog_t *redolog, Bit64s offset, int whence)
|
||||||
|
{
|
||||||
|
char msg[80];
|
||||||
|
Bit32u old_extent_index;
|
||||||
|
|
||||||
|
if (whence == SEEK_SET) {
|
||||||
|
redolog->imagepos = offset;
|
||||||
|
} else if (whence == SEEK_CUR) {
|
||||||
|
redolog->imagepos += offset;
|
||||||
|
} else {
|
||||||
|
fatal("redolog: lseek() mode not supported yet");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
if (redolog->imagepos > (Bit64s)dtoh64(redolog->header.specific.disk)) {
|
||||||
|
sprintf(msg, "redolog : lseek() to byte %ld failed", (long)offset);
|
||||||
|
fatal(msg);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
old_extent_index = redolog->extent_index;
|
||||||
|
redolog->extent_index = (Bit32u)(redolog->imagepos / dtoh32(redolog->header.specific.extent));
|
||||||
|
if (redolog->extent_index != old_extent_index) {
|
||||||
|
redolog->bitmap_update = 1;
|
||||||
|
}
|
||||||
|
redolog->extent_offset = (Bit32u)((redolog->imagepos % dtoh32(redolog->header.specific.extent)) / 512);
|
||||||
|
|
||||||
|
return redolog->imagepos;
|
||||||
|
}
|
||||||
|
|
||||||
|
int redolog_write_sector(redolog_t *redolog, Bit8u *buf, Bit64u offset)
|
||||||
|
{
|
||||||
|
Bit32u i;
|
||||||
|
Bit64s block_offset, bitmap_offset, catalog_offset;
|
||||||
|
ssize_t written;
|
||||||
|
bx_bool update_catalog = 0;
|
||||||
|
char *zerobuffer;
|
||||||
|
char msg[80];
|
||||||
|
|
||||||
|
redolog_lseek(redolog, offset, SEEK_SET);
|
||||||
|
|
||||||
|
if (dtoh32(redolog->catalog[redolog->extent_index]) == REDOLOG_PAGE_NOT_ALLOCATED) {
|
||||||
|
if (redolog->extent_next >= dtoh32(redolog->header.specific.catalog)) {
|
||||||
|
fatal("redolog : can't allocate new extent... catalog is full");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Extent not allocated, allocate new
|
||||||
|
redolog->catalog[redolog->extent_index] = htod32(redolog->extent_next);
|
||||||
|
|
||||||
|
redolog->extent_next += 1;
|
||||||
|
|
||||||
|
zerobuffer = (char*)malloc(512);
|
||||||
|
memset(zerobuffer, 0, 512);
|
||||||
|
|
||||||
|
// Write bitmap
|
||||||
|
bitmap_offset = (Bit64s)STANDARD_HEADER_SIZE + (dtoh32(redolog->header.specific.catalog) * sizeof(Bit32u));
|
||||||
|
bitmap_offset += (Bit64s)512 * dtoh32(redolog->catalog[redolog->extent_index]) * (redolog->extent_blocks + redolog->bitmap_blocks);
|
||||||
|
lseek(redolog->fd, (off_t)bitmap_offset, SEEK_SET);
|
||||||
|
for (i=0; i<redolog->bitmap_blocks; i++) {
|
||||||
|
write(redolog->fd, zerobuffer, 512);
|
||||||
|
}
|
||||||
|
// Write extent
|
||||||
|
for (i=0; i<redolog->extent_blocks; i++) {
|
||||||
|
write(redolog->fd, zerobuffer, 512);
|
||||||
|
}
|
||||||
|
|
||||||
|
free(zerobuffer);
|
||||||
|
|
||||||
|
update_catalog = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
bitmap_offset = (Bit64s)STANDARD_HEADER_SIZE + (dtoh32(redolog->header.specific.catalog) * sizeof(Bit32u));
|
||||||
|
bitmap_offset += (Bit64s)512 * dtoh32(redolog->catalog[redolog->extent_index]) * (redolog->extent_blocks + redolog->bitmap_blocks);
|
||||||
|
block_offset = bitmap_offset + ((Bit64s)512 * (redolog->bitmap_blocks + redolog->extent_offset));
|
||||||
|
|
||||||
|
// Write block
|
||||||
|
written = bx_write_image(redolog->fd, (off_t)block_offset, (void*)buf, 512);
|
||||||
|
|
||||||
|
// Write bitmap
|
||||||
|
if (redolog->bitmap_update) {
|
||||||
|
if (bx_read_image(redolog->fd, (off_t)bitmap_offset, redolog->bitmap, dtoh32(redolog->header.specific.bitmap)) != (ssize_t)dtoh32(redolog->header.specific.bitmap)) {
|
||||||
|
sprintf(msg, "redolog : failed to read bitmap for extent %d", redolog->extent_index);
|
||||||
|
fatal(msg);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
redolog->bitmap_update = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If block does not belong to extent yet
|
||||||
|
if (((redolog->bitmap[redolog->extent_offset/8] >> (redolog->extent_offset%8)) & 0x01) == 0x00) {
|
||||||
|
redolog->bitmap[redolog->extent_offset/8] |= 1 << (redolog->extent_offset%8);
|
||||||
|
bx_write_image(redolog->fd, (off_t)bitmap_offset, redolog->bitmap, dtoh32(redolog->header.specific.bitmap));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write catalog
|
||||||
|
if (update_catalog) {
|
||||||
|
// FIXME if mmap
|
||||||
|
catalog_offset = (Bit64s)STANDARD_HEADER_SIZE + (redolog->extent_index * sizeof(Bit32u));
|
||||||
|
|
||||||
|
bx_write_image(redolog->fd, (off_t)catalog_offset, &redolog->catalog[redolog->extent_index], sizeof(Bit32u));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (written >= 0) redolog_lseek(redolog, 512, SEEK_CUR);
|
||||||
|
|
||||||
|
return written;
|
||||||
|
}
|
||||||
|
|
||||||
|
int convert_flat_image()
|
||||||
|
{
|
||||||
|
int flatfd, redologfd;
|
||||||
|
Bit64u disk_size, offset;
|
||||||
|
redolog_t redolog;
|
||||||
|
Bit32u i;
|
||||||
|
struct stat stat_buf;
|
||||||
|
Bit8u buffer[512];
|
||||||
|
|
||||||
|
if (bxcommit_mode == BXCOMMIT_MODE_FLAT_TO_GROWING) {
|
||||||
|
// check if flat file exists
|
||||||
|
flatfd = open(bx_flat_filename, O_RDONLY
|
||||||
|
#ifdef O_BINARY
|
||||||
|
| O_BINARY
|
||||||
|
#endif
|
||||||
|
);
|
||||||
|
if (flatfd < 0) {
|
||||||
|
fatal("ERROR: flat file not found or not readable");
|
||||||
|
}
|
||||||
|
if (fstat(flatfd, &stat_buf)) {
|
||||||
|
fatal("fstat() returns error!");
|
||||||
|
}
|
||||||
|
disk_size = (Bit64u)stat_buf.st_size;
|
||||||
|
memset(null_sector, 0, 512);
|
||||||
|
|
||||||
|
redologfd = open(bx_redolog_name, O_RDONLY
|
||||||
|
#ifdef O_BINARY
|
||||||
|
| O_BINARY
|
||||||
|
#endif
|
||||||
|
);
|
||||||
|
if (redologfd >= 0) {
|
||||||
|
close(flatfd);
|
||||||
|
close(redologfd);
|
||||||
|
fatal("ERROR: growing file already exists");
|
||||||
|
}
|
||||||
|
fprintf(stderr, "\nCreating growing image file: [");
|
||||||
|
memset(&redolog, 0, sizeof(redolog_t));
|
||||||
|
redolog.fd = open(bx_redolog_name, O_RDWR | O_CREAT
|
||||||
|
#ifdef O_BINARY
|
||||||
|
| O_BINARY
|
||||||
|
#endif
|
||||||
|
, S_IWUSR | S_IRUSR | S_IWGRP | S_IRGRP
|
||||||
|
);
|
||||||
|
if (redolog.fd < 0) {
|
||||||
|
close(flatfd);
|
||||||
|
fatal("ERROR: redolog file is not writable");
|
||||||
|
}
|
||||||
|
redolog_make_header(&redolog.header, REDOLOG_SUBTYPE_GROWING, disk_size);
|
||||||
|
if (write(redolog.fd, &redolog.header, sizeof(redolog.header)) < 0) {
|
||||||
|
fatal("ERROR: The disk image is not complete - could not write header!");
|
||||||
|
} else {
|
||||||
|
lseek(redolog.fd, sizeof(redolog.header), SEEK_SET);
|
||||||
|
}
|
||||||
|
redolog.catalog = (Bit32u*)malloc(dtoh32(redolog.header.specific.catalog) * sizeof(Bit32u));
|
||||||
|
for (i=0; i<dtoh32(redolog.header.specific.catalog); i++) {
|
||||||
|
redolog.catalog[i] = htod32(REDOLOG_PAGE_NOT_ALLOCATED);
|
||||||
|
}
|
||||||
|
if (bx_write_image(redolog.fd, dtoh32(redolog.header.standard.header), redolog.catalog,
|
||||||
|
dtoh32(redolog.header.specific.catalog) * sizeof(Bit32u)) < 0) {
|
||||||
|
close(redolog.fd);
|
||||||
|
fatal("ERROR: The disk image is not complete - could not write catalog!");
|
||||||
|
}
|
||||||
|
redolog.bitmap = (Bit8u *)malloc(dtoh32(redolog.header.specific.bitmap));
|
||||||
|
redolog.bitmap_blocks = 1 + (dtoh32(redolog.header.specific.bitmap) - 1) / 512;
|
||||||
|
redolog.extent_blocks = 1 + (dtoh32(redolog.header.specific.extent) - 1) / 512;
|
||||||
|
redolog.bitmap_update = 1;
|
||||||
|
|
||||||
|
offset = 0;
|
||||||
|
while (offset < disk_size) {
|
||||||
|
if (flat_image_read_sector(flatfd, buffer, offset) > 0) {
|
||||||
|
if (redolog_write_sector(&redolog, buffer, offset) <= 0)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
offset += 512;
|
||||||
|
if (((offset >> 9) % (disk_size >> 15)) == 0) fprintf(stderr, ".");
|
||||||
|
}
|
||||||
|
fprintf(stderr, "]\n");
|
||||||
|
} else {
|
||||||
|
fatal("ERROR: unknown / unsupported mode");
|
||||||
|
}
|
||||||
|
|
||||||
|
close(flatfd);
|
||||||
|
close(redolog.fd);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/* produce the image file */
|
/* produce the image file */
|
||||||
int commit_redolog()
|
int commit_redolog()
|
||||||
{
|
{
|
||||||
@ -400,11 +692,12 @@ void print_usage()
|
|||||||
fprintf(stderr,
|
fprintf(stderr,
|
||||||
"Usage: bxcommit [options] [flat filename] [redolog filename]\n\n"
|
"Usage: bxcommit [options] [flat filename] [redolog filename]\n\n"
|
||||||
"Supported options:\n"
|
"Supported options:\n"
|
||||||
" -mode=undoable commit undoable redolog to flat file\n"
|
" -mode=commit-undoable commit undoable redolog to flat file\n"
|
||||||
" -mode=growing create flat disk image from growing disk image\n"
|
" -mode=growing-to-flat create flat disk image from growing disk image\n"
|
||||||
" -d delete redolog file after commit\n"
|
" -mode=flat-to-growing create growing disk image from flat disk image\n"
|
||||||
" -q quiet mode (don't prompt for user input)\n"
|
" -d delete source file after commit\n"
|
||||||
" --help display this help and exit\n\n");
|
" -q quiet mode (don't prompt for user input)\n"
|
||||||
|
" --help display this help and exit\n\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
int parse_cmdline(int argc, char *argv[])
|
int parse_cmdline(int argc, char *argv[])
|
||||||
@ -425,10 +718,12 @@ int parse_cmdline(int argc, char *argv[])
|
|||||||
ret = 0;
|
ret = 0;
|
||||||
}
|
}
|
||||||
else if (!strncmp("-mode=", argv[arg], 6)) {
|
else if (!strncmp("-mode=", argv[arg], 6)) {
|
||||||
if (!strcmp(&argv[arg][6], "undoable")) {
|
if (!strcmp(&argv[arg][6], "commit-undoable")) {
|
||||||
bxcommit_mode = BXCOMMIT_MODE_COMMIT_UNDOABLE;
|
bxcommit_mode = BXCOMMIT_MODE_COMMIT_UNDOABLE;
|
||||||
} else if (!strcmp(&argv[arg][6], "growing")) {
|
} else if (!strcmp(&argv[arg][6], "growing-to-flat")) {
|
||||||
bxcommit_mode = BXCOMMIT_MODE_GROWING_TO_FLAT;
|
bxcommit_mode = BXCOMMIT_MODE_GROWING_TO_FLAT;
|
||||||
|
} else if (!strcmp(&argv[arg][6], "flat-to-growing")) {
|
||||||
|
bxcommit_mode = BXCOMMIT_MODE_FLAT_TO_GROWING;
|
||||||
} else {
|
} else {
|
||||||
printf("Unknown bxcommit mode '%s'\n\n", &argv[arg][6]);
|
printf("Unknown bxcommit mode '%s'\n\n", &argv[arg][6]);
|
||||||
}
|
}
|
||||||
@ -471,7 +766,7 @@ int CDECL main(int argc, char *argv[])
|
|||||||
print_banner();
|
print_banner();
|
||||||
|
|
||||||
if (bx_interactive) {
|
if (bx_interactive) {
|
||||||
if (ask_int(main_menu_prompt, 0, 2, bxcommit_mode, &bxcommit_mode) < 0)
|
if (ask_int(main_menu_prompt, 0, 3, bxcommit_mode, &bxcommit_mode) < 0)
|
||||||
fatal(EOF_ERR);
|
fatal(EOF_ERR);
|
||||||
|
|
||||||
switch (bxcommit_mode) {
|
switch (bxcommit_mode) {
|
||||||
@ -510,14 +805,36 @@ int CDECL main(int argc, char *argv[])
|
|||||||
if (ask_yn("\nShould the 'growing' image been removed afterwards?\n", 0, &bx_remove) < 0)
|
if (ask_yn("\nShould the 'growing' image been removed afterwards?\n", 0, &bx_remove) < 0)
|
||||||
fatal(EOF_ERR);
|
fatal(EOF_ERR);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case BXCOMMIT_MODE_FLAT_TO_GROWING:
|
||||||
|
if (!strlen(bx_flat_filename)) {
|
||||||
|
strcpy(bx_flat_filename, "flat.img");
|
||||||
|
}
|
||||||
|
if (ask_string("\nWhat is the name of the 'flat' image?\n", bx_flat_filename, bx_flat_filename) < 0)
|
||||||
|
fatal(EOF_ERR);
|
||||||
|
if (!strlen(bx_redolog_name)) {
|
||||||
|
strcpy(bx_redolog_name, "c.img");
|
||||||
|
}
|
||||||
|
if (ask_string("\nWhat should be the 'growing' image name?\n", bx_redolog_name, bx_redolog_name) < 0)
|
||||||
|
fatal(EOF_ERR);
|
||||||
|
if (ask_yn("\nShould the 'flat' image been removed afterwards?\n", 0, &bx_remove) < 0)
|
||||||
|
fatal(EOF_ERR);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
commit_redolog();
|
if (bxcommit_mode != BXCOMMIT_MODE_FLAT_TO_GROWING) {
|
||||||
|
commit_redolog();
|
||||||
if (bx_remove) {
|
if (bx_remove) {
|
||||||
if (unlink(bx_redolog_name) != 0)
|
if (unlink(bx_redolog_name) != 0)
|
||||||
fatal("ERROR: while removing the redolog !\n");
|
fatal("ERROR: while removing the redolog !\n");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
convert_flat_image();
|
||||||
|
if (bx_remove) {
|
||||||
|
if (unlink(bx_flat_filename) != 0)
|
||||||
|
fatal("ERROR: while removing the flat file !\n");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// make picky compilers (c++, gcc) happy,
|
// make picky compilers (c++, gcc) happy,
|
||||||
|
Loading…
Reference in New Issue
Block a user