1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2 * vim:expandtab:shiftwidth=8:tabstop=8:
6 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 only,
10 * as published by the Free Software Foundation.
12 * This program is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License version 2 for more details (a copy is included
16 * in the LICENSE file that accompanied this code).
18 * You should have received a copy of the GNU General Public License
19 * version 2 along with this program; If not, see
20 * http://www.sun.com/software/products/lustre/docs/GPLv2.pdf
22 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
23 * CA 95054 USA or visit www.sun.com if you need additional information or
29 * Copyright 2008 Sun Microsystems, Inc. All rights reserved
30 * Use is subject to license terms.
33 * This file is part of Lustre, http://www.lustre.org/
34 * Lustre is a trademark of Sun Microsystems, Inc.
40 * Author: Nikita Danilov <nikita@clusterfs.com>
44 * oi uses two mechanisms to implement fid->cookie mapping:
46 * - persistent index, where cookie is a record and fid is a key, and
48 * - algorithmic mapping for "igif" fids.
53 # define EXPORT_SYMTAB
55 #define DEBUG_SUBSYSTEM S_MDS
57 #include <linux/module.h>
59 /* LUSTRE_VERSION_CODE */
60 #include <lustre_ver.h>
62 * struct OBD_{ALLOC,FREE}*()
66 #include <obd_support.h>
69 #include <lustre_fid.h>
72 /* osd_lookup(), struct osd_thread_info */
73 #include "osd_internal.h"
75 #include "dt_object.h"
82 static const struct oi_descr oi_descr[OSD_OI_FID_NR] = {
83 [OSD_OI_FID_SMALL] = {
87 [OSD_OI_FID_OTHER] = {
88 .fid_size = sizeof(struct lu_fid),
93 int osd_oi_init(struct osd_thread_info *info,
94 struct osd_oi *oi, struct dt_device *dev)
98 const struct lu_env *env;
100 CLASSERT(ARRAY_SIZE(oi->oi_dir) == ARRAY_SIZE(oi_descr));
104 memset(oi, 0, sizeof *oi);
106 for (i = rc = 0; i < ARRAY_SIZE(oi->oi_dir) && rc == 0; ++i) {
109 * Allocate on stack---this is initialization.
111 const struct dt_index_features feat = {
112 .dif_flags = DT_IND_UPDATE,
113 .dif_keysize_min = oi_descr[i].fid_size,
114 .dif_keysize_max = oi_descr[i].fid_size,
115 .dif_recsize_min = sizeof(struct osd_inode_id),
116 .dif_recsize_max = sizeof(struct osd_inode_id)
118 struct dt_object *obj;
120 name = oi_descr[i].name;
121 obj = dt_store_open(env, dev, name, &info->oti_fid);
123 rc = obj->do_ops->do_index_try(env, obj, &feat);
125 LASSERT(obj->do_index_ops != NULL);
128 CERROR("Wrong index \"%s\": %d\n", name, rc);
129 lu_object_put(env, &obj->do_lu);
133 CERROR("Cannot open \"%s\": %d\n", name, rc);
137 osd_oi_fini(info, oi);
141 void osd_oi_fini(struct osd_thread_info *info, struct osd_oi *oi)
144 for (i = 0; i < ARRAY_SIZE(oi->oi_dir); ++i) {
145 if (oi->oi_dir[i] != NULL) {
146 lu_object_put(info->oti_env, &oi->oi_dir[i]->do_lu);
147 oi->oi_dir[i] = NULL;
152 static const struct dt_key *oi_fid_key(struct osd_thread_info *info,
154 const struct lu_fid *fid,
155 struct dt_object **idx)
158 struct lu_fid_pack *pack;
160 pack = &info->oti_pack;
161 fid_pack(pack, fid, &info->oti_fid);
162 for (i = 0; i < ARRAY_SIZE(oi->oi_dir); ++i) {
163 if (pack->fp_len == oi_descr[i].fid_size + sizeof pack->fp_len){
164 *idx = oi->oi_dir[i];
165 return (const struct dt_key *)&pack->fp_area;
168 CERROR("Unsupported packed fid size: %d ("DFID")\n",
169 pack->fp_len, PFID(fid));
174 int osd_oi_lookup(struct osd_thread_info *info, struct osd_oi *oi,
175 const struct lu_fid *fid, struct osd_inode_id *id)
179 if (fid_is_igif(fid)) {
180 lu_igif_to_id(fid, id);
183 struct dt_object *idx;
184 const struct dt_key *key;
186 key = oi_fid_key(info, oi, fid, &idx);
187 rc = idx->do_index_ops->dio_lookup(info->oti_env, idx,
188 (struct dt_rec *)id, key,
190 id->oii_ino = be32_to_cpu(id->oii_ino);
191 id->oii_gen = be32_to_cpu(id->oii_gen);
196 int osd_oi_insert(struct osd_thread_info *info, struct osd_oi *oi,
197 const struct lu_fid *fid, const struct osd_inode_id *id0,
200 struct dt_object *idx;
201 struct osd_inode_id *id;
202 const struct dt_key *key;
204 if (fid_is_igif(fid))
207 key = oi_fid_key(info, oi, fid, &idx);
209 id->oii_ino = cpu_to_be32(id0->oii_ino);
210 id->oii_gen = cpu_to_be32(id0->oii_gen);
211 return idx->do_index_ops->dio_insert(info->oti_env, idx,
212 (const struct dt_rec *)id,
213 key, th, BYPASS_CAPA);
216 int osd_oi_delete(struct osd_thread_info *info,
217 struct osd_oi *oi, const struct lu_fid *fid,
220 struct dt_object *idx;
221 const struct dt_key *key;
223 if (fid_is_igif(fid))
226 key = oi_fid_key(info, oi, fid, &idx);
227 return idx->do_index_ops->dio_delete(info->oti_env, idx,
228 key, th, BYPASS_CAPA);