mirror of
https://gitlab.com/cryptsetup/cryptsetup.git
synced 2025-12-05 16:00:05 +01:00
Add --device-size option for reencryption tool.
This commit is contained in:
@@ -1,3 +1,6 @@
|
|||||||
|
2012-06-25 Milan Broz <gmazyland@gmail.com>
|
||||||
|
* Add --device-size option for reencryption tool.
|
||||||
|
|
||||||
2012-06-20 Milan Broz <gmazyland@gmail.com>
|
2012-06-20 Milan Broz <gmazyland@gmail.com>
|
||||||
* Version 1.5.0-rc2.
|
* Version 1.5.0-rc2.
|
||||||
|
|
||||||
|
|||||||
@@ -23,6 +23,8 @@
|
|||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
#include <ctype.h>
|
||||||
|
#include <limits.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
@@ -423,3 +425,65 @@ ssize_t crypt_hex_to_bytes(const char *hex, char **result, int safe_alloc)
|
|||||||
*result = bytes;
|
*result = bytes;
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Device size string parsing, suffixes:
|
||||||
|
* s|S - 512 bytes sectors
|
||||||
|
* k |K |m |M |g |G |t |T - 1024 base
|
||||||
|
* kiB|KiB|miB|MiB|giB|GiB|tiB|TiB - 1024 base
|
||||||
|
* kb |KB |mM |MB |gB |GB |tB |TB - 1000 base
|
||||||
|
*/
|
||||||
|
int crypt_string_to_size(struct crypt_device *cd, const char *s, uint64_t *size)
|
||||||
|
{
|
||||||
|
char *endp = NULL;
|
||||||
|
size_t len;
|
||||||
|
uint64_t mult_base, mult, tmp;
|
||||||
|
|
||||||
|
*size = strtoull(s, &endp, 10);
|
||||||
|
if (!isdigit(s[0]) ||
|
||||||
|
(errno == ERANGE && *size == ULLONG_MAX) ||
|
||||||
|
(errno != 0 && *size == 0))
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
if (!endp)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
len = strlen(endp);
|
||||||
|
/* Allow "B" and "iB" suffixes */
|
||||||
|
if (len > 3 ||
|
||||||
|
(len == 3 && (endp[1] != 'i' || endp[2] != 'B')) ||
|
||||||
|
(len == 2 && endp[1] != 'B'))
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
if (len == 1 || len == 3)
|
||||||
|
mult_base = 1024;
|
||||||
|
else
|
||||||
|
mult_base = 1000;
|
||||||
|
|
||||||
|
mult = 1;
|
||||||
|
switch (endp[0]) {
|
||||||
|
case 's':
|
||||||
|
case 'S': mult = 512;
|
||||||
|
break;
|
||||||
|
case 't':
|
||||||
|
case 'T': mult *= mult_base;
|
||||||
|
case 'g':
|
||||||
|
case 'G': mult *= mult_base;
|
||||||
|
case 'm':
|
||||||
|
case 'M': mult *= mult_base;
|
||||||
|
case 'k':
|
||||||
|
case 'K': mult *= mult_base;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
tmp = *size * mult;
|
||||||
|
if ((tmp / *size) != mult) {
|
||||||
|
log_dbg("Device size overflow.");
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
*size = tmp;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|||||||
@@ -44,5 +44,6 @@ void crypt_safe_free(void *data);
|
|||||||
void *crypt_safe_realloc(void *data, size_t size);
|
void *crypt_safe_realloc(void *data, size_t size);
|
||||||
|
|
||||||
ssize_t crypt_hex_to_bytes(const char *hex, char **result, int safe_alloc);
|
ssize_t crypt_hex_to_bytes(const char *hex, char **result, int safe_alloc);
|
||||||
|
int crypt_string_to_size(struct crypt_device *cd, const char *s, uint64_t *size);
|
||||||
|
|
||||||
#endif /* _UTILS_CRYPT_H */
|
#endif /* _UTILS_CRYPT_H */
|
||||||
|
|||||||
@@ -122,6 +122,23 @@ partition (so last sectors contains no data).
|
|||||||
WARNING: This is destructive operation and cannot be reverted.
|
WARNING: This is destructive operation and cannot be reverted.
|
||||||
Use with extreme care - shrinked filesystems are usually unrecoverable.
|
Use with extreme care - shrinked filesystems are usually unrecoverable.
|
||||||
|
|
||||||
|
You cannot shrink device more than by 64 MiB (131072 sectors).
|
||||||
|
.TP
|
||||||
|
.B "\-\-device-size \fIsize[units]\fR"
|
||||||
|
Instead of real device size, use specified value.
|
||||||
|
|
||||||
|
It means that only specified area (from the start of the device
|
||||||
|
to the specified size) will be reencrypted.
|
||||||
|
|
||||||
|
WARNING: This is destructive operation.
|
||||||
|
|
||||||
|
If no unit suffix is specified, the size is in bytes.
|
||||||
|
|
||||||
|
Unit suffix can be S for 512 byte sectors, K/M/G/T (or KiB,MiB,GiB,TiB)
|
||||||
|
for units with 1024 base or KB/MB/GB/TB for 1000 base (SI scale).
|
||||||
|
|
||||||
|
WARNING: This is destructive operation.
|
||||||
|
|
||||||
You cannot shrink device more than by 64 MiB (131072 sectors).
|
You cannot shrink device more than by 64 MiB (131072 sectors).
|
||||||
.TP
|
.TP
|
||||||
.B "\-\-new, N"
|
.B "\-\-new, N"
|
||||||
|
|||||||
@@ -67,6 +67,9 @@ static int opt_key_slot = CRYPT_ANY_SLOT;
|
|||||||
static int opt_key_size = 0;
|
static int opt_key_size = 0;
|
||||||
static int opt_new = 0;
|
static int opt_new = 0;
|
||||||
|
|
||||||
|
static const char *opt_device_size_str = NULL;
|
||||||
|
static uint64_t opt_device_size = 0;
|
||||||
|
|
||||||
static const char **action_argv;
|
static const char **action_argv;
|
||||||
|
|
||||||
static volatile int quit = 0;
|
static volatile int quit = 0;
|
||||||
@@ -75,7 +78,8 @@ static volatile int quit = 0;
|
|||||||
struct reenc_ctx {
|
struct reenc_ctx {
|
||||||
char *device;
|
char *device;
|
||||||
char *device_uuid;
|
char *device_uuid;
|
||||||
uint64_t device_size;
|
uint64_t device_size; /* overrided by parameter */
|
||||||
|
uint64_t device_size_real;
|
||||||
uint64_t device_offset;
|
uint64_t device_offset;
|
||||||
uint64_t device_shift;
|
uint64_t device_shift;
|
||||||
|
|
||||||
@@ -750,6 +754,10 @@ static int copy_data_forward(struct reenc_ctx *rc, int fd_old, int fd_new,
|
|||||||
return -EIO;
|
return -EIO;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* If device_size is forced, never write more than limit */
|
||||||
|
if ((s1 + rc->device_offset) > rc->device_size)
|
||||||
|
s1 = rc->device_size - rc->device_offset;
|
||||||
|
|
||||||
s2 = write(fd_new, buf, s1);
|
s2 = write(fd_new, buf, s1);
|
||||||
if (s2 < 0) {
|
if (s2 < 0) {
|
||||||
log_dbg("Write error, expecting %d, got %d.",
|
log_dbg("Write error, expecting %d, got %d.",
|
||||||
@@ -861,11 +869,13 @@ static int copy_data(struct reenc_ctx *rc)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Check size */
|
/* Check size */
|
||||||
if (ioctl(fd_new, BLKGETSIZE64, &rc->device_size) < 0) {
|
if (ioctl(fd_new, BLKGETSIZE64, &rc->device_size_real) < 0) {
|
||||||
log_err(_("Cannot get device size.\n"));
|
log_err(_("Cannot get device size.\n"));
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rc->device_size = opt_device_size ?: rc->device_size_real;
|
||||||
|
|
||||||
if (posix_memalign((void *)&buf, alignment(fd_new), block_size)) {
|
if (posix_memalign((void *)&buf, alignment(fd_new), block_size)) {
|
||||||
log_err(_("Allocation of aligned memory failed.\n"));
|
log_err(_("Allocation of aligned memory failed.\n"));
|
||||||
r = -ENOMEM;
|
r = -ENOMEM;
|
||||||
@@ -1230,6 +1240,7 @@ int main(int argc, const char **argv)
|
|||||||
{ "keyfile-offset", '\0', POPT_ARG_LONG, &opt_keyfile_offset, 0, N_("Number of bytes to skip in keyfile"), N_("bytes") },
|
{ "keyfile-offset", '\0', POPT_ARG_LONG, &opt_keyfile_offset, 0, N_("Number of bytes to skip in keyfile"), N_("bytes") },
|
||||||
{ "keyfile-size", 'l', POPT_ARG_LONG, &opt_keyfile_size, 0, N_("Limits the read from keyfile"), N_("bytes") },
|
{ "keyfile-size", 'l', POPT_ARG_LONG, &opt_keyfile_size, 0, N_("Limits the read from keyfile"), N_("bytes") },
|
||||||
{ "reduce-device-size",'\0', POPT_ARG_INT, &opt_reduce_device_size, 0, N_("Reduce data device size (move data offset). DANGEROUS!"), N_("SECTORS") },
|
{ "reduce-device-size",'\0', POPT_ARG_INT, &opt_reduce_device_size, 0, N_("Reduce data device size (move data offset). DANGEROUS!"), N_("SECTORS") },
|
||||||
|
{ "device-size", '\0', POPT_ARG_STRING, &opt_device_size_str, 0, N_("Use only specified device size (ignore rest of device). DANGEROUS!"), N_("bytes") },
|
||||||
{ "new", 'N', POPT_ARG_NONE,&opt_new, 0, N_("Create new header on not encrypted device."), NULL },
|
{ "new", 'N', POPT_ARG_NONE,&opt_new, 0, N_("Create new header on not encrypted device."), NULL },
|
||||||
POPT_TABLEEND
|
POPT_TABLEEND
|
||||||
};
|
};
|
||||||
@@ -1311,6 +1322,11 @@ int main(int argc, const char **argv)
|
|||||||
usage(popt_context, EXIT_FAILURE, _("Option --new must be used together with --reduce_device_size."),
|
usage(popt_context, EXIT_FAILURE, _("Option --new must be used together with --reduce_device_size."),
|
||||||
poptGetInvocationName(popt_context));
|
poptGetInvocationName(popt_context));
|
||||||
|
|
||||||
|
if (opt_device_size_str &&
|
||||||
|
crypt_string_to_size(NULL, opt_device_size_str, &opt_device_size))
|
||||||
|
usage(popt_context, EXIT_FAILURE, _("Invalid device size specification."),
|
||||||
|
poptGetInvocationName(popt_context));
|
||||||
|
|
||||||
if (opt_debug) {
|
if (opt_debug) {
|
||||||
opt_verbose = 1;
|
opt_verbose = 1;
|
||||||
crypt_set_debug_level(-1);
|
crypt_set_debug_level(-1);
|
||||||
|
|||||||
Reference in New Issue
Block a user