Whamcloud - gitweb
8900ec75d03291a570e200b98dc5727821744b20
[fs/lustre-release.git] / lnet / lnet / lib-me.c
1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2  * vim:expandtab:shiftwidth=8:tabstop=8:
3  *
4  * GPL HEADER START
5  *
6  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
7  *
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.
11  *
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).
17  *
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
21  *
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
24  * have any questions.
25  *
26  * GPL HEADER END
27  */
28 /*
29  * Copyright  2008 Sun Microsystems, Inc. All rights reserved
30  * Use is subject to license terms.
31  */
32 /*
33  * This file is part of Lustre, http://www.lustre.org/
34  * Lustre is a trademark of Sun Microsystems, Inc.
35  *
36  * lnet/lnet/lib-me.c
37  *
38  * Match Entry management routines
39  */
40
41 #define DEBUG_SUBSYSTEM S_LNET
42
43 #include <lnet/lib-lnet.h>
44
45 int
46 LNetMEAttach(unsigned int portal,
47              lnet_process_id_t match_id,
48              __u64 match_bits, __u64 ignore_bits,
49              lnet_unlink_t unlink, lnet_ins_pos_t pos,
50              lnet_handle_me_t *handle)
51 {
52         lnet_me_t     *me;
53
54         LASSERT (the_lnet.ln_init);
55         LASSERT (the_lnet.ln_refcount > 0);
56
57         if ((int)portal >= the_lnet.ln_nportals)
58                 return -EINVAL;
59
60         me = lnet_me_alloc();
61         if (me == NULL)
62                 return -ENOMEM;
63
64         LNET_LOCK();
65
66         me->me_portal = portal;
67         me->me_match_id = match_id;
68         me->me_match_bits = match_bits;
69         me->me_ignore_bits = ignore_bits;
70         me->me_unlink = unlink;
71         me->me_md = NULL;
72
73         lnet_initialise_handle (&me->me_lh, LNET_COOKIE_TYPE_ME);
74
75         if (pos == LNET_INS_AFTER)
76                 cfs_list_add_tail(&me->me_list,
77                                   &(the_lnet.ln_portals[portal].ptl_ml));
78         else
79                 cfs_list_add(&me->me_list,
80                              &(the_lnet.ln_portals[portal].ptl_ml));
81
82         lnet_me2handle(handle, me);
83
84         LNET_UNLOCK();
85
86         return 0;
87 }
88
89 int
90 LNetMEInsert(lnet_handle_me_t current_meh,
91              lnet_process_id_t match_id,
92              __u64 match_bits, __u64 ignore_bits,
93              lnet_unlink_t unlink, lnet_ins_pos_t pos,
94              lnet_handle_me_t *handle)
95 {
96         lnet_me_t     *current_me;
97         lnet_me_t     *new_me;
98
99         LASSERT (the_lnet.ln_init);
100         LASSERT (the_lnet.ln_refcount > 0);
101
102         new_me = lnet_me_alloc();
103         if (new_me == NULL)
104                 return -ENOMEM;
105
106         LNET_LOCK();
107
108         current_me = lnet_handle2me(&current_meh);
109         if (current_me == NULL) {
110                 lnet_me_free (new_me);
111
112                 LNET_UNLOCK();
113                 return -ENOENT;
114         }
115
116         new_me->me_portal = current_me->me_portal;
117         new_me->me_match_id = match_id;
118         new_me->me_match_bits = match_bits;
119         new_me->me_ignore_bits = ignore_bits;
120         new_me->me_unlink = unlink;
121         new_me->me_md = NULL;
122
123         lnet_initialise_handle (&new_me->me_lh, LNET_COOKIE_TYPE_ME);
124
125         if (pos == LNET_INS_AFTER)
126                 cfs_list_add(&new_me->me_list, &current_me->me_list);
127         else
128                 cfs_list_add_tail(&new_me->me_list, &current_me->me_list);
129
130         lnet_me2handle(handle, new_me);
131
132         LNET_UNLOCK();
133
134         return 0;
135 }
136
137 int
138 LNetMEUnlink(lnet_handle_me_t meh)
139 {
140         lnet_me_t    *me;
141         lnet_libmd_t *md;
142         lnet_event_t  ev;
143
144         LASSERT (the_lnet.ln_init);
145         LASSERT (the_lnet.ln_refcount > 0);
146
147         LNET_LOCK();
148
149         me = lnet_handle2me(&meh);
150         if (me == NULL) {
151                 LNET_UNLOCK();
152                 return -ENOENT;
153         }
154
155         md = me->me_md;
156         if (md != NULL &&
157             md->md_eq != NULL &&
158             md->md_refcount == 0) {
159                 lnet_build_unlink_event(md, &ev);
160                 lnet_enq_event_locked(md->md_eq, &ev);
161         }
162
163         lnet_me_unlink(me);
164
165         LNET_UNLOCK();
166         return 0;
167 }
168
169 /* call with LNET_LOCK please */
170 void
171 lnet_me_unlink(lnet_me_t *me)
172 {
173         cfs_list_del (&me->me_list);
174
175         if (me->me_md != NULL) {
176                 me->me_md->md_me = NULL;
177                 lnet_md_unlink(me->me_md);
178         }
179
180         lnet_invalidate_handle (&me->me_lh);
181         lnet_me_free(me);
182 }
183
184 #if 0
185 static void
186 lib_me_dump(lnet_me_t *me)
187 {
188         CWARN("Match Entry %p ("LPX64")\n", me,
189               me->me_lh.lh_cookie);
190
191         CWARN("\tMatch/Ignore\t= %016lx / %016lx\n",
192               me->me_match_bits, me->me_ignore_bits);
193
194         CWARN("\tMD\t= %p\n", me->md);
195         CWARN("\tprev\t= %p\n",
196               cfs_list_entry(me->me_list.prev, lnet_me_t, me_list));
197         CWARN("\tnext\t= %p\n",
198               cfs_list_entry(me->me_list.next, lnet_me_t, me_list));
199 }
200 #endif