source: mainline/uspace/srv/fs/udf/udf_idx.c@ 3d95c9d

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 3d95c9d was cde999a, checked in by Jiří Zárevúcky <zarevucky.jiri@…>, 7 years ago

Fix comments to stop referring to error codes as negative.

  • Property mode set to 100644
File size: 5.2 KB
Line 
1/*
2 * Copyright (c) 2012 Julia Medvedeva
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 fs
30 * @{
31 */
32/**
33 * @file udf_idx.c
34 * @brief Very simple UDF hashtable for nodes
35 */
36
37#include "../../vfs/vfs.h"
38#include <errno.h>
39#include <str.h>
40#include <assert.h>
41#include <fibril_synch.h>
42#include <stdlib.h>
43#include <adt/hash_table.h>
44#include <adt/hash.h>
45#include <adt/list.h>
46#include <stdbool.h>
47#include "udf_idx.h"
48#include "udf.h"
49
50static FIBRIL_MUTEX_INITIALIZE(udf_idx_lock);
51
52static hash_table_t udf_idx;
53
54typedef struct {
55 service_id_t service_id;
56 fs_index_t index;
57} udf_ht_key_t;
58
59static size_t udf_idx_hash(const ht_link_t *item)
60{
61 udf_node_t *node = hash_table_get_inst(item, udf_node_t, link);
62 return hash_combine(node->instance->service_id, node->index);
63}
64
65static size_t udf_idx_key_hash(void *k)
66{
67 udf_ht_key_t *key = (udf_ht_key_t *) k;
68 return hash_combine(key->service_id, key->index);
69}
70
71static bool udf_idx_key_equal(void *k, const ht_link_t *item)
72{
73 udf_ht_key_t *key = (udf_ht_key_t *) k;
74 udf_node_t *node = hash_table_get_inst(item, udf_node_t, link);
75
76 return (key->service_id == node->instance->service_id) &&
77 (key->index == node->index);
78}
79
80static hash_table_ops_t udf_idx_ops = {
81 .hash = udf_idx_hash,
82 .key_hash = udf_idx_key_hash,
83 .key_equal = udf_idx_key_equal,
84 .equal = NULL,
85 .remove_callback = NULL
86};
87
88/** Initialization of hash table
89 *
90 * @return EOK on success or an error code.
91 *
92 */
93int udf_idx_init(void)
94{
95 if (!hash_table_create(&udf_idx, 0, 0, &udf_idx_ops))
96 return ENOMEM;
97
98 return EOK;
99}
100
101/** Delete hash table
102 *
103 * @return EOK on success or an error code.
104 *
105 */
106int udf_idx_fini(void)
107{
108 hash_table_destroy(&udf_idx);
109 return EOK;
110}
111
112/** Get node from hash table
113 *
114 * @param udfn Returned value - UDF node
115 * @param instance UDF instance
116 * @param index Absolute position of ICB (sector)
117 *
118 * @return EOK on success or an error code.
119 *
120 */
121int udf_idx_get(udf_node_t **udfn, udf_instance_t *instance, fs_index_t index)
122{
123 fibril_mutex_lock(&udf_idx_lock);
124
125 udf_ht_key_t key = {
126 .service_id = instance->service_id,
127 .index = index
128 };
129
130 ht_link_t *already_open = hash_table_find(&udf_idx, &key);
131 if (already_open) {
132 udf_node_t *node = hash_table_get_inst(already_open,
133 udf_node_t, link);
134 node->ref_cnt++;
135
136 *udfn = node;
137
138 fibril_mutex_unlock(&udf_idx_lock);
139 return EOK;
140 }
141
142 fibril_mutex_unlock(&udf_idx_lock);
143 return ENOENT;
144}
145
146/** Create new node in hash table
147 *
148 * @param udfn Returned value - new UDF node
149 * @param instance UDF instance
150 * @param index Absolute position of ICB (sector)
151 *
152 * @return EOK on success or an error code.
153 *
154 */
155int udf_idx_add(udf_node_t **udfn, udf_instance_t *instance, fs_index_t index)
156{
157 fibril_mutex_lock(&udf_idx_lock);
158
159 udf_node_t *udf_node = malloc(sizeof(udf_node_t));
160 if (udf_node == NULL) {
161 fibril_mutex_unlock(&udf_idx_lock);
162 return ENOMEM;
163 }
164
165 fs_node_t *fs_node = malloc(sizeof(fs_node_t));
166 if (fs_node == NULL) {
167 free(udf_node);
168 fibril_mutex_unlock(&udf_idx_lock);
169 return ENOMEM;
170 }
171
172 fs_node_initialize(fs_node);
173
174 udf_node->index = index;
175 udf_node->instance = instance;
176 udf_node->ref_cnt = 1;
177 udf_node->link_cnt = 0;
178 udf_node->fs_node = fs_node;
179 udf_node->data = NULL;
180 udf_node->allocators = NULL;
181
182 fibril_mutex_initialize(&udf_node->lock);
183 fs_node->data = udf_node;
184
185 hash_table_insert(&udf_idx, &udf_node->link);
186 instance->open_nodes_count++;
187
188 *udfn = udf_node;
189
190 fibril_mutex_unlock(&udf_idx_lock);
191 return EOK;
192}
193
194/** Delete node from hash table
195 *
196 * @param node UDF node
197 *
198 * @return EOK on success or an error code.
199 *
200 */
201int udf_idx_del(udf_node_t *node)
202{
203 assert(node->ref_cnt == 0);
204
205 fibril_mutex_lock(&udf_idx_lock);
206
207 hash_table_remove_item(&udf_idx, &node->link);
208
209 assert(node->instance->open_nodes_count > 0);
210 node->instance->open_nodes_count--;
211
212 free(node->fs_node);
213 free(node);
214
215 fibril_mutex_unlock(&udf_idx_lock);
216 return EOK;
217}
218
219/**
220 * @}
221 */
Note: See TracBrowser for help on using the repository browser.