/*
 * copyright (c) 2004
 * the regents of the university of michigan
 * all rights reserved
 * 
 * permission is granted to use, copy, create derivative works and redistribute
 * this software and such derivative works for any purpose, so long as the name
 * of the university of michigan is not used in any advertising or publicity
 * pertaining to the use or distribution of this software without specific,
 * written prior authorization.  if the above copyright notice or any other
 * identification of the university of michigan is included in any copy of any
 * portion of this software, then the disclaimer below must also be included.
 * 
 * this software is provided as is, without representation from the university
 * of michigan as to its fitness for any purpose, and without warranty by the
 * university of michigan of any kind, either express or implied, including
 * without limitation the implied warranties of merchantability and fitness for
 * a particular purpose. the regents of the university of michigan shall not be
 * liable for any damages, including special, indirect, incidental, or
 * consequential damages, with respect to any claim arising out of or in
 * connection with the use of the software, even if it has been or is hereafter
 * advised of the possibility of such damages.
 */

#ifndef _NFS4M_GLUE_H
#define _NFS4M_GLUE_H


#ifndef __FreeBSD__		/* XXX - OpenBSD */

void *nfsm_dissect_xx(int, struct mbuf **, caddr_t *);
void *nfsm_build_xx(int, struct mbuf **, caddr_t *);
int nfsm_fhtom_xx(struct vnode *, int, struct mbuf **, caddr_t *);
int nfsm_postop_attr_xx(struct vnode **, int *, struct mbuf **, caddr_t *);
int nfsm_adv_xx(int, struct mbuf **, caddr_t *);
int nfsm_strtom_xx(const char *, int, int, struct mbuf **, caddr_t *);

#ifdef __APPLE__
/* XXXMARIUS: name collision */
void m_copyback_nfsx(struct mbuf *, int, int, const void *); 
#define m_copyback m_copyback_nfsx
#endif /* __APPLE__ */


#undef nfsm_build
#undef nfsm_dissect
#undef nfsm_request
#undef nfsm_request_mnt
#undef nfsm_fhtom


#undef fxdr_hyper
#define fxdr_hyper(f) \
        ((((u_quad_t)ntohl(((u_int32_t *)(f))[0])) << 32) | \
         (u_quad_t)(ntohl(((u_int32_t *)(f))[1])))
#undef txdr_hyper
#define txdr_hyper(f, t) \
do { \
        ((u_int32_t *)(t))[0] = htonl((u_int32_t)((f) >> 32)); \
        ((u_int32_t *)(t))[1] = htonl((u_int32_t)((f) & 0xffffffff)); \
} while (0)




#undef nfsm_postop_attr
#define nfsm_postop_attr(v, f) \
do { \
        int32_t t1; \
        t1 = nfsm_postop_attr_xx(&v, &f, &md, &dpos); \
        nfsm_dcheck(t1, mrep); \
} while (0)

#define nfsm_build(c, s) \
        (c)nfsm_build_xx((s), &mb, &bpos)

#define nfsm_request(v, t, p, c) \
do { \
        error = nfsx_request((v), mreq, (t), (p), (c), &mrep, &md, &dpos); \
        if (error != 0) { \
                if (error & NFSERR_RETERR) \
                        error &= ~NFSERR_RETERR; \
                else \
                        goto nfsmout; \
        } \
} while (0)

#define nfsm_request_mnt(n, t, p, c) \
do { \
        error = nfsx_request_mnt((n), mreq, (t), (p), (c), &mrep, &md, &dpos); \
        if (error != 0) { \
                if (error & NFSERR_RETERR) \
                        error &= ~NFSERR_RETERR; \
                else \
                        goto nfsmout; \
        } \
} while (0)

#define nfsm_bcheck(t1, mreq) \
do { \
        if (t1) { \
                error = t1; \
                m_freem(mreq); \
                goto nfsmout; \
        } \
} while (0)

/* Error check helpers */
#define nfsm_dcheck(t1, mrep) \
do { \
        if (t1 != 0) { \
                error = t1; \
                m_freem((mrep)); \
                (mrep) = NULL; \
                goto nfsmout; \
        } \
} while (0)


#define nfsm_dcheckp(retp, mrep) \
do { \
        if (retp == NULL) { \
                error = EBADRPC; \
                m_freem((mrep)); \
                (mrep) = NULL; \
                goto nfsmout; \
        } \
} while (0)

#undef nfsm_adv
#define nfsm_adv(s) \
do { \
        int t1; \
        t1 = nfsm_adv_xx((s), &md, &dpos); \
        nfsm_dcheck(t1, mrep); \
} while (0)

#undef nfsm_dissect
#define nfsm_dissect(c, s) \
({ \
        void *ret; \
        ret = nfsm_dissect_xx((s), &md, &dpos); \
        nfsm_dcheckp(ret, mrep); \
        (c)ret; \
})

#undef nfsm_fhtom
#define nfsm_fhtom(v, v3) \
do { \
        int32_t t1; \
        t1 = nfsm_fhtom_xx((v), (v3), &mb, &bpos); \
        nfsm_bcheck(t1, mreq); \
} while (0)

#undef nfsm_mtouio
#define nfsm_mtouio(p,s) \
do {\
        int32_t t1 = 0; \
        if ((s) > 0) \
                t1 = nfsm_mbuftouio(&md, (p), (s), &dpos); \
        nfsm_dcheck(t1, mrep); \
} while (0)


#undef nfsm_reqhead
#define	nfsm_reqhead(v,a,s) \
		(nfsm_reqh((v),(a),(s),&bpos))



	/* XXX */
/* #define nfsm_dissect(a, c, s) \ */
/*                 { t1 = mtod(md, caddr_t)+md->m_len-dpos; \ */
/*                 if (t1 >= (s)) { \ */
/*                         (a) = (c)(dpos); \ */
/*                         dpos += (s); \ */
/*                 } else if ((t1 = nfsm_disct(&md, &dpos, (s), t1, &cp2))) { \ */
/*                         error = t1; \ */
/*                         m_freem(mrep); \ */
/*                         goto nfsmout; \ */
/*                 } else { \ */
/*                         (a) = (c)cp2; \ */
/*                 } } */

/* #define nfsm_request(v, t, p, c, x)     \ */
/*                 { \ */
/*                 int nfsv3; \ */
/*                 if (!VFSTONFS((v)->v_mount)) { \ */
/*                         error = ENXIO; \ */
/*                         goto nfsmout; \ */
/*                 } \ */
/*                 nfsv3 = (VFSTONFS((v)->v_mount))->nm_flag & NFSMNT_NFSV3; \ */
/*                 if ((error = nfs_request((v), mreq, (t), (p), \ */
/*                    (c), &mrep, &md, &dpos, (x)))) { \ */
/*                         if (error & NFSERR_RETERR) \ */
/*                                 error &= ~NFSERR_RETERR; \ */
/*                         else \ */
/*                                 goto nfsmout; \ */
/*                 } \ */
/*                 } */


#endif /* ~__FreeBSD__ */


#endif /* _NFS4M_GLUE_H */
