static int dmg_read_resource_fork(BlockDriverState *bs, DmgHeaderState *ds,

                                  uint64_t info_begin, uint64_t info_length)

{

    BDRVDMGState *s = bs->opaque;

    int ret;

    uint32_t count, rsrc_data_offset;

    uint8_t *buffer = NULL;

    uint64_t info_end;

    uint64_t offset;



    /* read offset from begin of resource fork (info_begin) to resource data */

    ret = read_uint32(bs, info_begin, &rsrc_data_offset);

    if (ret < 0) {

        goto fail;

    } else if (rsrc_data_offset > info_length) {

        ret = -EINVAL;

        goto fail;

    }



    /* read length of resource data */

    ret = read_uint32(bs, info_begin + 8, &count);

    if (ret < 0) {

        goto fail;

    } else if (count == 0 || rsrc_data_offset + count > info_length) {

        ret = -EINVAL;

        goto fail;

    }



    /* begin of resource data (consisting of one or more resources) */

    offset = info_begin + rsrc_data_offset;



    /* end of resource data (there is possibly a following resource map

     * which will be ignored). */

    info_end = offset + count;



    /* read offsets (mish blocks) from one or more resources in resource data */

    while (offset < info_end) {

        /* size of following resource */

        ret = read_uint32(bs, offset, &count);

        if (ret < 0) {

            goto fail;

        } else if (count == 0) {

            ret = -EINVAL;

            goto fail;

        }

        offset += 4;



        buffer = g_realloc(buffer, count);

        ret = bdrv_pread(bs->file, offset, buffer, count);

        if (ret < 0) {

            goto fail;

        }



        ret = dmg_read_mish_block(s, ds, buffer, count);

        if (ret < 0) {

            goto fail;

        }

        /* advance offset by size of resource */

        offset += count;

    }

    ret = 0;



fail:

    g_free(buffer);

    return ret;

}

static int dmg_read_resource_fork(BlockDriverState *bs, DmgHeaderState *ds,

                                  uint64_t info_begin, uint64_t info_length)

{

    BDRVDMGState *s = bs->opaque;

    int ret;

    uint32_t count, rsrc_data_offset;

    uint8_t *buffer = NULL;

    uint64_t info_end;

    uint64_t offset;



    

    ret = read_uint32(bs, info_begin, &rsrc_data_offset);

    if (ret < 0) {

        goto fail;

    } else if (rsrc_data_offset > info_length) {

        ret = -EINVAL;

        goto fail;

    }



    

    ret = read_uint32(bs, info_begin + 8, &count);

    if (ret < 0) {

        goto fail;

    } else if (count == 0 || rsrc_data_offset + count > info_length) {

        ret = -EINVAL;

        goto fail;

    }



    

    offset = info_begin + rsrc_data_offset;



    



    info_end = offset + count;



    

    while (offset < info_end) {

        

        ret = read_uint32(bs, offset, &count);

        if (ret < 0) {

            goto fail;

        } else if (count == 0) {

            ret = -EINVAL;

            goto fail;

        }

        offset += 4;



        buffer = g_realloc(buffer, count);

        ret = bdrv_pread(bs->file, offset, buffer, count);

        if (ret < 0) {

            goto fail;

        }



        ret = dmg_read_mish_block(s, ds, buffer, count);

        if (ret < 0) {

            goto fail;

        }

        

        offset += count;

    }

    ret = 0;



fail:

    g_free(buffer);

    return ret;

}

        } else if (count == 0) {
static int FUNC_0(BlockDriverState *VAR_0, DmgHeaderState *VAR_1,

                                  uint64_t VAR_2, uint64_t VAR_3)

{

    BDRVDMGState *s = VAR_0->opaque;

    int VAR_4;

    uint32_t count, rsrc_data_offset;

    uint8_t *buffer = NULL;

    uint64_t info_end;

    uint64_t offset;



    

    VAR_4 = read_uint32(VAR_0, VAR_2, &rsrc_data_offset);

    if (VAR_4 < 0) {

        goto fail;

    } else if (rsrc_data_offset > VAR_3) {

        VAR_4 = -EINVAL;

        goto fail;

    }



    

    VAR_4 = read_uint32(VAR_0, VAR_2 + 8, &count);

    if (VAR_4 < 0) {

        goto fail;

    } else if (count == 0 || rsrc_data_offset + count > VAR_3) {

        VAR_4 = -EINVAL;

        goto fail;

    }



    

    offset = VAR_2 + rsrc_data_offset;



    



    info_end = offset + count;



    

    while (offset < info_end) {

        

        VAR_4 = read_uint32(VAR_0, offset, &count);

        if (VAR_4 < 0) {

            goto fail;

        } else if (count == 0) {

            VAR_4 = -EINVAL;

            goto fail;

        }

        offset += 4;



        buffer = g_realloc(buffer, count);

        VAR_4 = bdrv_pread(VAR_0->file, offset, buffer, count);

        if (VAR_4 < 0) {

            goto fail;

        }



        VAR_4 = dmg_read_mish_block(s, VAR_1, buffer, count);

        if (VAR_4 < 0) {

            goto fail;

        }

        

        offset += count;

    }

    VAR_4 = 0;



fail:

    g_free(buffer);

    return VAR_4;

}

static int FUNC_0(BlockDriverState *VAR_0, DmgHeaderState *VAR_1,
uint64_t VAR_2, uint64_t VAR_3)
{ BDRVDMGState *s = VAR_0->opaque; int VAR_4; uint32_t count, rsrc_data_offset; uint8_t *buffer = NULL; uint64_t info_end; uint64_t offset; VAR_4 = read_uint32(VAR_0, VAR_2, &rsrc_data_offset); if (VAR_4 < 0) { goto fail; } else if (rsrc_data_offset > VAR_3) { VAR_4 = -EINVAL; goto fail; } VAR_4 = read_uint32(VAR_0, VAR_2 + 8, &count); if (VAR_4 < 0) { goto fail; } else if (count == 0 || rsrc_data_offset + count > VAR_3) { VAR_4 = -EINVAL; goto fail; } offset = VAR_2 + rsrc_data_offset; info_end = offset + count; while (offset < info_end) { VAR_4 = read_uint32(VAR_0, offset, &count); if (VAR_4 < 0) { goto fail; } else if (count == 0) { VAR_4 = -EINVAL; goto fail; } offset += 4; buffer = g_realloc(buffer, count); VAR_4 = bdrv_pread(VAR_0->file, offset, buffer, count); if (VAR_4 < 0) { goto fail; } VAR_4 = dmg_read_mish_block(s, VAR_1, buffer, count); if (VAR_4 < 0) { goto fail; } offset += count; } VAR_4 = 0; fail:
g_free(buffer); return VAR_4; }