1 /* 2 * QEMU block full disk encryption 3 * 4 * Copyright (c) 2015-2016 Red Hat, Inc. 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Lesser General Public 8 * License as published by the Free Software Foundation; either 9 * version 2 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Lesser General Public License for more details. 15 * 16 * You should have received a copy of the GNU Lesser General Public 17 * License along with this library; if not, see <http://www.gnu.org/licenses/>. 18 * 19 */ 20 21 #include "qemu/osdep.h" 22 23 #include "block/block_int.h" 24 #include "sysemu/block-backend.h" 25 #include "crypto/block.h" 26 #include "qapi/opts-visitor.h" 27 #include "qapi/qobject-input-visitor.h" 28 #include "qapi-visit.h" 29 #include "qapi/error.h" 30 #include "block/crypto.h" 31 32 typedef struct BlockCrypto BlockCrypto; 33 34 struct BlockCrypto { 35 QCryptoBlock *block; 36 }; 37 38 39 static int block_crypto_probe_generic(QCryptoBlockFormat format, 40 const uint8_t *buf, 41 int buf_size, 42 const char *filename) 43 { 44 if (qcrypto_block_has_format(format, buf, buf_size)) { 45 return 100; 46 } else { 47 return 0; 48 } 49 } 50 51 52 static ssize_t block_crypto_read_func(QCryptoBlock *block, 53 size_t offset, 54 uint8_t *buf, 55 size_t buflen, 56 void *opaque, 57 Error **errp) 58 { 59 BlockDriverState *bs = opaque; 60 ssize_t ret; 61 62 ret = bdrv_pread(bs->file, offset, buf, buflen); 63 if (ret < 0) { 64 error_setg_errno(errp, -ret, "Could not read encryption header"); 65 return ret; 66 } 67 return ret; 68 } 69 70 71 struct BlockCryptoCreateData { 72 const char *filename; 73 QemuOpts *opts; 74 BlockBackend *blk; 75 uint64_t size; 76 }; 77 78 79 static ssize_t block_crypto_write_func(QCryptoBlock *block, 80 size_t offset, 81 const uint8_t *buf, 82 size_t buflen, 83 void *opaque, 84 Error **errp) 85 { 86 struct BlockCryptoCreateData *data = opaque; 87 ssize_t ret; 88 89 ret = blk_pwrite(data->blk, offset, buf, buflen, 0); 90 if (ret < 0) { 91 error_setg_errno(errp, -ret, "Could not write encryption header"); 92 return ret; 93 } 94 return ret; 95 } 96 97 98 static ssize_t block_crypto_init_func(QCryptoBlock *block, 99 size_t headerlen, 100 void *opaque, 101 Error **errp) 102 { 103 struct BlockCryptoCreateData *data = opaque; 104 int ret; 105 106 /* User provided size should reflect amount of space made 107 * available to the guest, so we must take account of that 108 * which will be used by the crypto header 109 */ 110 data->size += headerlen; 111 112 qemu_opt_set_number(data->opts, BLOCK_OPT_SIZE, data->size, &error_abort); 113 ret = bdrv_create_file(data->filename, data->opts, errp); 114 if (ret < 0) { 115 return -1; 116 } 117 118 data->blk = blk_new_open(data->filename, NULL, NULL, 119 BDRV_O_RDWR | BDRV_O_PROTOCOL, errp); 120 if (!data->blk) { 121 return -1; 122 } 123 124 return 0; 125 } 126 127 128 static QemuOptsList block_crypto_runtime_opts_luks = { 129 .name = "crypto", 130 .head = QTAILQ_HEAD_INITIALIZER(block_crypto_runtime_opts_luks.head), 131 .desc = { 132 BLOCK_CRYPTO_OPT_DEF_LUKS_KEY_SECRET(""), 133 { /* end of list */ } 134 }, 135 }; 136 137 138 static QemuOptsList block_crypto_create_opts_luks = { 139 .name = "crypto", 140 .head = QTAILQ_HEAD_INITIALIZER(block_crypto_create_opts_luks.head), 141 .desc = { 142 { 143 .name = BLOCK_OPT_SIZE, 144 .type = QEMU_OPT_SIZE, 145 .help = "Virtual disk size" 146 }, 147 BLOCK_CRYPTO_OPT_DEF_LUKS_KEY_SECRET(""), 148 BLOCK_CRYPTO_OPT_DEF_LUKS_CIPHER_ALG(""), 149 BLOCK_CRYPTO_OPT_DEF_LUKS_CIPHER_MODE(""), 150 BLOCK_CRYPTO_OPT_DEF_LUKS_IVGEN_ALG(""), 151 BLOCK_CRYPTO_OPT_DEF_LUKS_IVGEN_HASH_ALG(""), 152 BLOCK_CRYPTO_OPT_DEF_LUKS_HASH_ALG(""), 153 BLOCK_CRYPTO_OPT_DEF_LUKS_ITER_TIME(""), 154 { /* end of list */ } 155 }, 156 }; 157 158 159 QCryptoBlockOpenOptions * 160 block_crypto_open_opts_init(QCryptoBlockFormat format, 161 QDict *opts, 162 Error **errp) 163 { 164 Visitor *v; 165 QCryptoBlockOpenOptions *ret = NULL; 166 Error *local_err = NULL; 167 168 ret = g_new0(QCryptoBlockOpenOptions, 1); 169 ret->format = format; 170 171 v = qobject_input_visitor_new_keyval(QOBJECT(opts)); 172 173 visit_start_struct(v, NULL, NULL, 0, &local_err); 174 if (local_err) { 175 goto out; 176 } 177 178 switch (format) { 179 case Q_CRYPTO_BLOCK_FORMAT_LUKS: 180 visit_type_QCryptoBlockOptionsLUKS_members( 181 v, &ret->u.luks, &local_err); 182 break; 183 184 case Q_CRYPTO_BLOCK_FORMAT_QCOW: 185 visit_type_QCryptoBlockOptionsQCow_members( 186 v, &ret->u.qcow, &local_err); 187 break; 188 189 default: 190 error_setg(&local_err, "Unsupported block format %d", format); 191 break; 192 } 193 if (!local_err) { 194 visit_check_struct(v, &local_err); 195 } 196 197 visit_end_struct(v, NULL); 198 199 out: 200 if (local_err) { 201 error_propagate(errp, local_err); 202 qapi_free_QCryptoBlockOpenOptions(ret); 203 ret = NULL; 204 } 205 visit_free(v); 206 return ret; 207 } 208 209 210 QCryptoBlockCreateOptions * 211 block_crypto_create_opts_init(QCryptoBlockFormat format, 212 QDict *opts, 213 Error **errp) 214 { 215 Visitor *v; 216 QCryptoBlockCreateOptions *ret = NULL; 217 Error *local_err = NULL; 218 219 ret = g_new0(QCryptoBlockCreateOptions, 1); 220 ret->format = format; 221 222 v = qobject_input_visitor_new_keyval(QOBJECT(opts)); 223 224 visit_start_struct(v, NULL, NULL, 0, &local_err); 225 if (local_err) { 226 goto out; 227 } 228 229 switch (format) { 230 case Q_CRYPTO_BLOCK_FORMAT_LUKS: 231 visit_type_QCryptoBlockCreateOptionsLUKS_members( 232 v, &ret->u.luks, &local_err); 233 break; 234 235 case Q_CRYPTO_BLOCK_FORMAT_QCOW: 236 visit_type_QCryptoBlockOptionsQCow_members( 237 v, &ret->u.qcow, &local_err); 238 break; 239 240 default: 241 error_setg(&local_err, "Unsupported block format %d", format); 242 break; 243 } 244 if (!local_err) { 245 visit_check_struct(v, &local_err); 246 } 247 248 visit_end_struct(v, NULL); 249 250 out: 251 if (local_err) { 252 error_propagate(errp, local_err); 253 qapi_free_QCryptoBlockCreateOptions(ret); 254 ret = NULL; 255 } 256 visit_free(v); 257 return ret; 258 } 259 260 261 static int block_crypto_open_generic(QCryptoBlockFormat format, 262 QemuOptsList *opts_spec, 263 BlockDriverState *bs, 264 QDict *options, 265 int flags, 266 Error **errp) 267 { 268 BlockCrypto *crypto = bs->opaque; 269 QemuOpts *opts = NULL; 270 Error *local_err = NULL; 271 int ret = -EINVAL; 272 QCryptoBlockOpenOptions *open_opts = NULL; 273 unsigned int cflags = 0; 274 QDict *cryptoopts = NULL; 275 276 bs->file = bdrv_open_child(NULL, options, "file", bs, &child_file, 277 false, errp); 278 if (!bs->file) { 279 return -EINVAL; 280 } 281 282 bs->supported_write_flags = BDRV_REQ_FUA & 283 bs->file->bs->supported_write_flags; 284 285 opts = qemu_opts_create(opts_spec, NULL, 0, &error_abort); 286 qemu_opts_absorb_qdict(opts, options, &local_err); 287 if (local_err) { 288 error_propagate(errp, local_err); 289 goto cleanup; 290 } 291 292 cryptoopts = qemu_opts_to_qdict(opts, NULL); 293 294 open_opts = block_crypto_open_opts_init(format, cryptoopts, errp); 295 if (!open_opts) { 296 goto cleanup; 297 } 298 299 if (flags & BDRV_O_NO_IO) { 300 cflags |= QCRYPTO_BLOCK_OPEN_NO_IO; 301 } 302 crypto->block = qcrypto_block_open(open_opts, NULL, 303 block_crypto_read_func, 304 bs, 305 cflags, 306 errp); 307 308 if (!crypto->block) { 309 ret = -EIO; 310 goto cleanup; 311 } 312 313 bs->encrypted = true; 314 315 ret = 0; 316 cleanup: 317 QDECREF(cryptoopts); 318 qapi_free_QCryptoBlockOpenOptions(open_opts); 319 return ret; 320 } 321 322 323 static int block_crypto_create_generic(QCryptoBlockFormat format, 324 const char *filename, 325 QemuOpts *opts, 326 Error **errp) 327 { 328 int ret = -EINVAL; 329 QCryptoBlockCreateOptions *create_opts = NULL; 330 QCryptoBlock *crypto = NULL; 331 struct BlockCryptoCreateData data = { 332 .size = ROUND_UP(qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0), 333 BDRV_SECTOR_SIZE), 334 .opts = opts, 335 .filename = filename, 336 }; 337 QDict *cryptoopts; 338 339 cryptoopts = qemu_opts_to_qdict(opts, NULL); 340 341 create_opts = block_crypto_create_opts_init(format, cryptoopts, errp); 342 if (!create_opts) { 343 return -1; 344 } 345 346 crypto = qcrypto_block_create(create_opts, NULL, 347 block_crypto_init_func, 348 block_crypto_write_func, 349 &data, 350 errp); 351 352 if (!crypto) { 353 ret = -EIO; 354 goto cleanup; 355 } 356 357 ret = 0; 358 cleanup: 359 QDECREF(cryptoopts); 360 qcrypto_block_free(crypto); 361 blk_unref(data.blk); 362 qapi_free_QCryptoBlockCreateOptions(create_opts); 363 return ret; 364 } 365 366 static int block_crypto_truncate(BlockDriverState *bs, int64_t offset, 367 PreallocMode prealloc, Error **errp) 368 { 369 BlockCrypto *crypto = bs->opaque; 370 uint64_t payload_offset = 371 qcrypto_block_get_payload_offset(crypto->block); 372 assert(payload_offset < (INT64_MAX - offset)); 373 374 offset += payload_offset; 375 376 return bdrv_truncate(bs->file, offset, prealloc, errp); 377 } 378 379 static void block_crypto_close(BlockDriverState *bs) 380 { 381 BlockCrypto *crypto = bs->opaque; 382 qcrypto_block_free(crypto->block); 383 } 384 385 386 /* 387 * 1 MB bounce buffer gives good performance / memory tradeoff 388 * when using cache=none|directsync. 389 */ 390 #define BLOCK_CRYPTO_MAX_IO_SIZE (1024 * 1024) 391 392 static coroutine_fn int 393 block_crypto_co_preadv(BlockDriverState *bs, uint64_t offset, uint64_t bytes, 394 QEMUIOVector *qiov, int flags) 395 { 396 BlockCrypto *crypto = bs->opaque; 397 uint64_t cur_bytes; /* number of bytes in current iteration */ 398 uint64_t bytes_done = 0; 399 uint8_t *cipher_data = NULL; 400 QEMUIOVector hd_qiov; 401 int ret = 0; 402 uint64_t sector_size = qcrypto_block_get_sector_size(crypto->block); 403 uint64_t payload_offset = qcrypto_block_get_payload_offset(crypto->block); 404 405 assert(!flags); 406 assert(payload_offset < INT64_MAX); 407 assert(QEMU_IS_ALIGNED(offset, sector_size)); 408 assert(QEMU_IS_ALIGNED(bytes, sector_size)); 409 410 qemu_iovec_init(&hd_qiov, qiov->niov); 411 412 /* Bounce buffer because we don't wish to expose cipher text 413 * in qiov which points to guest memory. 414 */ 415 cipher_data = 416 qemu_try_blockalign(bs->file->bs, MIN(BLOCK_CRYPTO_MAX_IO_SIZE, 417 qiov->size)); 418 if (cipher_data == NULL) { 419 ret = -ENOMEM; 420 goto cleanup; 421 } 422 423 while (bytes) { 424 cur_bytes = MIN(bytes, BLOCK_CRYPTO_MAX_IO_SIZE); 425 426 qemu_iovec_reset(&hd_qiov); 427 qemu_iovec_add(&hd_qiov, cipher_data, cur_bytes); 428 429 ret = bdrv_co_preadv(bs->file, payload_offset + offset + bytes_done, 430 cur_bytes, &hd_qiov, 0); 431 if (ret < 0) { 432 goto cleanup; 433 } 434 435 if (qcrypto_block_decrypt(crypto->block, offset + bytes_done, 436 cipher_data, cur_bytes, NULL) < 0) { 437 ret = -EIO; 438 goto cleanup; 439 } 440 441 qemu_iovec_from_buf(qiov, bytes_done, cipher_data, cur_bytes); 442 443 bytes -= cur_bytes; 444 bytes_done += cur_bytes; 445 } 446 447 cleanup: 448 qemu_iovec_destroy(&hd_qiov); 449 qemu_vfree(cipher_data); 450 451 return ret; 452 } 453 454 455 static coroutine_fn int 456 block_crypto_co_pwritev(BlockDriverState *bs, uint64_t offset, uint64_t bytes, 457 QEMUIOVector *qiov, int flags) 458 { 459 BlockCrypto *crypto = bs->opaque; 460 uint64_t cur_bytes; /* number of bytes in current iteration */ 461 uint64_t bytes_done = 0; 462 uint8_t *cipher_data = NULL; 463 QEMUIOVector hd_qiov; 464 int ret = 0; 465 uint64_t sector_size = qcrypto_block_get_sector_size(crypto->block); 466 uint64_t payload_offset = qcrypto_block_get_payload_offset(crypto->block); 467 468 assert(!(flags & ~BDRV_REQ_FUA)); 469 assert(payload_offset < INT64_MAX); 470 assert(QEMU_IS_ALIGNED(offset, sector_size)); 471 assert(QEMU_IS_ALIGNED(bytes, sector_size)); 472 473 qemu_iovec_init(&hd_qiov, qiov->niov); 474 475 /* Bounce buffer because we're not permitted to touch 476 * contents of qiov - it points to guest memory. 477 */ 478 cipher_data = 479 qemu_try_blockalign(bs->file->bs, MIN(BLOCK_CRYPTO_MAX_IO_SIZE, 480 qiov->size)); 481 if (cipher_data == NULL) { 482 ret = -ENOMEM; 483 goto cleanup; 484 } 485 486 while (bytes) { 487 cur_bytes = MIN(bytes, BLOCK_CRYPTO_MAX_IO_SIZE); 488 489 qemu_iovec_to_buf(qiov, bytes_done, cipher_data, cur_bytes); 490 491 if (qcrypto_block_encrypt(crypto->block, offset + bytes_done, 492 cipher_data, cur_bytes, NULL) < 0) { 493 ret = -EIO; 494 goto cleanup; 495 } 496 497 qemu_iovec_reset(&hd_qiov); 498 qemu_iovec_add(&hd_qiov, cipher_data, cur_bytes); 499 500 ret = bdrv_co_pwritev(bs->file, payload_offset + offset + bytes_done, 501 cur_bytes, &hd_qiov, flags); 502 if (ret < 0) { 503 goto cleanup; 504 } 505 506 bytes -= cur_bytes; 507 bytes_done += cur_bytes; 508 } 509 510 cleanup: 511 qemu_iovec_destroy(&hd_qiov); 512 qemu_vfree(cipher_data); 513 514 return ret; 515 } 516 517 static void block_crypto_refresh_limits(BlockDriverState *bs, Error **errp) 518 { 519 BlockCrypto *crypto = bs->opaque; 520 uint64_t sector_size = qcrypto_block_get_sector_size(crypto->block); 521 bs->bl.request_alignment = sector_size; /* No sub-sector I/O */ 522 } 523 524 525 static int64_t block_crypto_getlength(BlockDriverState *bs) 526 { 527 BlockCrypto *crypto = bs->opaque; 528 int64_t len = bdrv_getlength(bs->file->bs); 529 530 uint64_t offset = qcrypto_block_get_payload_offset(crypto->block); 531 assert(offset < INT64_MAX); 532 assert(offset < len); 533 534 len -= offset; 535 536 return len; 537 } 538 539 540 static int block_crypto_probe_luks(const uint8_t *buf, 541 int buf_size, 542 const char *filename) { 543 return block_crypto_probe_generic(Q_CRYPTO_BLOCK_FORMAT_LUKS, 544 buf, buf_size, filename); 545 } 546 547 static int block_crypto_open_luks(BlockDriverState *bs, 548 QDict *options, 549 int flags, 550 Error **errp) 551 { 552 return block_crypto_open_generic(Q_CRYPTO_BLOCK_FORMAT_LUKS, 553 &block_crypto_runtime_opts_luks, 554 bs, options, flags, errp); 555 } 556 557 static int block_crypto_create_luks(const char *filename, 558 QemuOpts *opts, 559 Error **errp) 560 { 561 return block_crypto_create_generic(Q_CRYPTO_BLOCK_FORMAT_LUKS, 562 filename, opts, errp); 563 } 564 565 static int block_crypto_get_info_luks(BlockDriverState *bs, 566 BlockDriverInfo *bdi) 567 { 568 BlockDriverInfo subbdi; 569 int ret; 570 571 ret = bdrv_get_info(bs->file->bs, &subbdi); 572 if (ret != 0) { 573 return ret; 574 } 575 576 bdi->unallocated_blocks_are_zero = false; 577 bdi->can_write_zeroes_with_unmap = false; 578 bdi->cluster_size = subbdi.cluster_size; 579 580 return 0; 581 } 582 583 static ImageInfoSpecific * 584 block_crypto_get_specific_info_luks(BlockDriverState *bs) 585 { 586 BlockCrypto *crypto = bs->opaque; 587 ImageInfoSpecific *spec_info; 588 QCryptoBlockInfo *info; 589 590 info = qcrypto_block_get_info(crypto->block, NULL); 591 if (!info) { 592 return NULL; 593 } 594 if (info->format != Q_CRYPTO_BLOCK_FORMAT_LUKS) { 595 qapi_free_QCryptoBlockInfo(info); 596 return NULL; 597 } 598 599 spec_info = g_new(ImageInfoSpecific, 1); 600 spec_info->type = IMAGE_INFO_SPECIFIC_KIND_LUKS; 601 spec_info->u.luks.data = g_new(QCryptoBlockInfoLUKS, 1); 602 *spec_info->u.luks.data = info->u.luks; 603 604 /* Blank out pointers we've just stolen to avoid double free */ 605 memset(&info->u.luks, 0, sizeof(info->u.luks)); 606 607 qapi_free_QCryptoBlockInfo(info); 608 609 return spec_info; 610 } 611 612 BlockDriver bdrv_crypto_luks = { 613 .format_name = "luks", 614 .instance_size = sizeof(BlockCrypto), 615 .bdrv_probe = block_crypto_probe_luks, 616 .bdrv_open = block_crypto_open_luks, 617 .bdrv_close = block_crypto_close, 618 .bdrv_child_perm = bdrv_format_default_perms, 619 .bdrv_create = block_crypto_create_luks, 620 .bdrv_truncate = block_crypto_truncate, 621 .create_opts = &block_crypto_create_opts_luks, 622 623 .bdrv_refresh_limits = block_crypto_refresh_limits, 624 .bdrv_co_preadv = block_crypto_co_preadv, 625 .bdrv_co_pwritev = block_crypto_co_pwritev, 626 .bdrv_getlength = block_crypto_getlength, 627 .bdrv_get_info = block_crypto_get_info_luks, 628 .bdrv_get_specific_info = block_crypto_get_specific_info_luks, 629 }; 630 631 static void block_crypto_init(void) 632 { 633 bdrv_register(&bdrv_crypto_luks); 634 } 635 636 block_init(block_crypto_init); 637