quota update partial NTGetUserQuota support
[obnox/wireshark/wip.git] / packet-nlm.c
1 /* packet-nlm.c
2  * Routines for nlm dissection
3  *
4  * $Id: packet-nlm.c,v 1.23 2002/01/24 09:20:50 guy Exp $
5  *
6  * Ethereal - Network traffic analyzer
7  * By Gerald Combs <gerald@ethereal.com>
8  * Copyright 1998 Gerald Combs
9  *
10  * Copied from packet-mount.c
11  *
12  * 2001-JAN  Ronnie Sahlberg <See AUTHORS for email>
13  *  Updates to version 1 of the protocol.
14  *  Added version 3 of the protocol.
15  *  Added version 4 of the protocol.
16  *
17  *
18  * This program is free software; you can redistribute it and/or
19  * modify it under the terms of the GNU General Public License
20  * as published by the Free Software Foundation; either version 2
21  * of the License, or (at your option) any later version.
22  *
23  * This program is distributed in the hope that it will be useful,
24  * but WITHOUT ANY WARRANTY; without even the implied warranty of
25  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
26  * GNU General Public License for more details.
27  *
28  * You should have received a copy of the GNU General Public License
29  * along with this program; if not, write to the Free Software
30  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
31  */
32
33
34 #ifdef HAVE_CONFIG_H
35 #include "config.h"
36 #endif
37
38
39 #ifdef HAVE_SYS_TYPES_H
40 #include <sys/types.h>
41 #endif
42
43
44 #include "packet-rpc.h"
45 #include "packet-nfs.h"
46 #include "packet-nlm.h"
47
48 /*
49  * NFS Lock Manager protocol specs can only be found in actual
50  * implementations or in the nice book:
51  * Brent Callaghan: "NFS Illustrated", Addison-Wesley, ISBN 0-201-32570-5
52  * which I use here as reference (BC).
53  *
54  * They can also be found if you go to
55  *
56  *      http://www.opengroup.org/publications/catalog/c702.htm
57  *
58  * and follow the links to the HTML version of the document.
59  */
60
61 static int proto_nlm = -1;
62
63 static int hf_nlm_cookie = -1;
64 static int hf_nlm_block = -1;
65 static int hf_nlm_exclusive = -1;
66 static int hf_nlm_lock = -1;
67 static int hf_nlm_lock_caller_name = -1;
68 static int hf_nlm_lock_owner = -1;
69 static int hf_nlm_lock_svid = -1;
70 static int hf_nlm_lock_l_offset = -1;
71 static int hf_nlm_lock_l_offset64 = -1;
72 static int hf_nlm_lock_l_len = -1;
73 static int hf_nlm_lock_l_len64 = -1;
74 static int hf_nlm_reclaim = -1;
75 static int hf_nlm_stat = -1;
76 static int hf_nlm_state = -1;
77 static int hf_nlm_test_stat = -1;
78 static int hf_nlm_test_stat_stat = -1;
79 static int hf_nlm_holder = -1;
80 static int hf_nlm_share = -1;
81 static int hf_nlm_share_mode = -1;
82 static int hf_nlm_share_access = -1;
83 static int hf_nlm_share_name = -1;
84 static int hf_nlm_sequence = -1;
85
86 static gint ett_nlm = -1;
87 static gint ett_nlm_lock = -1;
88
89
90 const value_string names_nlm_stats[] =
91 {
92         /* NLM_GRANTED is the function number 5 and the state code 0.
93          * So we use for the state the postfix _S.
94          */
95 #define NLM_GRANTED_S           0
96                 {       NLM_GRANTED_S,  "NLM_GRANTED"   },
97 #define NLM_DENIED              1
98                 {       NLM_DENIED,     "NLM_DENIED"    },
99 #define NLM_DENIED_NOLOCKS      2
100                 {       NLM_DENIED_NOLOCKS,     "NLM_DENIED_NOLOCKS"    },
101 #define NLM_BLOCKED             3
102                 {       NLM_BLOCKED,    "NLM_BLOCKED"           },
103 #define NLM_DENIED_GRACE_PERIOD 4
104                 {       NLM_DENIED_GRACE_PERIOD,        "NLM_DENIED_GRACE_PERIOD"       },
105 #define NLM_DEADLCK             5
106                 {       NLM_DEADLCK,    "NLM_DEADLCK"   },
107 #define NLM_ROFS                6
108                 {       NLM_ROFS,       "NLM_ROFS"      },
109 #define NLM_STALE_FH            7
110                 {       NLM_STALE_FH,   "NLM_STALE_FH"  },
111 #define NLM_BIG                 8
112                 {       NLM_BIG,        "NLM_BIG"       },
113 #define NLM_FAILED              9
114                 {       NLM_FAILED,     "NLM_FAILED"    },
115                 {       0,              NULL            }
116 };
117
118
119 const value_string names_fsh_mode[] =
120 {
121 #define FSM_DN  0
122                 {       FSM_DN,         "deny none"     },
123 #define FSM_DR  1
124                 {       FSM_DR,         "deny read"     },
125 #define FSM_DW  2
126                 {       FSM_DW,         "deny write"    },
127 #define FSM_DRW 3
128                 {       FSM_DRW,        "deny read/write"       },
129
130                 {       0,              NULL    }
131 };
132
133
134 const value_string names_fsh_access[] =
135 {
136 #define FSA_NONE        0
137                 {       FSA_NONE,       "no access"     },
138 #define FSA_R   1
139                 {       FSA_R,          "read-only"     },
140 #define FSA_W   2
141                 {       FSA_W,          "write-only"    },
142 #define FSA_RW  3
143                 {       FSA_RW,         "read/write"    },
144                 {       0,              NULL    }
145 };
146
147
148
149
150
151
152 /* **************************** */
153 /* generic dissecting functions */
154 /* **************************** */
155 static int
156 dissect_lock(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int version, int offset)
157 {
158         proto_item* lock_item = NULL;
159         proto_tree* lock_tree = NULL;
160
161         if (tree) {
162                 lock_item = proto_tree_add_item(tree, hf_nlm_lock, tvb,
163                                 offset, -1, FALSE);
164                 if (lock_item)
165                         lock_tree = proto_item_add_subtree(lock_item, ett_nlm_lock);
166         }
167
168         offset = dissect_rpc_string(tvb,pinfo,lock_tree,
169                         hf_nlm_lock_caller_name, offset, NULL);
170         offset = dissect_nfs_fh3(tvb, offset, pinfo, lock_tree,"fh");
171
172         offset = dissect_rpc_data(tvb, pinfo, lock_tree, hf_nlm_lock_owner, offset);
173
174         offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_lock_svid, offset);
175
176         if (version == 4) {
177                 offset = dissect_rpc_uint64(tvb, pinfo, lock_tree, hf_nlm_lock_l_offset64, offset);
178                 offset = dissect_rpc_uint64(tvb, pinfo, lock_tree, hf_nlm_lock_l_len64, offset);
179         }
180         else {
181                 offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_lock_l_offset, offset);
182                 offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_lock_l_len, offset);
183         }
184
185         return offset;
186 }
187
188
189 static int
190 dissect_nlm_test(tvbuff_t *tvb, int offset, packet_info *pinfo,
191     proto_tree *tree, int version)
192 {
193         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
194         dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_exclusive, offset);
195         offset += 4;
196         offset = dissect_lock(tvb, pinfo, tree, version, offset);
197         return offset;
198 }
199
200 static int
201 dissect_nlm_lock(tvbuff_t *tvb, int offset, packet_info *pinfo,
202     proto_tree *tree,int version)
203 {
204         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
205         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_block, offset);
206         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_exclusive, offset);
207         offset = dissect_lock(tvb, pinfo, tree, version, offset);
208         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_reclaim, offset);
209         offset = dissect_rpc_uint32(tvb, pinfo, tree, hf_nlm_state, offset);
210         return offset;
211 }
212
213 static int
214 dissect_nlm_cancel(tvbuff_t *tvb, int offset, packet_info *pinfo,
215     proto_tree *tree,int version)
216 {
217         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
218         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_block, offset);
219         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_exclusive, offset);
220         offset = dissect_lock(tvb, pinfo, tree, version, offset);
221         return offset;
222 }
223
224 static int
225 dissect_nlm_unlock(tvbuff_t *tvb, int offset, packet_info *pinfo,
226     proto_tree *tree,int version)
227 {
228         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
229         offset = dissect_lock(tvb, pinfo, tree, version, offset);
230         return offset;
231 }
232
233 static int
234 dissect_nlm_granted(tvbuff_t *tvb, int offset, packet_info *pinfo,
235     proto_tree *tree,int version)
236 {
237         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
238         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_exclusive, offset);
239         offset = dissect_lock(tvb, pinfo, tree, version, offset);
240         return offset;
241 }
242
243
244 static int
245 dissect_nlm_test_res(tvbuff_t *tvb, int offset, packet_info *pinfo,
246     proto_tree *tree,int version)
247 {
248         proto_item* lock_item = NULL;
249         proto_tree* lock_tree = NULL;
250
251         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
252
253         if (tree) {
254                 lock_item = proto_tree_add_item(tree, hf_nlm_test_stat, tvb,
255                                 offset, -1, FALSE);
256                 if (lock_item)
257                         lock_tree = proto_item_add_subtree(lock_item, 
258                                 ett_nlm_lock);
259         }
260
261         offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_test_stat_stat,
262             offset);
263
264         /* last structure is optional, only supplied for stat==1 (LOCKED) */
265         if(tvb_reported_length_remaining(tvb, offset) == 0){
266                 return offset;
267         }
268
269         if (tree) {
270                 lock_item = proto_tree_add_item(lock_tree, hf_nlm_holder, tvb,
271                                 offset, -1, FALSE);
272                 if (lock_item)
273                         lock_tree = proto_item_add_subtree(lock_item, 
274                                 ett_nlm_lock);
275         }
276
277         offset = dissect_rpc_bool(tvb, pinfo, lock_tree, hf_nlm_exclusive,
278             offset);
279         offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_lock_svid,
280             offset);
281         offset = dissect_rpc_data(tvb, pinfo, lock_tree, hf_nlm_lock_owner,
282             offset);
283
284         if (version == 4) {
285                 offset = dissect_rpc_uint64(tvb, pinfo, lock_tree,
286                     hf_nlm_lock_l_offset64, offset);
287                 offset = dissect_rpc_uint64(tvb, pinfo, lock_tree,
288                     hf_nlm_lock_l_len64, offset);
289         }
290         else {
291                 offset = dissect_rpc_uint32(tvb, pinfo, lock_tree,
292                     hf_nlm_lock_l_offset, offset);
293                 offset = dissect_rpc_uint32(tvb, pinfo, lock_tree,
294                     hf_nlm_lock_l_len, offset);
295         }
296
297         return offset;
298 }
299
300
301 static int
302 dissect_nlm_share(tvbuff_t *tvb, int offset, packet_info *pinfo,
303     proto_tree *tree,int version)
304 {
305         proto_item* lock_item = NULL;
306         proto_tree* lock_tree = NULL;
307
308         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
309
310         if (tree) {
311                 lock_item = proto_tree_add_item(tree, hf_nlm_share, tvb,
312                                 offset, -1, FALSE);
313                 if (lock_item)
314                         lock_tree = proto_item_add_subtree(lock_item, 
315                                 ett_nlm_lock);
316         }
317
318         offset = dissect_rpc_string(tvb,pinfo,lock_tree,
319                         hf_nlm_lock_caller_name, offset, NULL);
320         
321         offset = dissect_nfs_fh3(tvb, offset, pinfo, lock_tree, "fh");
322
323         offset = dissect_rpc_data(tvb, pinfo, lock_tree, hf_nlm_lock_owner, offset);
324
325         offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_share_mode, offset);
326         offset = dissect_rpc_uint32(tvb, pinfo, lock_tree, hf_nlm_share_access, offset);
327
328
329         offset = dissect_rpc_bool(tvb, pinfo, tree, hf_nlm_reclaim, offset);
330         return offset;
331 }
332
333 static int
334 dissect_nlm_shareres(tvbuff_t *tvb, int offset, packet_info *pinfo,
335     proto_tree *tree, int version)
336 {
337         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
338         offset = dissect_rpc_uint32(tvb, pinfo, tree, hf_nlm_stat, offset);
339         offset = dissect_rpc_uint32(tvb, pinfo, tree, hf_nlm_sequence, offset);
340         return offset;
341 }
342
343 static int
344 dissect_nlm_freeall(tvbuff_t *tvb, int offset, packet_info *pinfo,
345     proto_tree *tree,int version)
346 {
347         offset = dissect_rpc_string(tvb,pinfo,tree,
348                         hf_nlm_share_name, offset, NULL);
349
350         offset = dissect_rpc_uint32(tvb, pinfo, tree, hf_nlm_stat, offset);
351
352         return offset;
353 }
354
355
356 /* RPC functions */
357
358
359 /* This function is identical for all NLM protocol versions (1-4)*/
360 static int
361 dissect_nlm_gen_reply(tvbuff_t *tvb, int offset, packet_info *pinfo,
362     proto_tree *tree)
363 {
364         offset = dissect_rpc_data(tvb, pinfo, tree, hf_nlm_cookie, offset);
365         offset = dissect_rpc_uint32(tvb, pinfo, tree, hf_nlm_stat, offset);
366         return offset;
367 }
368
369 static int
370 dissect_nlm1_test(tvbuff_t *tvb, int offset, packet_info *pinfo,
371     proto_tree *tree)
372 {
373         return dissect_nlm_test(tvb,offset,pinfo,tree,1);
374 }
375
376 static int
377 dissect_nlm4_test(tvbuff_t *tvb, int offset, packet_info *pinfo,
378     proto_tree *tree)
379 {
380         return dissect_nlm_test(tvb,offset,pinfo,tree,4);
381 }
382
383
384 static int
385 dissect_nlm1_lock(tvbuff_t *tvb, int offset, packet_info *pinfo,
386     proto_tree *tree)
387 {
388         return dissect_nlm_lock(tvb,offset,pinfo,tree,1);
389 }
390
391 static int
392 dissect_nlm4_lock(tvbuff_t *tvb, int offset, packet_info *pinfo,
393     proto_tree *tree)
394 {
395         return dissect_nlm_lock(tvb,offset,pinfo,tree,4);
396 }
397
398
399 static int
400 dissect_nlm1_cancel(tvbuff_t *tvb, int offset, packet_info *pinfo,
401     proto_tree *tree)
402 {
403         return dissect_nlm_cancel(tvb,offset,pinfo,tree,1);
404 }
405
406 static int
407 dissect_nlm4_cancel(tvbuff_t *tvb, int offset, packet_info *pinfo,
408     proto_tree *tree)
409 {
410         return dissect_nlm_cancel(tvb,offset,pinfo,tree,4);
411 }
412
413
414 static int
415 dissect_nlm1_unlock(tvbuff_t *tvb, int offset, packet_info *pinfo,
416     proto_tree *tree)
417 {
418         return dissect_nlm_unlock(tvb,offset,pinfo,tree,1);
419 }
420
421 static int
422 dissect_nlm4_unlock(tvbuff_t *tvb, int offset, packet_info *pinfo,
423     proto_tree *tree)
424 {
425         return dissect_nlm_unlock(tvb,offset,pinfo,tree,4);
426 }
427
428
429 static int
430 dissect_nlm1_granted(tvbuff_t *tvb, int offset, packet_info *pinfo,
431     proto_tree *tree)
432 {
433         return dissect_nlm_granted(tvb,offset,pinfo,tree,1);
434 }
435
436 static int
437 dissect_nlm4_granted(tvbuff_t *tvb, int offset, packet_info *pinfo,
438     proto_tree *tree)
439 {
440         return dissect_nlm_granted(tvb,offset,pinfo,tree,4);
441 }
442
443
444 static int
445 dissect_nlm1_test_res(tvbuff_t *tvb, int offset, packet_info *pinfo,
446     proto_tree *tree)
447 {
448         return dissect_nlm_test_res(tvb,offset,pinfo,tree,1);
449 }
450
451 static int
452 dissect_nlm4_test_res(tvbuff_t *tvb, int offset, packet_info *pinfo,
453     proto_tree *tree)
454 {
455         return dissect_nlm_test_res(tvb,offset,pinfo,tree,4);
456 }
457
458 static int
459 dissect_nlm3_share(tvbuff_t *tvb, int offset, packet_info *pinfo,
460     proto_tree *tree)
461 {
462         return dissect_nlm_share(tvb,offset,pinfo,tree,3);
463 }
464
465 static int
466 dissect_nlm4_share(tvbuff_t *tvb, int offset, packet_info *pinfo,
467     proto_tree *tree)
468 {
469         return dissect_nlm_share(tvb,offset,pinfo,tree,4);
470 }
471
472 static int
473 dissect_nlm3_shareres(tvbuff_t *tvb, int offset, packet_info *pinfo,
474     proto_tree *tree)
475 {
476         return dissect_nlm_shareres(tvb,offset,pinfo,tree,3);
477 }
478
479 static int
480 dissect_nlm4_shareres(tvbuff_t *tvb, int offset, packet_info *pinfo,
481     proto_tree *tree)
482 {
483         return dissect_nlm_shareres(tvb,offset,pinfo,tree,4);
484 }
485
486 static int
487 dissect_nlm3_freeall(tvbuff_t *tvb, int offset, packet_info *pinfo,
488     proto_tree *tree)
489 {
490         return dissect_nlm_freeall(tvb,offset,pinfo,tree,3);
491 }
492
493 static int
494 dissect_nlm4_freeall(tvbuff_t *tvb, int offset, packet_info *pinfo,
495     proto_tree *tree)
496 {
497         return dissect_nlm_freeall(tvb,offset,pinfo,tree,4);
498 }
499
500
501
502
503 /* proc number, "proc name", dissect_request, dissect_reply */
504 /* NULL as function pointer means: type of arguments is "void". */
505 /* NLM protocol version 1 */
506 static const vsff nlm1_proc[] = {
507         { NLM_NULL,             "NULL",         
508                 NULL,                           NULL },
509         { NLM_TEST,             "TEST",
510                 dissect_nlm1_test,              dissect_nlm1_test_res },
511         { NLM_LOCK,             "LOCK", 
512                 dissect_nlm1_lock,              dissect_nlm_gen_reply },
513         { NLM_CANCEL,           "CANCEL",
514                 dissect_nlm1_cancel,            dissect_nlm_gen_reply },
515         { NLM_UNLOCK,           "UNLOCK",
516                 dissect_nlm1_unlock,            dissect_nlm_gen_reply },
517         { NLM_GRANTED,          "GRANTED",
518                 dissect_nlm1_granted,           dissect_nlm_gen_reply },
519         { NLM_TEST_MSG,         "TEST_MSG",
520                 dissect_nlm1_test,              NULL },
521         { NLM_LOCK_MSG,         "LOCK_MSG",
522                 dissect_nlm1_lock,              NULL },
523         { NLM_CANCEL_MSG,       "CANCEL_MSG",
524                 dissect_nlm1_cancel,            NULL },
525         { NLM_UNLOCK_MSG,       "UNLOCK_MSG",   
526                 dissect_nlm1_unlock,            NULL },
527         { NLM_GRANTED_MSG,      "GRANTED_MSG",
528                 dissect_nlm1_granted,           NULL },
529         { NLM_TEST_RES,         "TEST_RES",
530                 dissect_nlm1_test_res,          NULL },
531         { NLM_LOCK_RES,         "LOCK_RES",     
532                 dissect_nlm_gen_reply,          NULL },
533         { NLM_CANCEL_RES,       "CANCEL_RES",   
534                 dissect_nlm_gen_reply,          NULL },
535         { NLM_UNLOCK_RES,       "UNLOCK_RES",   
536                 dissect_nlm_gen_reply,          NULL },
537         { NLM_GRANTED_RES,      "GRANTED_RES",  
538                 dissect_nlm_gen_reply,          NULL },
539         { 0,                    NULL,
540                 NULL,                           NULL }
541 };
542 /* end of NLM protocol version 1 */
543
544 /* NLM protocol version 2 */
545 static const vsff nlm2_proc[] = {
546         { NLM_NULL,             "NULL",         
547                 NULL,                           NULL },
548         { NLM_TEST,             "TEST",
549                 dissect_nlm1_test,              dissect_nlm1_test_res },
550         { NLM_LOCK,             "LOCK", 
551                 dissect_nlm1_lock,              dissect_nlm_gen_reply },
552         { NLM_CANCEL,           "CANCEL",
553                 dissect_nlm1_cancel,            dissect_nlm_gen_reply },
554         { NLM_UNLOCK,           "UNLOCK",
555                 dissect_nlm1_unlock,            dissect_nlm_gen_reply },
556         { NLM_GRANTED,          "GRANTED",
557                 dissect_nlm1_granted,           dissect_nlm_gen_reply },
558         { NLM_TEST_MSG,         "TEST_MSG",
559                 dissect_nlm1_test,              NULL },
560         { NLM_LOCK_MSG,         "LOCK_MSG",
561                 dissect_nlm1_lock,              NULL },
562         { NLM_CANCEL_MSG,       "CANCEL_MSG",
563                 dissect_nlm1_cancel,            NULL },
564         { NLM_UNLOCK_MSG,       "UNLOCK_MSG",   
565                 dissect_nlm1_unlock,            NULL },
566         { NLM_GRANTED_MSG,      "GRANTED_MSG",
567                 dissect_nlm1_granted,           NULL },
568         { NLM_TEST_RES,         "TEST_RES",
569                 dissect_nlm1_test_res,          NULL },
570         { NLM_LOCK_RES,         "LOCK_RES",     
571                 dissect_nlm_gen_reply,          NULL },
572         { NLM_CANCEL_RES,       "CANCEL_RES",   
573                 dissect_nlm_gen_reply,          NULL },
574         { NLM_UNLOCK_RES,       "UNLOCK_RES",   
575                 dissect_nlm_gen_reply,          NULL },
576         { NLM_GRANTED_RES,      "GRANTED_RES",  
577                 dissect_nlm_gen_reply,          NULL },
578         { 0,                    NULL,
579                 NULL,                           NULL }
580 };
581 /* end of NLM protocol version 2 */
582
583 /* NLM protocol version 3 */
584 static const vsff nlm3_proc[] = {
585         { NLM_NULL,             "NULL",         
586                 NULL,                           NULL },
587         { NLM_TEST,             "TEST",
588                 dissect_nlm1_test,              dissect_nlm1_test_res },
589         { NLM_LOCK,             "LOCK", 
590                 dissect_nlm1_lock,              dissect_nlm_gen_reply },
591         { NLM_CANCEL,           "CANCEL",
592                 dissect_nlm1_cancel,            dissect_nlm_gen_reply },
593         { NLM_UNLOCK,           "UNLOCK",
594                 dissect_nlm1_unlock,            dissect_nlm_gen_reply },
595         { NLM_GRANTED,          "GRANTED",
596                 dissect_nlm1_granted,           dissect_nlm_gen_reply },
597         { NLM_TEST_MSG,         "TEST_MSG",
598                 dissect_nlm1_test,              NULL },
599         { NLM_LOCK_MSG,         "LOCK_MSG",
600                 dissect_nlm1_lock,              NULL },
601         { NLM_CANCEL_MSG,       "CANCEL_MSG",
602                 dissect_nlm1_cancel,            NULL },
603         { NLM_UNLOCK_MSG,       "UNLOCK_MSG",   
604                 dissect_nlm1_unlock,            NULL },
605         { NLM_GRANTED_MSG,      "GRANTED_MSG",
606                 dissect_nlm1_granted,           NULL },
607         { NLM_TEST_RES,         "TEST_RES",
608                 dissect_nlm1_test_res,          NULL },
609         { NLM_LOCK_RES,         "LOCK_RES",     
610                 dissect_nlm_gen_reply,          NULL },
611         { NLM_CANCEL_RES,       "CANCEL_RES",   
612                 dissect_nlm_gen_reply,          NULL },
613         { NLM_UNLOCK_RES,       "UNLOCK_RES",   
614                 dissect_nlm_gen_reply,          NULL },
615         { NLM_GRANTED_RES,      "GRANTED_RES",  
616                 dissect_nlm_gen_reply,          NULL },
617         { NLM_SHARE,            "SHARE",        
618                 dissect_nlm3_share,             dissect_nlm3_shareres },
619         { NLM_UNSHARE,          "UNSHARE",      
620                 dissect_nlm3_share,             dissect_nlm3_shareres },
621         { NLM_NM_LOCK,          "NM_LOCK",      
622                 dissect_nlm1_lock,              dissect_nlm_gen_reply },
623         { NLM_FREE_ALL,         "FREE_ALL",     
624                 dissect_nlm3_freeall,           NULL },
625         { 0,                    NULL,
626                 NULL,                           NULL }
627 };
628 /* end of NLM protocol version 3 */
629
630
631 /* NLM protocol version 4 */
632 static const vsff nlm4_proc[] = {
633         { NLM_NULL,             "NULL",         
634                 NULL,                           NULL },
635         { NLM_TEST,             "TEST",         
636                 dissect_nlm4_test,              dissect_nlm4_test_res },
637         { NLM_LOCK,             "LOCK",         
638                 dissect_nlm4_lock,              dissect_nlm_gen_reply },
639         { NLM_CANCEL,           "CANCEL",       
640                 dissect_nlm4_cancel,            dissect_nlm_gen_reply },
641         { NLM_UNLOCK,           "UNLOCK",       
642                 dissect_nlm4_unlock,            dissect_nlm_gen_reply },
643         { NLM_GRANTED,          "GRANTED",      
644                 dissect_nlm4_granted,           dissect_nlm_gen_reply },
645         { NLM_TEST_MSG,         "TEST_MSG",     
646                 dissect_nlm4_test,              NULL },
647         { NLM_LOCK_MSG,         "LOCK_MSG",     
648                 dissect_nlm4_lock,              NULL },
649         { NLM_CANCEL_MSG,       "CANCEL_MSG",   
650                 dissect_nlm4_cancel,            NULL },
651         { NLM_UNLOCK_MSG,       "UNLOCK_MSG",   
652                 dissect_nlm4_unlock,            NULL },
653         { NLM_GRANTED_MSG,      "GRANTED_MSG",  
654                 dissect_nlm4_granted,           NULL },
655         { NLM_TEST_RES,         "TEST_RES",
656                 dissect_nlm4_test_res,          NULL },
657         { NLM_LOCK_RES,         "LOCK_RES",     
658                 dissect_nlm_gen_reply,          NULL },
659         { NLM_CANCEL_RES,       "CANCEL_RES",   
660                 dissect_nlm_gen_reply,          NULL },
661         { NLM_UNLOCK_RES,       "UNLOCK_RES",   
662                 dissect_nlm_gen_reply,          NULL },
663         { NLM_GRANTED_RES,      "GRANTED_RES",  
664                 dissect_nlm_gen_reply,          NULL },
665         { NLM_SHARE,            "SHARE",
666                 dissect_nlm4_share,             dissect_nlm4_shareres },
667         { NLM_UNSHARE,          "UNSHARE",
668                 dissect_nlm4_share,             dissect_nlm4_shareres },
669         { NLM_NM_LOCK,          "NM_LOCK",      
670                 dissect_nlm4_lock,              dissect_nlm_gen_reply },
671         { NLM_FREE_ALL,         "FREE_ALL",
672                 dissect_nlm4_freeall,           NULL },
673         { 0,                    NULL,
674                 NULL,                           NULL }
675 };
676 /* end of NLM protocol version 4 */
677
678
679 static struct true_false_string yesno = { "Yes", "No" };
680
681
682 void
683 proto_register_nlm(void)
684 {
685         static hf_register_info hf[] = {
686                 { &hf_nlm_cookie, {
687                         "cookie", "nlm.cookie", FT_BYTES, BASE_DEC,
688                         NULL, 0, "cookie", HFILL }},
689                 { &hf_nlm_block, {
690                         "block", "nlm.block", FT_BOOLEAN, BASE_NONE,
691                         &yesno, 0, "block", HFILL }},
692                 { &hf_nlm_exclusive, {
693                         "exclusive", "nlm.exclusive", FT_BOOLEAN, BASE_NONE,
694                         &yesno, 0, "exclusive", HFILL }},
695                 { &hf_nlm_lock, {
696                         "lock", "nlm.lock", FT_NONE, 0,
697                         NULL, 0, "lock", HFILL }},
698                 { &hf_nlm_lock_caller_name, {
699                         "caller_name", "nlm.lock.caller_name", FT_STRING, BASE_NONE,
700                         NULL, 0, "caller_name", HFILL }},
701                 { &hf_nlm_lock_owner, {
702                         "owner", "nlm.lock.owner", FT_BYTES, BASE_DEC,
703                         NULL, 0, "owner", HFILL }},
704                 { &hf_nlm_lock_svid, {
705                         "svid", "nlm.lock.svid", FT_UINT32, BASE_DEC,
706                         NULL, 0, "svid", HFILL }},
707                 { &hf_nlm_lock_l_offset64, {
708                         "l_offset", "nlm.lock.l_offset", FT_UINT64, BASE_DEC,
709                         NULL, 0, "l_offset", HFILL }},
710                 { &hf_nlm_lock_l_offset, {
711                         "l_offset", "nlm.lock.l_offset", FT_UINT32, BASE_DEC,
712                         NULL, 0, "l_offset", HFILL }},
713                 { &hf_nlm_lock_l_len64, {
714                         "l_len", "nlm.lock.l_len", FT_UINT64, BASE_DEC,
715                         NULL, 0, "l_len", HFILL }},
716                 { &hf_nlm_lock_l_len, {
717                         "l_len", "nlm.lock.l_len", FT_UINT32, BASE_DEC,
718                         NULL, 0, "l_len", HFILL }},
719                 { &hf_nlm_reclaim, {
720                         "reclaim", "nlm.reclaim", FT_BOOLEAN, BASE_NONE,
721                         &yesno, 0, "reclaim", HFILL }},
722                 { &hf_nlm_state, {
723                         "state", "nlm.state", FT_UINT32, BASE_DEC,
724                         NULL, 0, "STATD state", HFILL }},
725                 { &hf_nlm_stat, {
726                         "stat", "nlm.stat", FT_UINT32, BASE_DEC,
727                         VALS(names_nlm_stats), 0, "stat", HFILL }},
728                 { &hf_nlm_test_stat, {
729                         "test_stat", "nlm.test_stat", FT_NONE, 0,
730                         NULL, 0, "test_stat", HFILL }},
731                 { &hf_nlm_test_stat_stat, {
732                         "stat", "nlm.test_stat.stat", FT_UINT32, BASE_DEC,
733                         VALS(names_nlm_stats), 0, "stat", HFILL }},
734                 { &hf_nlm_holder, {
735                         "holder", "nlm.holder", FT_NONE, 0,
736                         NULL, 0, "holder", HFILL }},
737                 { &hf_nlm_share, {
738                         "share", "nlm.share", FT_NONE, 0,
739                         NULL, 0, "share", HFILL }},
740                 { &hf_nlm_share_mode, {
741                         "mode", "nlm.share.mode", FT_UINT32, BASE_DEC,
742                         VALS(names_fsh_mode), 0, "mode", HFILL }},
743                 { &hf_nlm_share_access, {
744                         "access", "nlm.share.access", FT_UINT32, BASE_DEC,
745                         VALS(names_fsh_access), 0, "access", HFILL }},
746                 { &hf_nlm_share_name, {
747                         "name", "nlm.share.name", FT_STRING, BASE_NONE,
748                         NULL, 0, "name", HFILL }},
749                 { &hf_nlm_sequence, {
750                         "sequence", "nlm.sequence", FT_INT32, BASE_DEC,
751                         NULL, 0, "sequence", HFILL }},
752                 };
753
754         static gint *ett[] = {
755                 &ett_nlm,
756                 &ett_nlm_lock,
757         };
758
759         proto_nlm = proto_register_protocol("Network Lock Manager Protocol",
760             "NLM", "nlm");
761         proto_register_field_array(proto_nlm, hf, array_length(hf));
762         proto_register_subtree_array(ett, array_length(ett));
763 }
764
765 void
766 proto_reg_handoff_nlm(void)
767 {
768         /* Register the protocol as RPC */
769         rpc_init_prog(proto_nlm, NLM_PROGRAM, ett_nlm);
770         /* Register the procedure tables */
771         rpc_init_proc_table(NLM_PROGRAM, 1, nlm1_proc);
772         rpc_init_proc_table(NLM_PROGRAM, 2, nlm2_proc);
773         rpc_init_proc_table(NLM_PROGRAM, 3, nlm3_proc);
774         rpc_init_proc_table(NLM_PROGRAM, 4, nlm4_proc);
775 }