Whamcloud - gitweb
merge b_devel into HEAD (20030703)
[fs/lustre-release.git] / lustre / llite / dcache.c
1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2  * vim:expandtab:shiftwidth=8:tabstop=8:
3  *
4  *  Copyright (c) 2001-2003 Cluster File Systems, Inc.
5  *
6  *   This file is part of Lustre, http://www.lustre.org.
7  *
8  *   Lustre is free software; you can redistribute it and/or
9  *   modify it under the terms of version 2 of the GNU General Public
10  *   License as published by the Free Software Foundation.
11  *
12  *   Lustre is distributed in the hope that it will be useful,
13  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *   GNU General Public License for more details.
16  *
17  *   You should have received a copy of the GNU General Public License
18  *   along with Lustre; if not, write to the Free Software
19  *   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20  */
21
22 #include <linux/fs.h>
23 #include <linux/sched.h>
24 #include <linux/smp_lock.h>
25 #include <linux/quotaops.h>
26
27 #define DEBUG_SUBSYSTEM S_LLITE
28
29 #include <linux/obd_support.h>
30 #include <linux/lustre_lite.h>
31 #include <linux/lustre_idl.h>
32 #include <linux/lustre_dlm.h>
33
34 /* should NOT be called with the dcache lock, see fs/dcache.c */
35 void ll_release(struct dentry *de)
36 {
37         ENTRY;
38         OBD_FREE(de->d_fsdata, sizeof(struct ll_dentry_data));
39         EXIT;
40 }
41
42 int ll_delete(struct dentry *de)
43 {
44         if (de->d_it != 0) {
45                 CERROR("%s put dentry %p+%p with d_it %p\n", current->comm,
46                        de, de->d_fsdata, de->d_it);
47                 LBUG();
48         }
49         return 0;
50 }
51
52 void ll_set_dd(struct dentry *de)
53 {
54         ENTRY;
55         LASSERT(de != NULL);
56
57         lock_kernel();
58
59         if (de->d_fsdata == NULL) {
60                 OBD_ALLOC(de->d_fsdata, sizeof(struct ll_dentry_data));
61                 sema_init(&ll_d2d(de)->lld_it_sem, 1);
62         }
63
64         unlock_kernel();
65
66         EXIT;
67 }
68
69 void ll_intent_release(struct dentry *de, struct lookup_intent *it)
70 {
71         struct lustre_handle *handle;
72         ENTRY;
73
74         if (it->it_lock_mode) {
75                 handle = (struct lustre_handle *)it->it_lock_handle;
76                 CDEBUG(D_DLMTRACE, "releasing lock with cookie "LPX64
77                        " from it %p\n",
78                        handle->cookie, it);
79                 ldlm_lock_decref(handle, it->it_lock_mode);
80
81                 /* intent_release may be called multiple times, from
82                    this thread and we don't want to double-decref this
83                    lock (see bug 494) */
84                 it->it_lock_mode = 0;
85         }
86
87         if (!de->d_it || it->it_op == IT_RELEASED_MAGIC) {
88                 EXIT;
89                 return;
90         }
91
92         if (de->d_it == it)
93                 LL_GET_INTENT(de, it);
94         else
95                 CDEBUG(D_INODE, "STRANGE intent release: %p %p\n",
96                        de->d_it, it);
97
98         EXIT;
99 }
100
101 extern struct dentry *ll_find_alias(struct inode *, struct dentry *);
102
103 static int revalidate2_finish(int flag, struct ptlrpc_request *request,
104                               struct inode *parent, struct dentry **de,
105                               struct lookup_intent *it, int offset, obd_id ino)
106 {
107         struct ll_sb_info     *sbi = ll_i2sbi(parent);
108         struct mds_body       *body;
109         struct lov_stripe_md  *lsm = NULL;
110         struct lov_mds_md     *lmm;
111         int                    lmmsize;
112         int                    rc = 0;
113         ENTRY;
114
115         /* NB 1 request reference will be taken away by ll_intent_lock()
116          * when I return */
117
118         if ((flag & LL_LOOKUP_NEGATIVE) != 0)
119                 GOTO (out, rc = -ENOENT);
120
121         /* We only get called if the mdc_enqueue() called from
122          * ll_intent_lock() was successful.  Therefore the mds_body is
123          * present and correct, and the eadata is present (but still
124          * opaque, so only obd_unpackmd() can check the size) */
125         body = lustre_msg_buf(request->rq_repmsg, offset, sizeof (*body));
126         LASSERT (body != NULL);
127         LASSERT_REPSWABBED (request, offset);
128
129         if (body->valid & OBD_MD_FLEASIZE) {
130                 /* Only bother with this if inodes's LSM not set? */
131
132                 if (body->eadatasize == 0) {
133                         CERROR ("OBD_MD_FLEASIZE set, but eadatasize 0\n");
134                         GOTO (out, rc = -EPROTO);
135                 }
136                 lmmsize = body->eadatasize;
137                 lmm = lustre_msg_buf (request->rq_repmsg, offset + 1, lmmsize);
138                 LASSERT (lmm != NULL);
139                 LASSERT_REPSWABBED (request, offset + 1);
140
141                 rc = obd_unpackmd (&sbi->ll_osc_conn,
142                                    &lsm, lmm, lmmsize);
143                 if (rc < 0) {
144                         CERROR ("Error %d unpacking eadata\n", rc);
145                         LBUG();
146                         /* XXX don't know if I should do this... */
147                         GOTO (out, rc);
148                         /* or skip the ll_update_inode but still do
149                          * mdc_lock_set_inode() */
150                 }
151                 LASSERT (rc >= sizeof (*lsm));
152                 rc = 0;
153         }
154
155         ll_update_inode((*de)->d_inode, body, lsm);
156
157         if (lsm != NULL &&
158             ll_i2info((*de)->d_inode)->lli_smd != lsm)
159                 obd_free_memmd (&sbi->ll_osc_conn, &lsm);
160
161         ll_mdc_lock_set_inode((struct lustre_handle *)it->it_lock_handle,
162                               (*de)->d_inode);
163  out:
164         RETURN(rc);
165 }
166
167 int ll_have_md_lock(struct dentry *de)
168 {
169         struct ll_sb_info *sbi = ll_s2sbi(de->d_sb);
170         struct lustre_handle lockh;
171         struct ldlm_res_id res_id = { .name = {0} };
172         struct obd_device *obddev;
173         int flags;
174         ENTRY;
175
176         if (!de->d_inode)
177                RETURN(0);
178
179         obddev = class_conn2obd(&sbi->ll_mdc_conn);
180         res_id.name[0] = de->d_inode->i_ino;
181         res_id.name[1] = de->d_inode->i_generation;
182
183         CDEBUG(D_INFO, "trying to match res "LPU64"\n", res_id.name[0]);
184
185         flags = LDLM_FL_BLOCK_GRANTED | LDLM_FL_MATCH_DATA;
186         if (ldlm_lock_match(obddev->obd_namespace, flags, &res_id, LDLM_PLAIN,
187                             NULL, 0, LCK_PR, de->d_inode, &lockh)) {
188                 ldlm_lock_decref(&lockh, LCK_PR);
189                 RETURN(1);
190         }
191
192         if (ldlm_lock_match(obddev->obd_namespace, flags, &res_id, LDLM_PLAIN,
193                             NULL, 0, LCK_PW, de->d_inode, &lockh)) {
194                 ldlm_lock_decref(&lockh, LCK_PW);
195                 RETURN(1);
196         }
197         RETURN(0);
198 }
199
200 int ll_revalidate2(struct dentry *de, int flags, struct lookup_intent *it)
201 {
202         int rc;
203         ENTRY;
204         CDEBUG(D_VFSTRACE, "VFS Op:name=%s,intent=%s\n", de->d_name.name,
205                LL_IT2STR(it));
206
207         /* We don't want to cache negative dentries, so return 0 immediately.
208          * We believe that this is safe, that negative dentries cannot be
209          * pinned by someone else */
210         if (de->d_inode == NULL) {
211                 CDEBUG(D_INODE, "negative dentry: ret 0 to force lookup2\n");
212                 RETURN(0);
213         }
214
215         if (it == NULL || it->it_op == IT_GETATTR) {
216                 /* We could just return 1 immediately, but since we should only
217                  * be called in revalidate2 if we already have a lock, let's
218                  * verify that. */
219                 struct inode *inode = de->d_inode;
220                 struct ll_sb_info *sbi = ll_i2sbi(inode);
221                 struct obd_device *obddev = class_conn2obd(&sbi->ll_mdc_conn);
222                 struct ldlm_res_id res_id =
223                         { .name = {inode->i_ino, (__u64)inode->i_generation} };
224                 struct lustre_handle lockh;
225                 int flags;
226                 flags = LDLM_FL_BLOCK_GRANTED | LDLM_FL_MATCH_DATA;
227                 rc = ldlm_lock_match(obddev->obd_namespace, flags, &res_id,
228                                      LDLM_PLAIN, NULL, 0, LCK_PR, inode,
229                                      &lockh);
230                 if (rc) {
231                         de->d_flags &= ~DCACHE_LUSTRE_INVALID;
232                         if (it && it->it_op == IT_GETATTR) {
233                                 memcpy(it->it_lock_handle, &lockh,
234                                        sizeof(lockh));
235                                 it->it_lock_mode = LCK_PR;
236                                 LL_SAVE_INTENT(de, it);
237                         } else {
238                                 ldlm_lock_decref(&lockh, LCK_PR);
239                         }
240                         RETURN(1);
241                 }
242                 rc = ldlm_lock_match(obddev->obd_namespace, flags, &res_id,
243                                      LDLM_PLAIN, NULL, 0, LCK_PW, inode,
244                                      &lockh);
245                 if (rc) {
246                         de->d_flags &= ~DCACHE_LUSTRE_INVALID;
247                         if (it && it->it_op == IT_GETATTR) {
248                                 memcpy(it->it_lock_handle, &lockh,
249                                        sizeof(lockh));
250                                 it->it_lock_mode = LCK_PW;
251                                 LL_SAVE_INTENT(de, it);
252                         } else {
253                                 ldlm_lock_decref(&lockh, LCK_PW);
254                         }
255                         RETURN(1);
256                 }
257                 if (S_ISDIR(de->d_inode->i_mode))
258                         ll_invalidate_inode_pages(de->d_inode);
259                 d_unhash_aliases(de->d_inode);
260                 RETURN(0);
261         }
262
263         rc = ll_intent_lock(de->d_parent->d_inode, &de, it, revalidate2_finish);
264         if (rc < 0) {
265                 if (rc != -ESTALE) {
266                         CERROR("ll_intent_lock: rc %d : it->it_status %d\n", rc,
267                                it->it_status);
268                 }
269                 RETURN(0);
270         }
271         /* unfortunately ll_intent_lock may cause a callback and revoke our
272            dentry */
273         spin_lock(&dcache_lock);
274         list_del_init(&de->d_hash);
275         __d_rehash(de, 0);
276         spin_unlock(&dcache_lock);
277
278         RETURN(1);
279 }
280
281 struct dentry_operations ll_d_ops = {
282         .d_revalidate2 = ll_revalidate2,
283         .d_intent_release = ll_intent_release,
284         .d_release = ll_release,
285         .d_delete = ll_delete,
286 };