qemu/qemu-file.c
<<
>>
Prefs
   1/*
   2 * QEMU System Emulator
   3 *
   4 * Copyright (c) 2003-2008 Fabrice Bellard
   5 *
   6 * Permission is hereby granted, free of charge, to any person obtaining a copy
   7 * of this software and associated documentation files (the "Software"), to deal
   8 * in the Software without restriction, including without limitation the rights
   9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  10 * copies of the Software, and to permit persons to whom the Software is
  11 * furnished to do so, subject to the following conditions:
  12 *
  13 * The above copyright notice and this permission notice shall be included in
  14 * all copies or substantial portions of the Software.
  15 *
  16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
  19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  22 * THE SOFTWARE.
  23 */
  24#include "qemu-common.h"
  25#include "qemu/iov.h"
  26#include "qemu/sockets.h"
  27#include "block/coroutine.h"
  28#include "migration/migration.h"
  29#include "migration/qemu-file.h"
  30#include "trace.h"
  31
  32#define IO_BUF_SIZE 32768
  33#define MAX_IOV_SIZE MIN(IOV_MAX, 64)
  34
  35struct QEMUFile {
  36    const QEMUFileOps *ops;
  37    void *opaque;
  38
  39    int64_t bytes_xfer;
  40    int64_t xfer_limit;
  41
  42    int64_t pos; /* start of buffer when writing, end of buffer
  43                    when reading */
  44    int buf_index;
  45    int buf_size; /* 0 when writing */
  46    uint8_t buf[IO_BUF_SIZE];
  47
  48    struct iovec iov[MAX_IOV_SIZE];
  49    unsigned int iovcnt;
  50
  51    int last_error;
  52};
  53
  54bool qemu_file_mode_is_not_valid(const char *mode)
  55{
  56    if (mode == NULL ||
  57        (mode[0] != 'r' && mode[0] != 'w') ||
  58        mode[1] != 'b' || mode[2] != 0) {
  59        fprintf(stderr, "qemu_fopen: Argument validity check failed\n");
  60        return true;
  61    }
  62
  63    return false;
  64}
  65
  66QEMUFile *qemu_fopen_ops(void *opaque, const QEMUFileOps *ops)
  67{
  68    QEMUFile *f;
  69
  70    f = g_malloc0(sizeof(QEMUFile));
  71
  72    f->opaque = opaque;
  73    f->ops = ops;
  74    return f;
  75}
  76
  77/*
  78 * Get last error for stream f
  79 *
  80 * Return negative error value if there has been an error on previous
  81 * operations, return 0 if no error happened.
  82 *
  83 */
  84int qemu_file_get_error(QEMUFile *f)
  85{
  86    return f->last_error;
  87}
  88
  89void qemu_file_set_error(QEMUFile *f, int ret)
  90{
  91    if (f->last_error == 0) {
  92        f->last_error = ret;
  93    }
  94}
  95
  96bool qemu_file_is_writable(QEMUFile *f)
  97{
  98    return f->ops->writev_buffer || f->ops->put_buffer;
  99}
 100
 101/**
 102 * Flushes QEMUFile buffer
 103 *
 104 * If there is writev_buffer QEMUFileOps it uses it otherwise uses
 105 * put_buffer ops.
 106 */
 107void qemu_fflush(QEMUFile *f)
 108{
 109    ssize_t ret = 0;
 110
 111    if (!qemu_file_is_writable(f)) {
 112        return;
 113    }
 114
 115    if (f->ops->writev_buffer) {
 116        if (f->iovcnt > 0) {
 117            ret = f->ops->writev_buffer(f->opaque, f->iov, f->iovcnt, f->pos);
 118        }
 119    } else {
 120        if (f->buf_index > 0) {
 121            ret = f->ops->put_buffer(f->opaque, f->buf, f->pos, f->buf_index);
 122        }
 123    }
 124    if (ret >= 0) {
 125        f->pos += ret;
 126    }
 127    f->buf_index = 0;
 128    f->iovcnt = 0;
 129    if (ret < 0) {
 130        qemu_file_set_error(f, ret);
 131    }
 132}
 133
 134void ram_control_before_iterate(QEMUFile *f, uint64_t flags)
 135{
 136    int ret = 0;
 137
 138    if (f->ops->before_ram_iterate) {
 139        ret = f->ops->before_ram_iterate(f, f->opaque, flags);
 140        if (ret < 0) {
 141            qemu_file_set_error(f, ret);
 142        }
 143    }
 144}
 145
 146void ram_control_after_iterate(QEMUFile *f, uint64_t flags)
 147{
 148    int ret = 0;
 149
 150    if (f->ops->after_ram_iterate) {
 151        ret = f->ops->after_ram_iterate(f, f->opaque, flags);
 152        if (ret < 0) {
 153            qemu_file_set_error(f, ret);
 154        }
 155    }
 156}
 157
 158void ram_control_load_hook(QEMUFile *f, uint64_t flags)
 159{
 160    int ret = -EINVAL;
 161
 162    if (f->ops->hook_ram_load) {
 163        ret = f->ops->hook_ram_load(f, f->opaque, flags);
 164        if (ret < 0) {
 165            qemu_file_set_error(f, ret);
 166        }
 167    } else {
 168        qemu_file_set_error(f, ret);
 169    }
 170}
 171
 172size_t ram_control_save_page(QEMUFile *f, ram_addr_t block_offset,
 173                         ram_addr_t offset, size_t size, int *bytes_sent)
 174{
 175    if (f->ops->save_page) {
 176        int ret = f->ops->save_page(f, f->opaque, block_offset,
 177                                    offset, size, bytes_sent);
 178
 179        if (ret != RAM_SAVE_CONTROL_DELAYED) {
 180            if (bytes_sent && *bytes_sent > 0) {
 181                qemu_update_position(f, *bytes_sent);
 182            } else if (ret < 0) {
 183                qemu_file_set_error(f, ret);
 184            }
 185        }
 186
 187        return ret;
 188    }
 189
 190    return RAM_SAVE_CONTROL_NOT_SUPP;
 191}
 192
 193/*
 194 * Attempt to fill the buffer from the underlying file
 195 * Returns the number of bytes read, or negative value for an error.
 196 *
 197 * Note that it can return a partially full buffer even in a not error/not EOF
 198 * case if the underlying file descriptor gives a short read, and that can
 199 * happen even on a blocking fd.
 200 */
 201static ssize_t qemu_fill_buffer(QEMUFile *f)
 202{
 203    int len;
 204    int pending;
 205
 206    assert(!qemu_file_is_writable(f));
 207
 208    pending = f->buf_size - f->buf_index;
 209    if (pending > 0) {
 210        memmove(f->buf, f->buf + f->buf_index, pending);
 211    }
 212    f->buf_index = 0;
 213    f->buf_size = pending;
 214
 215    len = f->ops->get_buffer(f->opaque, f->buf + pending, f->pos,
 216                        IO_BUF_SIZE - pending);
 217    if (len > 0) {
 218        f->buf_size += len;
 219        f->pos += len;
 220    } else if (len == 0) {
 221        qemu_file_set_error(f, -EIO);
 222    } else if (len != -EAGAIN) {
 223        qemu_file_set_error(f, len);
 224    }
 225
 226    return len;
 227}
 228
 229int qemu_get_fd(QEMUFile *f)
 230{
 231    if (f->ops->get_fd) {
 232        return f->ops->get_fd(f->opaque);
 233    }
 234    return -1;
 235}
 236
 237void qemu_update_position(QEMUFile *f, size_t size)
 238{
 239    f->pos += size;
 240}
 241
 242/** Closes the file
 243 *
 244 * Returns negative error value if any error happened on previous operations or
 245 * while closing the file. Returns 0 or positive number on success.
 246 *
 247 * The meaning of return value on success depends on the specific backend
 248 * being used.
 249 */
 250int qemu_fclose(QEMUFile *f)
 251{
 252    int ret;
 253    qemu_fflush(f);
 254    ret = qemu_file_get_error(f);
 255
 256    if (f->ops->close) {
 257        int ret2 = f->ops->close(f->opaque);
 258        if (ret >= 0) {
 259            ret = ret2;
 260        }
 261    }
 262    /* If any error was spotted before closing, we should report it
 263     * instead of the close() return value.
 264     */
 265    if (f->last_error) {
 266        ret = f->last_error;
 267    }
 268    g_free(f);
 269    trace_qemu_file_fclose();
 270    return ret;
 271}
 272
 273static void add_to_iovec(QEMUFile *f, const uint8_t *buf, int size)
 274{
 275    /* check for adjacent buffer and coalesce them */
 276    if (f->iovcnt > 0 && buf == f->iov[f->iovcnt - 1].iov_base +
 277        f->iov[f->iovcnt - 1].iov_len) {
 278        f->iov[f->iovcnt - 1].iov_len += size;
 279    } else {
 280        f->iov[f->iovcnt].iov_base = (uint8_t *)buf;
 281        f->iov[f->iovcnt++].iov_len = size;
 282    }
 283
 284    if (f->iovcnt >= MAX_IOV_SIZE) {
 285        qemu_fflush(f);
 286    }
 287}
 288
 289void qemu_put_buffer_async(QEMUFile *f, const uint8_t *buf, int size)
 290{
 291    if (!f->ops->writev_buffer) {
 292        qemu_put_buffer(f, buf, size);
 293        return;
 294    }
 295
 296    if (f->last_error) {
 297        return;
 298    }
 299
 300    f->bytes_xfer += size;
 301    add_to_iovec(f, buf, size);
 302}
 303
 304void qemu_put_buffer(QEMUFile *f, const uint8_t *buf, int size)
 305{
 306    int l;
 307
 308    if (f->last_error) {
 309        return;
 310    }
 311
 312    while (size > 0) {
 313        l = IO_BUF_SIZE - f->buf_index;
 314        if (l > size) {
 315            l = size;
 316        }
 317        memcpy(f->buf + f->buf_index, buf, l);
 318        f->bytes_xfer += l;
 319        if (f->ops->writev_buffer) {
 320            add_to_iovec(f, f->buf + f->buf_index, l);
 321        }
 322        f->buf_index += l;
 323        if (f->buf_index == IO_BUF_SIZE) {
 324            qemu_fflush(f);
 325        }
 326        if (qemu_file_get_error(f)) {
 327            break;
 328        }
 329        buf += l;
 330        size -= l;
 331    }
 332}
 333
 334void qemu_put_byte(QEMUFile *f, int v)
 335{
 336    if (f->last_error) {
 337        return;
 338    }
 339
 340    f->buf[f->buf_index] = v;
 341    f->bytes_xfer++;
 342    if (f->ops->writev_buffer) {
 343        add_to_iovec(f, f->buf + f->buf_index, 1);
 344    }
 345    f->buf_index++;
 346    if (f->buf_index == IO_BUF_SIZE) {
 347        qemu_fflush(f);
 348    }
 349}
 350
 351void qemu_file_skip(QEMUFile *f, int size)
 352{
 353    if (f->buf_index + size <= f->buf_size) {
 354        f->buf_index += size;
 355    }
 356}
 357
 358/*
 359 * Read 'size' bytes from file (at 'offset') into buf without moving the
 360 * pointer.
 361 *
 362 * It will return size bytes unless there was an error, in which case it will
 363 * return as many as it managed to read (assuming blocking fd's which
 364 * all current QEMUFile are)
 365 */
 366int qemu_peek_buffer(QEMUFile *f, uint8_t *buf, int size, size_t offset)
 367{
 368    int pending;
 369    int index;
 370
 371    assert(!qemu_file_is_writable(f));
 372    assert(offset < IO_BUF_SIZE);
 373    assert(size <= IO_BUF_SIZE - offset);
 374
 375    /* The 1st byte to read from */
 376    index = f->buf_index + offset;
 377    /* The number of available bytes starting at index */
 378    pending = f->buf_size - index;
 379
 380    /*
 381     * qemu_fill_buffer might return just a few bytes, even when there isn't
 382     * an error, so loop collecting them until we get enough.
 383     */
 384    while (pending < size) {
 385        int received = qemu_fill_buffer(f);
 386
 387        if (received <= 0) {
 388            break;
 389        }
 390
 391        index = f->buf_index + offset;
 392        pending = f->buf_size - index;
 393    }
 394
 395    if (pending <= 0) {
 396        return 0;
 397    }
 398    if (size > pending) {
 399        size = pending;
 400    }
 401
 402    memcpy(buf, f->buf + index, size);
 403    return size;
 404}
 405
 406/*
 407 * Read 'size' bytes of data from the file into buf.
 408 * 'size' can be larger than the internal buffer.
 409 *
 410 * It will return size bytes unless there was an error, in which case it will
 411 * return as many as it managed to read (assuming blocking fd's which
 412 * all current QEMUFile are)
 413 */
 414int qemu_get_buffer(QEMUFile *f, uint8_t *buf, int size)
 415{
 416    int pending = size;
 417    int done = 0;
 418
 419    while (pending > 0) {
 420        int res;
 421
 422        res = qemu_peek_buffer(f, buf, MIN(pending, IO_BUF_SIZE), 0);
 423        if (res == 0) {
 424            return done;
 425        }
 426        qemu_file_skip(f, res);
 427        buf += res;
 428        pending -= res;
 429        done += res;
 430    }
 431    return done;
 432}
 433
 434/*
 435 * Peeks a single byte from the buffer; this isn't guaranteed to work if
 436 * offset leaves a gap after the previous read/peeked data.
 437 */
 438int qemu_peek_byte(QEMUFile *f, int offset)
 439{
 440    int index = f->buf_index + offset;
 441
 442    assert(!qemu_file_is_writable(f));
 443    assert(offset < IO_BUF_SIZE);
 444
 445    if (index >= f->buf_size) {
 446        qemu_fill_buffer(f);
 447        index = f->buf_index + offset;
 448        if (index >= f->buf_size) {
 449            return 0;
 450        }
 451    }
 452    return f->buf[index];
 453}
 454
 455int qemu_get_byte(QEMUFile *f)
 456{
 457    int result;
 458
 459    result = qemu_peek_byte(f, 0);
 460    qemu_file_skip(f, 1);
 461    return result;
 462}
 463
 464int64_t qemu_ftell(QEMUFile *f)
 465{
 466    qemu_fflush(f);
 467    return f->pos;
 468}
 469
 470int qemu_file_rate_limit(QEMUFile *f)
 471{
 472    if (qemu_file_get_error(f)) {
 473        return 1;
 474    }
 475    if (f->xfer_limit > 0 && f->bytes_xfer > f->xfer_limit) {
 476        return 1;
 477    }
 478    return 0;
 479}
 480
 481int64_t qemu_file_get_rate_limit(QEMUFile *f)
 482{
 483    return f->xfer_limit;
 484}
 485
 486void qemu_file_set_rate_limit(QEMUFile *f, int64_t limit)
 487{
 488    f->xfer_limit = limit;
 489}
 490
 491void qemu_file_reset_rate_limit(QEMUFile *f)
 492{
 493    f->bytes_xfer = 0;
 494}
 495
 496void qemu_put_be16(QEMUFile *f, unsigned int v)
 497{
 498    qemu_put_byte(f, v >> 8);
 499    qemu_put_byte(f, v);
 500}
 501
 502void qemu_put_be32(QEMUFile *f, unsigned int v)
 503{
 504    qemu_put_byte(f, v >> 24);
 505    qemu_put_byte(f, v >> 16);
 506    qemu_put_byte(f, v >> 8);
 507    qemu_put_byte(f, v);
 508}
 509
 510void qemu_put_be64(QEMUFile *f, uint64_t v)
 511{
 512    qemu_put_be32(f, v >> 32);
 513    qemu_put_be32(f, v);
 514}
 515
 516unsigned int qemu_get_be16(QEMUFile *f)
 517{
 518    unsigned int v;
 519    v = qemu_get_byte(f) << 8;
 520    v |= qemu_get_byte(f);
 521    return v;
 522}
 523
 524unsigned int qemu_get_be32(QEMUFile *f)
 525{
 526    unsigned int v;
 527    v = qemu_get_byte(f) << 24;
 528    v |= qemu_get_byte(f) << 16;
 529    v |= qemu_get_byte(f) << 8;
 530    v |= qemu_get_byte(f);
 531    return v;
 532}
 533
 534uint64_t qemu_get_be64(QEMUFile *f)
 535{
 536    uint64_t v;
 537    v = (uint64_t)qemu_get_be32(f) << 32;
 538    v |= qemu_get_be32(f);
 539    return v;
 540}
 541
 542#define QSB_CHUNK_SIZE      (1 << 10)
 543#define QSB_MAX_CHUNK_SIZE  (16 * QSB_CHUNK_SIZE)
 544
 545/**
 546 * Create a QEMUSizedBuffer
 547 * This type of buffer uses scatter-gather lists internally and
 548 * can grow to any size. Any data array in the scatter-gather list
 549 * can hold different amount of bytes.
 550 *
 551 * @buffer: Optional buffer to copy into the QSB
 552 * @len: size of initial buffer; if @buffer is given, buffer must
 553 *       hold at least len bytes
 554 *
 555 * Returns a pointer to a QEMUSizedBuffer or NULL on allocation failure
 556 */
 557QEMUSizedBuffer *qsb_create(const uint8_t *buffer, size_t len)
 558{
 559    QEMUSizedBuffer *qsb;
 560    size_t alloc_len, num_chunks, i, to_copy;
 561    size_t chunk_size = (len > QSB_MAX_CHUNK_SIZE)
 562                        ? QSB_MAX_CHUNK_SIZE
 563                        : QSB_CHUNK_SIZE;
 564
 565    num_chunks = DIV_ROUND_UP(len ? len : QSB_CHUNK_SIZE, chunk_size);
 566    alloc_len = num_chunks * chunk_size;
 567
 568    qsb = g_try_new0(QEMUSizedBuffer, 1);
 569    if (!qsb) {
 570        return NULL;
 571    }
 572
 573    qsb->iov = g_try_new0(struct iovec, num_chunks);
 574    if (!qsb->iov) {
 575        g_free(qsb);
 576        return NULL;
 577    }
 578
 579    qsb->n_iov = num_chunks;
 580
 581    for (i = 0; i < num_chunks; i++) {
 582        qsb->iov[i].iov_base = g_try_malloc0(chunk_size);
 583        if (!qsb->iov[i].iov_base) {
 584            /* qsb_free is safe since g_free can cope with NULL */
 585            qsb_free(qsb);
 586            return NULL;
 587        }
 588
 589        qsb->iov[i].iov_len = chunk_size;
 590        if (buffer) {
 591            to_copy = (len - qsb->used) > chunk_size
 592                      ? chunk_size : (len - qsb->used);
 593            memcpy(qsb->iov[i].iov_base, &buffer[qsb->used], to_copy);
 594            qsb->used += to_copy;
 595        }
 596    }
 597
 598    qsb->size = alloc_len;
 599
 600    return qsb;
 601}
 602
 603/**
 604 * Free the QEMUSizedBuffer
 605 *
 606 * @qsb: The QEMUSizedBuffer to free
 607 */
 608void qsb_free(QEMUSizedBuffer *qsb)
 609{
 610    size_t i;
 611
 612    if (!qsb) {
 613        return;
 614    }
 615
 616    for (i = 0; i < qsb->n_iov; i++) {
 617        g_free(qsb->iov[i].iov_base);
 618    }
 619    g_free(qsb->iov);
 620    g_free(qsb);
 621}
 622
 623/**
 624 * Get the number of used bytes in the QEMUSizedBuffer
 625 *
 626 * @qsb: A QEMUSizedBuffer
 627 *
 628 * Returns the number of bytes currently used in this buffer
 629 */
 630size_t qsb_get_length(const QEMUSizedBuffer *qsb)
 631{
 632    return qsb->used;
 633}
 634
 635/**
 636 * Set the length of the buffer; the primary usage of this
 637 * function is to truncate the number of used bytes in the buffer.
 638 * The size will not be extended beyond the current number of
 639 * allocated bytes in the QEMUSizedBuffer.
 640 *
 641 * @qsb: A QEMUSizedBuffer
 642 * @new_len: The new length of bytes in the buffer
 643 *
 644 * Returns the number of bytes the buffer was truncated or extended
 645 * to.
 646 */
 647size_t qsb_set_length(QEMUSizedBuffer *qsb, size_t new_len)
 648{
 649    if (new_len <= qsb->size) {
 650        qsb->used = new_len;
 651    } else {
 652        qsb->used = qsb->size;
 653    }
 654    return qsb->used;
 655}
 656
 657/**
 658 * Get the iovec that holds the data for a given position @pos.
 659 *
 660 * @qsb: A QEMUSizedBuffer
 661 * @pos: The index of a byte in the buffer
 662 * @d_off: Pointer to an offset that this function will indicate
 663 *         at what position within the returned iovec the byte
 664 *         is to be found
 665 *
 666 * Returns the index of the iovec that holds the byte at the given
 667 * index @pos in the byte stream; a negative number if the iovec
 668 * for the given position @pos does not exist.
 669 */
 670static ssize_t qsb_get_iovec(const QEMUSizedBuffer *qsb,
 671                             off_t pos, off_t *d_off)
 672{
 673    ssize_t i;
 674    off_t curr = 0;
 675
 676    if (pos > qsb->used) {
 677        return -1;
 678    }
 679
 680    for (i = 0; i < qsb->n_iov; i++) {
 681        if (curr + qsb->iov[i].iov_len > pos) {
 682            *d_off = pos - curr;
 683            return i;
 684        }
 685        curr += qsb->iov[i].iov_len;
 686    }
 687    return -1;
 688}
 689
 690/*
 691 * Convert the QEMUSizedBuffer into a flat buffer.
 692 *
 693 * Note: If at all possible, try to avoid this function since it
 694 *       may unnecessarily copy memory around.
 695 *
 696 * @qsb: pointer to QEMUSizedBuffer
 697 * @start: offset to start at
 698 * @count: number of bytes to copy
 699 * @buf: a pointer to a buffer to write into (at least @count bytes)
 700 *
 701 * Returns the number of bytes copied into the output buffer
 702 */
 703ssize_t qsb_get_buffer(const QEMUSizedBuffer *qsb, off_t start,
 704                       size_t count, uint8_t *buffer)
 705{
 706    const struct iovec *iov;
 707    size_t to_copy, all_copy;
 708    ssize_t index;
 709    off_t s_off;
 710    off_t d_off = 0;
 711    char *s;
 712
 713    if (start > qsb->used) {
 714        return 0;
 715    }
 716
 717    all_copy = qsb->used - start;
 718    if (all_copy > count) {
 719        all_copy = count;
 720    } else {
 721        count = all_copy;
 722    }
 723
 724    index = qsb_get_iovec(qsb, start, &s_off);
 725    if (index < 0) {
 726        return 0;
 727    }
 728
 729    while (all_copy > 0) {
 730        iov = &qsb->iov[index];
 731
 732        s = iov->iov_base;
 733
 734        to_copy = iov->iov_len - s_off;
 735        if (to_copy > all_copy) {
 736            to_copy = all_copy;
 737        }
 738        memcpy(&buffer[d_off], &s[s_off], to_copy);
 739
 740        d_off += to_copy;
 741        all_copy -= to_copy;
 742
 743        s_off = 0;
 744        index++;
 745    }
 746
 747    return count;
 748}
 749
 750/**
 751 * Grow the QEMUSizedBuffer to the given size and allocate
 752 * memory for it.
 753 *
 754 * @qsb: A QEMUSizedBuffer
 755 * @new_size: The new size of the buffer
 756 *
 757 * Return:
 758 *    a negative error code in case of memory allocation failure
 759 * or
 760 *    the new size of the buffer. The returned size may be greater or equal
 761 *    to @new_size.
 762 */
 763static ssize_t qsb_grow(QEMUSizedBuffer *qsb, size_t new_size)
 764{
 765    size_t needed_chunks, i;
 766
 767    if (qsb->size < new_size) {
 768        struct iovec *new_iov;
 769        size_t size_diff = new_size - qsb->size;
 770        size_t chunk_size = (size_diff > QSB_MAX_CHUNK_SIZE)
 771                             ? QSB_MAX_CHUNK_SIZE : QSB_CHUNK_SIZE;
 772
 773        needed_chunks = DIV_ROUND_UP(size_diff, chunk_size);
 774
 775        new_iov = g_try_new(struct iovec, qsb->n_iov + needed_chunks);
 776        if (new_iov == NULL) {
 777            return -ENOMEM;
 778        }
 779
 780        /* Allocate new chunks as needed into new_iov */
 781        for (i = qsb->n_iov; i < qsb->n_iov + needed_chunks; i++) {
 782            new_iov[i].iov_base = g_try_malloc0(chunk_size);
 783            new_iov[i].iov_len = chunk_size;
 784            if (!new_iov[i].iov_base) {
 785                size_t j;
 786
 787                /* Free previously allocated new chunks */
 788                for (j = qsb->n_iov; j < i; j++) {
 789                    g_free(new_iov[j].iov_base);
 790                }
 791                g_free(new_iov);
 792
 793                return -ENOMEM;
 794            }
 795        }
 796
 797        /*
 798         * Now we can't get any allocation errors, copy over to new iov
 799         * and switch.
 800         */
 801        for (i = 0; i < qsb->n_iov; i++) {
 802            new_iov[i] = qsb->iov[i];
 803        }
 804
 805        qsb->n_iov += needed_chunks;
 806        g_free(qsb->iov);
 807        qsb->iov = new_iov;
 808        qsb->size += (needed_chunks * chunk_size);
 809    }
 810
 811    return qsb->size;
 812}
 813
 814/**
 815 * Write into the QEMUSizedBuffer at a given position and a given
 816 * number of bytes. This function will automatically grow the
 817 * QEMUSizedBuffer.
 818 *
 819 * @qsb: A QEMUSizedBuffer
 820 * @source: A byte array to copy data from
 821 * @pos: The position within the @qsb to write data to
 822 * @size: The number of bytes to copy into the @qsb
 823 *
 824 * Returns @size or a negative error code in case of memory allocation failure,
 825 *           or with an invalid 'pos'
 826 */
 827ssize_t qsb_write_at(QEMUSizedBuffer *qsb, const uint8_t *source,
 828                     off_t pos, size_t count)
 829{
 830    ssize_t rc = qsb_grow(qsb, pos + count);
 831    size_t to_copy;
 832    size_t all_copy = count;
 833    const struct iovec *iov;
 834    ssize_t index;
 835    char *dest;
 836    off_t d_off, s_off = 0;
 837
 838    if (rc < 0) {
 839        return rc;
 840    }
 841
 842    if (pos + count > qsb->used) {
 843        qsb->used = pos + count;
 844    }
 845
 846    index = qsb_get_iovec(qsb, pos, &d_off);
 847    if (index < 0) {
 848        return -EINVAL;
 849    }
 850
 851    while (all_copy > 0) {
 852        iov = &qsb->iov[index];
 853
 854        dest = iov->iov_base;
 855
 856        to_copy = iov->iov_len - d_off;
 857        if (to_copy > all_copy) {
 858            to_copy = all_copy;
 859        }
 860
 861        memcpy(&dest[d_off], &source[s_off], to_copy);
 862
 863        s_off += to_copy;
 864        all_copy -= to_copy;
 865
 866        d_off = 0;
 867        index++;
 868    }
 869
 870    return count;
 871}
 872
 873/**
 874 * Create a deep copy of the given QEMUSizedBuffer.
 875 *
 876 * @qsb: A QEMUSizedBuffer
 877 *
 878 * Returns a clone of @qsb or NULL on allocation failure
 879 */
 880QEMUSizedBuffer *qsb_clone(const QEMUSizedBuffer *qsb)
 881{
 882    QEMUSizedBuffer *out = qsb_create(NULL, qsb_get_length(qsb));
 883    size_t i;
 884    ssize_t res;
 885    off_t pos = 0;
 886
 887    if (!out) {
 888        return NULL;
 889    }
 890
 891    for (i = 0; i < qsb->n_iov; i++) {
 892        res =  qsb_write_at(out, qsb->iov[i].iov_base,
 893                            pos, qsb->iov[i].iov_len);
 894        if (res < 0) {
 895            qsb_free(out);
 896            return NULL;
 897        }
 898        pos += res;
 899    }
 900
 901    return out;
 902}
 903
 904typedef struct QEMUBuffer {
 905    QEMUSizedBuffer *qsb;
 906    QEMUFile *file;
 907} QEMUBuffer;
 908
 909static int buf_get_buffer(void *opaque, uint8_t *buf, int64_t pos, int size)
 910{
 911    QEMUBuffer *s = opaque;
 912    ssize_t len = qsb_get_length(s->qsb) - pos;
 913
 914    if (len <= 0) {
 915        return 0;
 916    }
 917
 918    if (len > size) {
 919        len = size;
 920    }
 921    return qsb_get_buffer(s->qsb, pos, len, buf);
 922}
 923
 924static int buf_put_buffer(void *opaque, const uint8_t *buf,
 925                          int64_t pos, int size)
 926{
 927    QEMUBuffer *s = opaque;
 928
 929    return qsb_write_at(s->qsb, buf, pos, size);
 930}
 931
 932static int buf_close(void *opaque)
 933{
 934    QEMUBuffer *s = opaque;
 935
 936    qsb_free(s->qsb);
 937
 938    g_free(s);
 939
 940    return 0;
 941}
 942
 943const QEMUSizedBuffer *qemu_buf_get(QEMUFile *f)
 944{
 945    QEMUBuffer *p;
 946
 947    qemu_fflush(f);
 948
 949    p = f->opaque;
 950
 951    return p->qsb;
 952}
 953
 954static const QEMUFileOps buf_read_ops = {
 955    .get_buffer = buf_get_buffer,
 956    .close =      buf_close,
 957};
 958
 959static const QEMUFileOps buf_write_ops = {
 960    .put_buffer = buf_put_buffer,
 961    .close =      buf_close,
 962};
 963
 964QEMUFile *qemu_bufopen(const char *mode, QEMUSizedBuffer *input)
 965{
 966    QEMUBuffer *s;
 967
 968    if (mode == NULL || (mode[0] != 'r' && mode[0] != 'w') ||
 969        mode[1] != '\0') {
 970        error_report("qemu_bufopen: Argument validity check failed");
 971        return NULL;
 972    }
 973
 974    s = g_malloc0(sizeof(QEMUBuffer));
 975    if (mode[0] == 'r') {
 976        s->qsb = input;
 977    }
 978
 979    if (s->qsb == NULL) {
 980        s->qsb = qsb_create(NULL, 0);
 981    }
 982    if (!s->qsb) {
 983        g_free(s);
 984        error_report("qemu_bufopen: qsb_create failed");
 985        return NULL;
 986    }
 987
 988
 989    if (mode[0] == 'r') {
 990        s->file = qemu_fopen_ops(s, &buf_read_ops);
 991    } else {
 992        s->file = qemu_fopen_ops(s, &buf_write_ops);
 993    }
 994    return s->file;
 995}
 996