source: mainline/uspace/app/bithenge/block.c@ 1923501

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 1923501 was 1923501, checked in by Sean Bartell <wingedtachikoma@…>, 13 years ago

Bithenge: use separate functions instead of casts.

  • Property mode set to 100644
File size: 3.8 KB
Line 
1/*
2 * Copyright (c) 2012 Sean Bartell
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29/** @addtogroup bithenge
30 * @{
31 */
32/**
33 * @file
34 * Access block devices as blobs.
35 * @todo Provide more information about the block device (block size).
36 */
37
38#include <assert.h>
39#include <errno.h>
40#include <libblock.h>
41#include <loc.h>
42#include <macros.h>
43#include <stdlib.h>
44#include "blob.h"
45#include "block.h"
46
47typedef struct {
48 bithenge_blob_t base;
49 service_id_t service_id;
50 aoff64_t size;
51} block_blob_t;
52
53static inline block_blob_t *block_from_blob(bithenge_blob_t *base)
54{
55 return (block_blob_t *)base;
56}
57
58static inline bithenge_blob_t *blob_from_block(block_blob_t *blob)
59{
60 return &blob->base;
61}
62
63static int block_size(bithenge_blob_t *base, aoff64_t *size)
64{
65 block_blob_t *blob = block_from_blob(base);
66 *size = blob->size;
67 return EOK;
68}
69
70static int block_read(bithenge_blob_t *base, aoff64_t offset, char *buffer,
71 aoff64_t *size)
72{
73 block_blob_t *blob = block_from_blob(base);
74 if (offset > blob->size)
75 return ELIMIT;
76 *size = min(*size, blob->size - offset);
77 return block_read_bytes_direct(blob->service_id, offset, *size, buffer);
78}
79
80static int block_destroy(bithenge_blob_t *base)
81{
82 block_blob_t *blob = block_from_blob(base);
83 block_fini(blob->service_id);
84 free(blob);
85 return EOK;
86}
87
88static const bithenge_random_access_blob_ops_t block_ops = {
89 .size = block_size,
90 .read = block_read,
91 .destroy = block_destroy,
92};
93
94/** Create a blob for a block device. The blob must be freed with
95 * @a bithenge_blob_t::bithenge_blob_destroy after it is used.
96 * @param out[out] Place to store the blob.
97 * @param service_id The service ID of the block device.
98 * @return EOK on success or an error code from errno.h. */
99int bithenge_new_block_blob(bithenge_blob_t **out, service_id_t service_id)
100{
101 assert(out);
102
103 // Initialize libblock
104 int rc;
105 rc = block_init(EXCHANGE_SERIALIZE, service_id, 2048);
106 if (rc != EOK)
107 return rc;
108
109 // Calculate total device size
110 size_t bsize;
111 aoff64_t nblocks;
112 aoff64_t size;
113 rc = block_get_bsize(service_id, &bsize);
114 if (rc != EOK)
115 return rc;
116 rc = block_get_nblocks(service_id, &nblocks);
117 if (rc != EOK)
118 return rc;
119 size = bsize * nblocks;
120
121 // Create blob
122 block_blob_t *blob = malloc(sizeof(*blob));
123 if (!blob)
124 return ENOMEM;
125 rc = bithenge_new_random_access_blob(blob_from_block(blob),
126 &block_ops);
127 if (rc != EOK) {
128 free(blob);
129 return rc;
130 }
131 blob->service_id = service_id;
132 blob->size = size;
133 *out = &blob->base;
134
135 return EOK;
136}
137
138/** @}
139 */
Note: See TracBrowser for help on using the repository browser.