2 * This software has been released under the terms of the IBM Public
3 * License. For details, see the LICENSE file in the top-level source
4 * directory or online at http://www.openafs.org/dl/license10.html
10 #include <afsconfig.h>
11 #include "afs/param.h"
15 /* Ugly Ugly Ugly but precludes conflicting XDR macros; We want kernel xdr */
16 #define __XDR_INCLUDE__
18 #include "afs/sysincludes.h" /* Standard vendor system headers */
19 #if defined(AFS_SUN55_ENV) && !defined(AFS_NONFSTRANS)
20 #include "rpc/types.h"
22 #include "rpc/auth_unix.h"
23 #include "rpc/auth_des.h"
24 #if !defined(AFS_SUN58_ENV)
25 #include "rpc/auth_kerb.h"
27 #include "sys/tiuser.h"
31 #include "nfs/export.h"
32 #include "nfs/nfs_clnt.h"
33 #include "nfs/nfs_acl.h"
34 #include "afs/afsincludes.h"
35 #include "afs/afs_stats.h"
36 #include "afs/exporter.h"
38 static int xlatorinit_v2_done=0;
39 static int xlatorinit_v3_done=0;
40 extern int afs_nobody;
41 extern int afs_NFSRootOnly;
45 xdrproc_t dis_xdrargs;
46 xdrproc_t dis_fastxdrargs;
49 xdrproc_t dis_fastxdrres;
51 void (*dis_resfree)();
53 fhandle_t (*dis_getfh)();
56 struct afs_nfs_disp_tbl {
60 struct afs_nfs2_resp {
67 struct afs_nfs_disp_tbl afs_rfs_disp_tbl[RFS_NPROC];
68 struct afs_nfs_disp_tbl afs_acl_disp_tbl[ACL2_NPROC];
71 is_afs_fh(fhandle_t *fhp) {
72 if ((fhp->fh_fsid.val[0] == AFS_VFSMAGIC) &&
73 (fhp->fh_fsid.val[1] == AFS_VFSFSID))
79 nfs2_to_afs_call(int which, caddr_t *args, fhandle_t **fhpp, fhandle_t **fh2pp)
86 *fh2pp = (fhandle_t *)0;
91 fhp1 = (fhandle_t *)args;
95 struct nfssaargs *sargs = (struct nfssaargs *)args;
96 fhp1 = (fhandle_t *)&sargs->saa_fh;
101 struct nfsdiropargs *sargs = (struct nfsdiropargs *)args;
102 fhp1 = (fhandle_t *)&sargs->da_fhandle;
107 struct nfsreadargs *sargs = (struct nfsreadargs *)args;
108 fhp1 = (fhandle_t *)&sargs->ra_fhandle;
113 struct nfswriteargs *sargs = (struct nfswriteargs *)args;
114 fhp1 = (fhandle_t *)&sargs->wa_fhandle;
119 struct nfscreatargs *sargs = (struct nfscreatargs *)args;
120 fhp1 = (fhandle_t *)&sargs->ca_da.da_fhandle;
125 struct nfsdiropargs *sargs = (struct nfsdiropargs *)args;
126 fhp1 = (fhandle_t *)&sargs->da_fhandle;
131 struct nfsrnmargs *sargs = (struct nfsrnmargs *)args;
132 fhp1 = (fhandle_t *)&sargs->rna_from.da_fhandle;
133 fhp2 = (fhandle_t *)&sargs->rna_to.da_fhandle;
138 struct nfslinkargs *sargs = (struct nfslinkargs *)args;
139 fhp1 = (fhandle_t *)&sargs->la_from;
140 fhp2 = (fhandle_t *)&sargs->la_to.da_fhandle;
145 struct nfsslargs *sargs = (struct nfsslargs *)args;
146 fhp1 = (fhandle_t *)&sargs->sla_from.da_fhandle;
151 struct nfscreatargs *sargs = (struct nfscreatargs *)args;
152 fhp1 = (fhandle_t *)&sargs->ca_da.da_fhandle;
157 struct nfsdiropargs *sargs = (struct nfsdiropargs *)args;
158 fhp1 = (fhandle_t *)&sargs->da_fhandle;
163 struct nfsrddirargs *sargs = (struct nfsrddirargs *)args;
164 fhp1 = (fhandle_t *)&sargs->rda_fh;
171 /* Ok if arg 1 is in AFS or if 2 args and arg 2 is in AFS */
172 if (is_afs_fh(fhp1)) {
178 if (fhp2 && is_afs_fh(fhp2)) {
187 acl2_to_afs_call(int which, caddr_t *args, fhandle_t **fhpp)
196 case ACLPROC2_GETACL:
198 struct GETACL2args *sargs = (struct GETACL2args *) args;
202 case ACLPROC2_SETACL:
204 struct SETACL2args *sargs = (struct SETACL2args *) args;
208 case ACLPROC2_GETATTR:
210 struct GETATTR2args *sargs = (struct GETATTR2args *) args;
214 case ACLPROC2_ACCESS:
216 struct ACCESS2args *sargs = (struct ACCESS2args *) args;
224 if (is_afs_fh(fhp)) {
233 afs_nfs2_dispatcher(int type, afs_int32 which, char *argp,
234 struct exportinfo **expp,
235 struct svc_req *rp, struct AFS_UCRED *crp)
239 afs_int32 client = 0;
241 fhandle_t *fh = (fhandle_t *)argp;
242 fhandle_t *fh2 = (fhandle_t *)0;
244 if (!xlatorinit_v2_done)
247 sa = (struct sockaddr *)svc_getrpccaller(rp->rq_xprt)->buf;
248 if (sa->sa_family == AF_INET)
249 client = ((struct sockaddr_in *)sa)->sin_addr.s_addr;
255 code = (client && nfs2_to_afs_call(which, argp, &fh, &fh2));
258 code = (client && acl2_to_afs_call(which, argp, &fh));
265 struct afs_exporter *out = 0;
268 struct SmallFid Sfid;
270 memcpy((char *)&Sfid, fh->fh_data, SIZEOF_SMALLFID);
272 afs_Trace2(afs_iclSetp, CM_TRACE_NFSIN1,
273 ICL_TYPE_POINTER, client,
274 ICL_TYPE_FID, &Sfid);
278 if (!once && *expp) {
279 afs_nobody = (*expp)->exi_export.ex_anon;
282 code = afs_nfsclient_reqhandler((struct afs_exporter *)0, &crp,
283 client, &dummy, &out);
297 afs_nfs2_smallfidder(struct nfsdiropres *dr)
299 register fhandle_t *fhp = (fhandle_t *)&dr->dr_fhandle;
303 #if defined(AFS_SUN57_64BIT_ENV)
304 /* See also afs_fid() */
305 memcpy((char *)addr, fhp->fh_data, SIZEOF_SMALLFID);
306 addr[1] = (addr[1] >> 48) & 0xffff;
308 memcpy((char *)addr, fhp->fh_data, 2 * sizeof(long));
312 vcp = VTOAFS((struct vnode*)addr[0]);
314 if (addr[1] == AFS_XLATOR_MAGIC)
316 if (dr->dr_status == NFS_OK) {
317 struct SmallFid Sfid;
320 /* Make up and copy out a SmallFid */
321 tcell = afs_GetCell(vcp->fid.Cell, READ_LOCK);
322 Sfid.Volume = vcp->fid.Fid.Volume;
323 Sfid.CellAndUnique = ((tcell->cellIndex << 24) |
324 (vcp->fid.Fid.Unique & 0xffffff));
325 afs_PutCell(tcell, READ_LOCK);
326 Sfid.Vnode = (u_short)(vcp->fid.Fid.Vnode & 0xffff);
327 fhp->fh_len = SIZEOF_SMALLFID;
328 memcpy(dr->dr_fhandle.fh_data, (char*)&Sfid, fhp->fh_len);
330 afs_Trace3(afs_iclSetp, CM_TRACE_NFSOUT, ICL_TYPE_INT32, 0,
331 ICL_TYPE_POINTER, vcp, ICL_TYPE_FID, &Sfid);
334 /* If we have a ref, release it */
335 if (vcp->vrefCount >= 1)
336 AFS_RELE(AFSTOV(vcp));
342 afs_nfs2_noaccess(struct afs_nfs2_resp *resp)
344 resp->status = NFSERR_ACCES;
347 void afs_nfs2_null(char *args, char *xp, char *exp, char *rp, char *crp)
352 afs_nfs2_root(char *args, char *xp, char *exp, char *rp, char *crp)
357 afs_nfs2_writecache(char *args, char *xp, char *exp, char *rp, char *crp)
361 void afs_nfs2_getattr(char *args, char *xp, char *exp, char *rp, char *crp) {
363 struct cred *svcred = curthread->t_cred;
364 curthread->t_cred = (struct cred*)crp;
365 call=afs_nfs2_dispatcher(0, RFS_GETATTR, (char *)args, &exp, rp, crp);
366 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
367 else (*afs_rfs_disp_tbl[RFS_GETATTR].orig_proc)(args, xp, exp, rp, crp);
368 curthread->t_cred = svcred;
372 void afs_nfs2_setattr(char *args, char *xp, char *exp, char *rp, char *crp) {
374 struct cred *svcred = curthread->t_cred;
375 curthread->t_cred = (struct cred*)crp;
376 call=afs_nfs2_dispatcher(0, RFS_SETATTR, (char *)args, &exp, rp, crp);
377 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
378 else (*afs_rfs_disp_tbl[RFS_SETATTR].orig_proc)(args, xp, exp, rp, crp);
379 curthread->t_cred = svcred;
383 void afs_nfs2_lookup(char *args, char *xp, char *exp, char *rp, char *crp) {
385 struct cred *svcred = curthread->t_cred;
386 curthread->t_cred = (struct cred*)crp;
387 call=afs_nfs2_dispatcher(0, RFS_LOOKUP, (char *)args, &exp, rp, crp);
388 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
389 else { (*afs_rfs_disp_tbl[RFS_LOOKUP].orig_proc)(args, xp, exp, rp, crp);
390 if (afs_NFSRootOnly && call) afs_nfs2_smallfidder(xp); }
391 curthread->t_cred = svcred;
395 void afs_nfs2_readlink(char *args, char *xp, char *exp, char *rp, char *crp) {
397 struct cred *svcred = curthread->t_cred;
398 curthread->t_cred = (struct cred*)crp;
399 call=afs_nfs2_dispatcher(0, RFS_READLINK, (char *)args, &exp, rp, crp);
400 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
401 else (*afs_rfs_disp_tbl[RFS_READLINK].orig_proc)(args, xp, exp, rp, crp);
402 curthread->t_cred = svcred;
406 void afs_nfs2_read(char *args, char *xp, char *exp, char *rp, char *crp) {
408 struct cred *svcred = curthread->t_cred;
409 curthread->t_cred = (struct cred*)crp;
410 call=afs_nfs2_dispatcher(0, RFS_READ, (char *)args, &exp, rp, crp);
411 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
412 else (*afs_rfs_disp_tbl[RFS_READ].orig_proc)(args, xp, exp, rp, crp);
413 curthread->t_cred = svcred;
417 void afs_nfs2_write(char *args, char *xp, char *exp, char *rp, char *crp) {
419 struct cred *svcred = curthread->t_cred;
420 curthread->t_cred = (struct cred*)crp;
421 call=afs_nfs2_dispatcher(0, RFS_WRITE, (char *)args, &exp, rp, crp);
422 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
423 else (*afs_rfs_disp_tbl[RFS_WRITE].orig_proc)(args, xp, exp, rp, crp);
424 curthread->t_cred = svcred;
428 void afs_nfs2_create(char *args, char *xp, char *exp, char *rp, char *crp) {
430 struct cred *svcred = curthread->t_cred;
431 curthread->t_cred = (struct cred*)crp;
432 call=afs_nfs2_dispatcher(0, RFS_CREATE, (char *)args, &exp, rp, crp);
433 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
434 else { (*afs_rfs_disp_tbl[RFS_CREATE].orig_proc)(args, xp, exp, rp, crp);
435 if (afs_NFSRootOnly && call) afs_nfs2_smallfidder(xp); }
436 curthread->t_cred = svcred;
440 void afs_nfs2_remove(char *args, char *xp, char *exp, char *rp, char *crp) {
442 struct cred *svcred = curthread->t_cred;
443 curthread->t_cred = (struct cred*)crp;
444 call=afs_nfs2_dispatcher(0, RFS_REMOVE, (char *)args, &exp, rp, crp);
445 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
446 else (*afs_rfs_disp_tbl[RFS_REMOVE].orig_proc)(args, xp, exp, rp, crp);
447 curthread->t_cred = svcred;
451 void afs_nfs2_rename(char *args, char *xp, char *exp, char *rp, char *crp) {
453 struct cred *svcred = curthread->t_cred;
454 curthread->t_cred = (struct cred*)crp;
455 call=afs_nfs2_dispatcher(0, RFS_RENAME, (char *)args, &exp, rp, crp);
456 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
457 else (*afs_rfs_disp_tbl[RFS_RENAME].orig_proc)(args, xp, exp, rp, crp);
458 curthread->t_cred = svcred;
462 void afs_nfs2_link(char *args, char *xp, char *exp, char *rp, char *crp) {
464 struct cred *svcred = curthread->t_cred;
465 curthread->t_cred = (struct cred*)crp;
466 call=afs_nfs2_dispatcher(0, RFS_LINK, (char *)args, &exp, rp, crp);
467 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
468 else (*afs_rfs_disp_tbl[RFS_LINK].orig_proc)(args, xp, exp, rp, crp);
469 curthread->t_cred = svcred;
473 void afs_nfs2_symlink(char *args, char *xp, char *exp, char *rp, char *crp) {
475 struct cred *svcred = curthread->t_cred;
476 curthread->t_cred = (struct cred*)crp;
477 call=afs_nfs2_dispatcher(0, RFS_SYMLINK, (char *)args, &exp, rp, crp);
478 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
479 else (*afs_rfs_disp_tbl[RFS_SYMLINK].orig_proc)(args, xp, exp, rp, crp);
480 curthread->t_cred = svcred;
484 void afs_nfs2_mkdir(char *args, char *xp, char *exp, char *rp, char *crp) {
486 struct cred *svcred = curthread->t_cred;
487 curthread->t_cred = (struct cred*)crp;
488 call=afs_nfs2_dispatcher(0, RFS_MKDIR, (char *)args, &exp, rp, crp);
489 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
490 else { (*afs_rfs_disp_tbl[RFS_MKDIR].orig_proc)(args, xp, exp, rp, crp);
491 if (afs_NFSRootOnly && call) afs_nfs2_smallfidder(xp); }
492 curthread->t_cred = svcred;
496 void afs_nfs2_rmdir(char *args, char *xp, char *exp, char *rp, char *crp) {
498 struct cred *svcred = curthread->t_cred;
499 curthread->t_cred = (struct cred*)crp;
500 call=afs_nfs2_dispatcher(0, RFS_RMDIR, (char *)args, &exp, rp, crp);
501 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
502 else (*afs_rfs_disp_tbl[RFS_RMDIR].orig_proc)(args, xp, exp, rp, crp);
503 curthread->t_cred = svcred;
507 void afs_nfs2_readdir(char *args, char *xp, char *exp, char *rp, char *crp) {
509 struct cred *svcred = curthread->t_cred;
510 curthread->t_cred = (struct cred*)crp;
511 call=afs_nfs2_dispatcher(0, RFS_READDIR, (char *)args, &exp, rp, crp);
512 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
513 else (*afs_rfs_disp_tbl[RFS_READDIR].orig_proc)(args, xp, exp, rp, crp);
514 curthread->t_cred = svcred;
518 void afs_nfs2_statfs(char *args, char *xp, char *exp, char *rp, char *crp) {
520 struct cred *svcred = curthread->t_cred;
521 curthread->t_cred = (struct cred*)crp;
522 call=afs_nfs2_dispatcher(0, RFS_STATFS, (char *)args, &exp, rp, crp);
523 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
524 else (*afs_rfs_disp_tbl[RFS_STATFS].orig_proc)(args, xp, exp, rp, crp);
525 curthread->t_cred = svcred;
529 struct afs_nfs_disp_tbl afs_rfs_disp_tbl[RFS_NPROC] = {
531 { afs_nfs2_getattr },
532 { afs_nfs2_setattr },
535 { afs_nfs2_readlink },
537 { afs_nfs2_writecache },
543 { afs_nfs2_symlink },
546 { afs_nfs2_readdir },
550 void afs_acl2_getacl(char *args, char *xp, char *exp, char *rp, char *crp) {
552 struct cred *svcred = curthread->t_cred;
553 curthread->t_cred = (struct cred*)crp;
554 call=afs_nfs2_dispatcher(1, ACLPROC2_GETACL, (char *)args, &exp, rp, crp);
555 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
556 else (*afs_rfs_disp_tbl[ACLPROC2_GETACL].orig_proc)(args, xp, exp, rp, crp);
557 curthread->t_cred = svcred;
561 void afs_acl2_setacl(char *args, char *xp, char *exp, char *rp, char *crp) {
563 struct cred *svcred = curthread->t_cred;
564 curthread->t_cred = (struct cred*)crp;
565 call=afs_nfs2_dispatcher(1, ACLPROC2_SETACL, (char *)args, &exp, rp, crp);
566 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
567 else (*afs_rfs_disp_tbl[ACLPROC2_SETACL].orig_proc)(args, xp, exp, rp, crp);
568 curthread->t_cred = svcred;
572 void afs_acl2_getattr(char *args, char *xp, char *exp, char *rp, char *crp) {
574 struct cred *svcred = curthread->t_cred;
575 curthread->t_cred = (struct cred*)crp;
576 call=afs_nfs2_dispatcher(1, ACLPROC2_GETATTR, (char *)args, &exp, rp, crp);
577 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
578 else (*afs_rfs_disp_tbl[ACLPROC2_GETATTR].orig_proc)(args, xp, exp, rp, crp);
579 curthread->t_cred = svcred;
583 void afs_acl2_access(char *args, char *xp, char *exp, char *rp, char *crp) {
585 struct cred *svcred = curthread->t_cred;
586 curthread->t_cred = (struct cred*)crp;
587 call=afs_nfs2_dispatcher(1, ACLPROC2_ACCESS, (char *)args, &exp, rp, crp);
588 if (call>1) afs_nfs2_noaccess((struct afs_nfs2_resp *)xp);
589 else (*afs_rfs_disp_tbl[ACLPROC2_ACCESS].orig_proc)(args, xp, exp, rp, crp);
590 curthread->t_cred = svcred;
594 struct afs_nfs_disp_tbl afs_acl_disp_tbl[5] = {
598 { afs_acl2_getattr },
602 /* Munge the dispatch tables to link us in first */
604 afs_xlatorinit_v2(struct rfs_disp_tbl *_rfs_tbl,
605 struct rfs_disp_tbl *_acl_tbl)
609 if (xlatorinit_v2_done++) return;
611 for (i=0; i < RFS_NPROC; i++) {
612 afs_rfs_disp_tbl[i].orig_proc = _rfs_tbl[i].dis_proc;
613 _rfs_tbl[i].dis_proc = afs_rfs_disp_tbl[i].afs_proc;
616 for (i=0; i < 5; i++) {
617 afs_acl_disp_tbl[i].orig_proc = _acl_tbl[i].dis_proc;
618 _acl_tbl[i].dis_proc = afs_acl_disp_tbl[i].afs_proc;
623 #define RFS3_NPROC 22
630 struct afs_nfs_disp_tbl afs_rfs3_disp_tbl[RFS3_NPROC];
631 struct afs_nfs_disp_tbl afs_acl3_disp_tbl[ACL3_NPROC];
633 struct afs_nfs3_resp {
637 typedef struct afs_nfs3_resp afs_nfs3_resp;
640 is_afs_fh3(nfs_fh3 *fhp) {
641 if ((fhp->fh3_fsid.val[0] == AFS_VFSMAGIC) &&
642 (fhp->fh3_fsid.val[1] == AFS_VFSFSID))
648 afs_nfs3_noaccess(struct afs_nfs3_resp *resp)
650 resp->status = NFS3ERR_ACCES;
655 nfs3_to_afs_call(int which, caddr_t *args, nfs_fh3 **fhpp, nfs_fh3 **fh2pp)
662 afs_Trace1(afs_iclSetp, CM_TRACE_NFS3IN, ICL_TYPE_INT32, which);
663 *fh2pp = (nfs_fh3 *)0;
665 case NFSPROC3_GETATTR:
667 GETATTR3args *arg = (GETATTR3args *)args;
668 fhp1 = (nfs_fh3 *) &arg->object;
671 case NFSPROC3_SETATTR:
673 SETATTR3args *arg = (SETATTR3args *)args;
674 fhp1 = (nfs_fh3 *) &arg->object;
677 case NFSPROC3_LOOKUP:
679 LOOKUP3args *arg = (LOOKUP3args *)args;
680 fhp1 = (nfs_fh3 *) &arg->what.dirp;
683 case NFSPROC3_ACCESS:
685 ACCESS3args *arg = (ACCESS3args *)args;
686 fhp1 = (nfs_fh3 *) &arg->object;
689 case NFSPROC3_READLINK:
691 READLINK3args *arg = (READLINK3args *)args;
692 fhp1 = (nfs_fh3 *) &arg->symlink;
697 READ3args *arg = (READ3args *)args;
698 fhp1 = (nfs_fh3 *) &arg->file;
703 WRITE3args *arg = (WRITE3args *)args;
704 fhp1 = (nfs_fh3 *) &arg->file;
707 case NFSPROC3_CREATE:
709 CREATE3args *arg = (CREATE3args *)args;
710 fhp1 = (nfs_fh3 *) &arg->where.dir;
715 MKDIR3args *arg = (MKDIR3args *)args;
716 fhp1 = (nfs_fh3 *) &arg->where.dir;
719 case NFSPROC3_SYMLINK:
721 SYMLINK3args *arg = (SYMLINK3args *)args;
722 fhp1 = (nfs_fh3 *) &arg->where.dir;
727 MKNOD3args *arg = (MKNOD3args *)args;
728 fhp1 = (nfs_fh3 *) &arg->where.dir;
731 case NFSPROC3_REMOVE:
733 REMOVE3args *arg = (REMOVE3args *)args;
734 fhp1 = (nfs_fh3 *) &arg->object.dir;
739 RMDIR3args *arg = (RMDIR3args *)args;
740 fhp1 = (nfs_fh3 *) &arg->object.dir;
743 case NFSPROC3_RENAME:
745 RENAME3args *arg = (RENAME3args *)args;
746 fhp1 = (nfs_fh3 *) &arg->from.dir;
747 fhp2 = (nfs_fh3 *) &arg->to.dir;
752 LINK3args *arg = (LINK3args *)args;
753 fhp1 = (nfs_fh3 *) &arg->file;
754 fhp2 = (nfs_fh3 *) &arg->link.dir;
757 case NFSPROC3_READDIR:
759 READDIR3args *arg = (READDIR3args *)args;
760 fhp1 = (nfs_fh3 *) &arg->dir;
763 case NFSPROC3_READDIRPLUS:
765 READDIRPLUS3args *arg = (READDIRPLUS3args *)args;
766 fhp1 = (nfs_fh3 *) &arg->dir;
769 case NFSPROC3_FSSTAT:
771 FSSTAT3args *arg = (FSSTAT3args *)args;
772 fhp1 = (nfs_fh3 *) &arg->fsroot;
775 case NFSPROC3_FSINFO:
777 FSINFO3args *arg = (FSINFO3args *)args;
778 fhp1 = (nfs_fh3 *) &arg->fsroot;
781 case NFSPROC3_PATHCONF:
783 PATHCONF3args *arg = (PATHCONF3args *)args;
784 fhp1 = (nfs_fh3 *) &arg->object;
787 case NFSPROC3_COMMIT:
789 COMMIT3args *arg = (COMMIT3args *)args;
790 fhp1 = (nfs_fh3 *) &arg->file;
797 if (is_afs_fh3(fhp1)) {
803 if (fhp2 && is_afs_fh3(fhp2)) {
812 acl3_to_afs_call(int which, caddr_t *args, nfs_fh3 **fhpp)
817 case ACLPROC3_GETACL:
819 struct GETACL3args *sargs = (struct GETACL3args *) args;
823 case ACLPROC3_SETACL:
825 struct SETACL3args *sargs = (struct SETACL3args *) args;
833 if (is_afs_fh3(fhp)) {
842 afs_nfs3_dispatcher(int type, afs_int32 which, char *argp,
843 struct exportinfo **expp,
844 struct svc_req *rp, struct AFS_UCRED *crp)
848 afs_int32 client = 0;
850 nfs_fh3 *fh = (nfs_fh3 *)argp;
851 nfs_fh3 *fh2 = (nfs_fh3 *)0;
853 if (!xlatorinit_v3_done)
856 sa = (struct sockaddr *)svc_getrpccaller(rp->rq_xprt)->buf;
857 if (sa->sa_family == AF_INET)
858 client = ((struct sockaddr_in *)sa)->sin_addr.s_addr;
864 code = (client && nfs3_to_afs_call(which, argp, &fh, &fh2));
867 code = (client && acl3_to_afs_call(which, argp, &fh));
874 struct afs_exporter *out = 0;
877 struct SmallFid Sfid;
879 memcpy((char *)&Sfid, fh->fh3_data, SIZEOF_SMALLFID);
881 afs_Trace2(afs_iclSetp, CM_TRACE_NFS3IN1,
882 ICL_TYPE_INT32, client,
883 ICL_TYPE_FID, &Sfid);
886 if (!once && *expp) {
887 afs_nobody = (*expp)->exi_export.ex_anon;
890 code = afs_nfsclient_reqhandler((struct afs_exporter *)0, &crp,
891 client, &dummy, &out);
906 afs_nfs3_smallfidder(struct nfs_fh3 *fhp, int status)
911 #if defined(AFS_SUN57_64BIT_ENV)
912 /* See also afs_fid() */
913 memcpy((char *)addr, fhp->fh3_data, 10);
914 addr[1] = (addr[1] >> 48) & 0xffff;
916 memcpy((char *)addr, fhp->fh3_data, 2 * sizeof(long));
920 vcp = VTOAFS((struct vnode*)addr[0]);
922 /* See also afs_osi_vget */
923 if (addr[1] == AFS_XLATOR_MAGIC)
925 if (status == NFS_OK) {
926 struct SmallFid Sfid;
929 /* Make up and copy out a SmallFid */
930 tcell = afs_GetCell(vcp->fid.Cell, READ_LOCK);
931 Sfid.Volume = vcp->fid.Fid.Volume;
932 Sfid.CellAndUnique = ((tcell->cellIndex << 24) |
933 (vcp->fid.Fid.Unique & 0xffffff));
934 afs_PutCell(tcell, READ_LOCK);
935 Sfid.Vnode = (u_short)(vcp->fid.Fid.Vnode & 0xffff);
936 fhp->fh3_len = SIZEOF_SMALLFID;
937 memcpy(fhp->fh3_data, (char*)&Sfid, fhp->fh3_len);
939 afs_Trace3(afs_iclSetp, CM_TRACE_NFS3OUT, ICL_TYPE_INT32, status,
940 ICL_TYPE_POINTER, vcp, ICL_TYPE_FID, &Sfid);
943 /* If we have a ref, release it */
944 if (vcp->vrefCount >= 1)
945 AFS_RELE(AFSTOV(vcp));
950 void afs_nfs3_getattr(char *args, char *xp, char *exp, char *rp, char *crp) {
953 struct cred *svcred = curthread->t_cred;
954 curthread->t_cred = (struct cred*)crp;
955 call=afs_nfs3_dispatcher(0, NFSPROC3_GETATTR, (char *)args, &exp, rp, crp);
956 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
957 else (*afs_rfs3_disp_tbl[NFSPROC3_GETATTR].orig_proc)(args, xp, exp, rp, crp);
958 curthread->t_cred = svcred;
962 void afs_nfs3_setattr(char *args, char *xp, char *exp, char *rp, char *crp) {
965 struct cred *svcred = curthread->t_cred;
966 curthread->t_cred = (struct cred*)crp;
967 call=afs_nfs3_dispatcher(0, NFSPROC3_SETATTR, (char *)args, &exp, rp, crp);
968 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
969 else (*afs_rfs3_disp_tbl[NFSPROC3_SETATTR].orig_proc)(args, xp, exp, rp, crp);
970 curthread->t_cred = svcred;
974 void afs_nfs3_lookup(char *args, char *xp, char *exp, char *rp, char *crp) {
977 struct cred *svcred = curthread->t_cred;
978 curthread->t_cred = (struct cred*)crp;
979 call=afs_nfs3_dispatcher(0, NFSPROC3_LOOKUP, (char *)args, &exp, rp, crp);
980 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
981 else { (*afs_rfs3_disp_tbl[NFSPROC3_LOOKUP].orig_proc)(args, xp, exp, rp, crp);
982 if (afs_NFSRootOnly && call) {
983 LOOKUP3res *resp = ( LOOKUP3res *)xp;
984 afs_nfs3_smallfidder( &resp->resok.object , resp->status); } }
985 curthread->t_cred = svcred;
989 void afs_nfs3_access(char *args, char *xp, char *exp, char *rp, char *crp) {
992 struct cred *svcred = curthread->t_cred;
993 curthread->t_cred = (struct cred*)crp;
994 call=afs_nfs3_dispatcher(0, NFSPROC3_ACCESS, (char *)args, &exp, rp, crp);
995 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
996 else (*afs_rfs3_disp_tbl[NFSPROC3_ACCESS].orig_proc)(args, xp, exp, rp, crp);
997 curthread->t_cred = svcred;
1001 void afs_nfs3_readlink(char *args, char *xp, char *exp, char *rp, char *crp) {
1003 afs_nfs3_resp dummy;
1004 struct cred *svcred = curthread->t_cred;
1005 curthread->t_cred = (struct cred*)crp;
1006 call=afs_nfs3_dispatcher(0, NFSPROC3_READLINK, (char *)args, &exp, rp, crp);
1007 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1008 else (*afs_rfs3_disp_tbl[NFSPROC3_READLINK].orig_proc)(args, xp, exp, rp, crp);
1009 curthread->t_cred = svcred;
1013 void afs_nfs3_read(char *args, char *xp, char *exp, char *rp, char *crp) {
1015 afs_nfs3_resp dummy;
1016 struct cred *svcred = curthread->t_cred;
1017 curthread->t_cred = (struct cred*)crp;
1018 call=afs_nfs3_dispatcher(0, NFSPROC3_READ, (char *)args, &exp, rp, crp);
1019 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1020 else (*afs_rfs3_disp_tbl[NFSPROC3_READ].orig_proc)(args, xp, exp, rp, crp);
1021 curthread->t_cred = svcred;
1025 void afs_nfs3_write(char *args, char *xp, char *exp, char *rp, char *crp) {
1027 afs_nfs3_resp dummy;
1028 struct cred *svcred = curthread->t_cred;
1029 curthread->t_cred = (struct cred*)crp;
1030 call=afs_nfs3_dispatcher(0, NFSPROC3_WRITE, (char *)args, &exp, rp, crp);
1031 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1032 else (*afs_rfs3_disp_tbl[NFSPROC3_WRITE].orig_proc)(args, xp, exp, rp, crp);
1033 curthread->t_cred = svcred;
1036 void afs_nfs3_create(char *args, char *xp, char *exp, char *rp, char *crp) {
1038 afs_nfs3_resp dummy;
1039 struct cred *svcred = curthread->t_cred;
1040 curthread->t_cred = (struct cred*)crp;
1041 call=afs_nfs3_dispatcher(0, NFSPROC3_CREATE, (char *)args, &exp, rp, crp);
1042 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1043 else { (*afs_rfs3_disp_tbl[NFSPROC3_CREATE].orig_proc)(args, xp, exp, rp, crp);
1044 if (afs_NFSRootOnly && call) {
1045 CREATE3res *resp = ( CREATE3res *)xp;
1046 afs_nfs3_smallfidder( &resp->resok.obj.handle , resp->status); } }
1047 curthread->t_cred = svcred;
1051 void afs_nfs3_mkdir(char *args, char *xp, char *exp, char *rp, char *crp) {
1053 afs_nfs3_resp dummy;
1054 struct cred *svcred = curthread->t_cred;
1055 curthread->t_cred = (struct cred*)crp;
1056 call=afs_nfs3_dispatcher(0, NFSPROC3_MKDIR, (char *)args, &exp, rp, crp);
1057 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1058 else { (*afs_rfs3_disp_tbl[NFSPROC3_MKDIR].orig_proc)(args, xp, exp, rp, crp);
1059 if (afs_NFSRootOnly && call) {
1060 MKDIR3res *resp = ( MKDIR3res *)xp;
1061 afs_nfs3_smallfidder( &resp->resok.obj.handle , resp->status); } }
1062 curthread->t_cred = svcred;
1066 void afs_nfs3_symlink(char *args, char *xp, char *exp, char *rp, char *crp) {
1068 afs_nfs3_resp dummy;
1069 struct cred *svcred = curthread->t_cred;
1070 curthread->t_cred = (struct cred*)crp;
1071 call=afs_nfs3_dispatcher(0, NFSPROC3_SYMLINK, (char *)args, &exp, rp, crp);
1072 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1073 else { (*afs_rfs3_disp_tbl[NFSPROC3_SYMLINK].orig_proc)(args, xp, exp, rp, crp);
1074 if (afs_NFSRootOnly && call) {
1075 SYMLINK3res *resp = ( SYMLINK3res *)xp;
1076 afs_nfs3_smallfidder( &resp->resok.obj.handle , resp->status); } }
1077 curthread->t_cred = svcred;
1081 void afs_nfs3_mknod(char *args, char *xp, char *exp, char *rp, char *crp) {
1083 afs_nfs3_resp dummy;
1084 struct cred *svcred = curthread->t_cred;
1085 curthread->t_cred = (struct cred*)crp;
1086 call=afs_nfs3_dispatcher(0, NFSPROC3_MKNOD, (char *)args, &exp, rp, crp);
1087 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1088 else { (*afs_rfs3_disp_tbl[NFSPROC3_MKNOD].orig_proc)(args, xp, exp, rp, crp);
1089 if (afs_NFSRootOnly && call) {
1090 MKNOD3res *resp = ( MKNOD3res *)xp;
1091 afs_nfs3_smallfidder( &resp->resok.obj.handle , resp->status); } }
1092 curthread->t_cred = svcred;
1096 void afs_nfs3_remove(char *args, char *xp, char *exp, char *rp, char *crp) {
1098 afs_nfs3_resp dummy;
1099 struct cred *svcred = curthread->t_cred;
1100 curthread->t_cred = (struct cred*)crp;
1101 call=afs_nfs3_dispatcher(0, NFSPROC3_REMOVE, (char *)args, &exp, rp, crp);
1102 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1103 else (*afs_rfs3_disp_tbl[NFSPROC3_REMOVE].orig_proc)(args, xp, exp, rp, crp);
1104 curthread->t_cred = svcred;
1108 void afs_nfs3_rmdir(char *args, char *xp, char *exp, char *rp, char *crp) {
1110 afs_nfs3_resp dummy;
1111 struct cred *svcred = curthread->t_cred;
1112 curthread->t_cred = (struct cred*)crp;
1113 call=afs_nfs3_dispatcher(0, NFSPROC3_RMDIR, (char *)args, &exp, rp, crp);
1114 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1115 else (*afs_rfs3_disp_tbl[NFSPROC3_RMDIR].orig_proc)(args, xp, exp, rp, crp);
1116 curthread->t_cred = svcred;
1120 void afs_nfs3_rename(char *args, char *xp, char *exp, char *rp, char *crp) {
1122 afs_nfs3_resp dummy;
1123 struct cred *svcred = curthread->t_cred;
1124 curthread->t_cred = (struct cred*)crp;
1125 call=afs_nfs3_dispatcher(0, NFSPROC3_RENAME, (char *)args, &exp, rp, crp);
1126 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1127 else (*afs_rfs3_disp_tbl[NFSPROC3_RENAME].orig_proc)(args, xp, exp, rp, crp);
1128 curthread->t_cred = svcred;
1132 void afs_nfs3_link(char *args, char *xp, char *exp, char *rp, char *crp) {
1134 afs_nfs3_resp dummy;
1135 struct cred *svcred = curthread->t_cred;
1136 curthread->t_cred = (struct cred*)crp;
1137 call=afs_nfs3_dispatcher(0, NFSPROC3_LINK, (char *)args, &exp, rp, crp);
1138 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1139 else (*afs_rfs3_disp_tbl[NFSPROC3_LINK].orig_proc)(args, xp, exp, rp, crp);
1140 curthread->t_cred = svcred;
1144 void afs_nfs3_readdir(char *args, char *xp, char *exp, char *rp, char *crp) {
1146 afs_nfs3_resp dummy;
1147 struct cred *svcred = curthread->t_cred;
1148 curthread->t_cred = (struct cred*)crp;
1149 call=afs_nfs3_dispatcher(0, NFSPROC3_READDIR, (char *)args, &exp, rp, crp);
1150 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1151 else (*afs_rfs3_disp_tbl[NFSPROC3_READDIR].orig_proc)(args, xp, exp, rp, crp);
1152 curthread->t_cred = svcred;
1156 void afs_nfs3_readdirplus(char *args, char *xp, char *exp, char *rp, char *crp) {
1158 afs_nfs3_resp dummy;
1159 struct cred *svcred = curthread->t_cred;
1160 curthread->t_cred = (struct cred*)crp;
1161 call=afs_nfs3_dispatcher(0, NFSPROC3_READDIRPLUS, (char *)args, &exp, rp, crp);
1162 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1163 else (*afs_rfs3_disp_tbl[NFSPROC3_READDIRPLUS].orig_proc)(args, xp, exp, rp, crp);
1164 curthread->t_cred = svcred;
1168 void afs_nfs3_fsstat(char *args, char *xp, char *exp, char *rp, char *crp) {
1170 afs_nfs3_resp dummy;
1171 struct cred *svcred = curthread->t_cred;
1172 curthread->t_cred = (struct cred*)crp;
1173 call=afs_nfs3_dispatcher(0, NFSPROC3_FSSTAT, (char *)args, &exp, rp, crp);
1174 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1175 else (*afs_rfs3_disp_tbl[NFSPROC3_FSSTAT].orig_proc)(args, xp, exp, rp, crp);
1176 curthread->t_cred = svcred;
1180 void afs_nfs3_fsinfo(char *args, char *xp, char *exp, char *rp, char *crp) {
1182 afs_nfs3_resp dummy;
1183 struct cred *svcred = curthread->t_cred;
1184 curthread->t_cred = (struct cred*)crp;
1185 call=afs_nfs3_dispatcher(0, NFSPROC3_FSINFO, (char *)args, &exp, rp, crp);
1186 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1187 else (*afs_rfs3_disp_tbl[NFSPROC3_FSINFO].orig_proc)(args, xp, exp, rp, crp);
1188 curthread->t_cred = svcred;
1192 void afs_nfs3_pathconf(char *args, char *xp, char *exp, char *rp, char *crp) {
1194 afs_nfs3_resp dummy;
1195 struct cred *svcred = curthread->t_cred;
1196 curthread->t_cred = (struct cred*)crp;
1197 call=afs_nfs3_dispatcher(0, NFSPROC3_PATHCONF, (char *)args, &exp, rp, crp);
1198 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1199 else (*afs_rfs3_disp_tbl[NFSPROC3_PATHCONF].orig_proc)(args, xp, exp, rp, crp);
1200 curthread->t_cred = svcred;
1204 void afs_nfs3_commit(char *args, char *xp, char *exp, char *rp, char *crp) {
1206 afs_nfs3_resp dummy;
1207 struct cred *svcred = curthread->t_cred;
1208 curthread->t_cred = (struct cred*)crp;
1209 call=afs_nfs3_dispatcher(0, NFSPROC3_COMMIT, (char *)args, &exp, rp, crp);
1210 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1211 else (*afs_rfs3_disp_tbl[NFSPROC3_COMMIT].orig_proc)(args, xp, exp, rp, crp);
1212 curthread->t_cred = svcred;
1216 struct afs_nfs_disp_tbl afs_rfs3_disp_tbl[22] = {
1218 { afs_nfs3_getattr },
1219 { afs_nfs3_setattr },
1220 { afs_nfs3_lookup },
1221 { afs_nfs3_access },
1222 { afs_nfs3_readlink },
1225 { afs_nfs3_create },
1227 { afs_nfs3_symlink },
1229 { afs_nfs3_remove },
1231 { afs_nfs3_rename },
1233 { afs_nfs3_readdir },
1234 { afs_nfs3_readdirplus },
1235 { afs_nfs3_fsstat },
1236 { afs_nfs3_fsinfo },
1237 { afs_nfs3_pathconf },
1241 void afs_acl3_getacl(char *args, char *xp, char *exp, char *rp, char *crp) {
1243 struct cred *svcred = curthread->t_cred;
1244 curthread->t_cred = (struct cred*)crp;
1245 call=afs_nfs3_dispatcher(1, ACLPROC3_GETACL, (char *)args, &exp, rp, crp);
1246 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1247 else (*afs_rfs3_disp_tbl[ACLPROC3_GETACL].orig_proc)(args, xp, exp, rp, crp);
1248 curthread->t_cred = svcred;
1252 void afs_acl3_setacl(char *args, char *xp, char *exp, char *rp, char *crp) {
1254 struct cred *svcred = curthread->t_cred;
1255 curthread->t_cred = (struct cred*)crp;
1256 call=afs_nfs3_dispatcher(1, ACLPROC3_SETACL, (char *)args, &exp, rp, crp);
1257 if (call>1) afs_nfs3_noaccess((struct afs_nfs3_resp *)xp);
1258 else (*afs_rfs3_disp_tbl[ACLPROC3_SETACL].orig_proc)(args, xp, exp, rp, crp);
1259 curthread->t_cred = svcred;
1263 struct afs_nfs_disp_tbl afs_acl3_disp_tbl[3] = {
1265 { afs_acl3_getacl },
1266 { afs_acl3_setacl },
1269 /* Munge the dispatch tables to link us in first */
1271 afs_xlatorinit_v3(struct rfs_disp_tbl *_rfs_tbl,
1272 struct rfs_disp_tbl *_acl_tbl)
1276 if (xlatorinit_v3_done++) return;
1278 for (i=0; i < 22; i++) {
1279 afs_rfs3_disp_tbl[i].orig_proc = _rfs_tbl[i].dis_proc;
1280 _rfs_tbl[i].dis_proc = afs_rfs3_disp_tbl[i].afs_proc;
1283 for (i=0; i < 3; i++) {
1284 afs_acl3_disp_tbl[i].orig_proc = _acl_tbl[i].dis_proc;
1285 _acl_tbl[i].dis_proc = afs_acl3_disp_tbl[i].afs_proc;
1288 #endif /* !defined(AFS_NONFSTRANS) */