#ifndef SYS_MBUF_H
#define SYS_MBUF_H

/*
 * Copyright (c) 1982, 1986, 1988 Regents of the University of California.
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms are permitted
 * provided that the above copyright notice and this paragraph are
 * duplicated in all such forms and that any documentation,
 * advertising materials, and other materials related to such
 * distribution and use acknowledge that the software was developed
 * by the University of California, Berkeley.  The name of the
 * University may not be used to endorse or promote products derived
 * from this software without specific prior written permission.
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 *
 *	@(#)mbuf.h      7.8.1.3 (Berkeley) 2/14/89
 */

/*
 * Constants related to memory allocator.
 */
#define MSIZE		512			/* size of an mbuf */
#define MMINOFF 	12			/* mbuf header length */
#define MTAIL		4
#define MMAXOFF 	(MSIZE-MTAIL)           /* offset where data ends */
#define MLEN		(MSIZE-MMINOFF-MTAIL)   /* mbuf data length */

/*
 * Macros for type conversion
 */

/* address in mbuf to mbuf head */
#define dtom(x)         ((struct mbuf *)((long)x & ~(MSIZE-1)))

/* mbuf head, to typed data */
#define mtod(x,t)       ((t)((long)(x) + (x)->m_off))

struct mbuf {
	struct	mbuf *m_next;		/* next buffer in chain */
	u_long	m_off;			/* offset of data */
	short	m_len;			/* amount of data in this mbuf */
	short	m_type; 		/* mbuf type (0 == free) */
	u_char	m_dat[MLEN];		/* data storage */
	struct	mbuf *m_act;		/* link in higher-level mbuf list */
};

/* mbuf types */
#define MT_FREE 	0	/* should be on free list */
#define MT_DATA 	1	/* dynamic (data) allocation */
#define MT_HEADER	2	/* packet header */
#define MT_SOCKET	3	/* socket structure */
#define MT_PCB		4	/* protocol control block */
#define MT_RTABLE	5	/* routing tables */
#define MT_HTABLE	6	/* IMP host tables */
#define MT_ATABLE	7	/* address resolution tables */
#define MT_SONAME	8	/* socket name */
#define MT_ZOMBIE	9	/* zombie proc status */
#define MT_SOOPTS	10	/* socket options */
#define MT_FTABLE	11	/* fragment reassembly header */
#define MT_RIGHTS	12	/* access rights */
#define MT_IFADDR	13	/* interface address */

/* flags to m_get */
#define M_DONTWAIT	0
#define M_WAIT		1

/* flags to m_pgalloc */
#define MPG_MBUFS	0		/* put new mbufs on free list */
#define MPG_SPACE	2		/* don't free; caller wants space */

/* length to m_copy to copy all */
#define M_COPYALL	1000000000

/*
 * m_pullup will pull up additional length if convenient;
 * should be enough to hold headers of second-level and higher protocols.
 */
#define MPULL_EXTRA	32

/*
 * Original MGET/MFREE were macros that fudged inline proc expansion.  We
 * call m_get/m_free to save quite a lot of space.
 */
#define MGET(m, i, t) (m) = m_get(i, t);
#define MFREE(m, n) (n) = m_free(m);

/*
 * Mbuf statistics.
 */
struct mbstat {
	u_long	m_mbufs;	/* mbufs obtained from page pool */
	u_long	m_clusters;	/* clusters obtained from page pool */
	u_long	m_space;	/* interface pages obtained from page pool */
	u_long	m_clfree;	/* free clusters */
	u_long	m_drops;	/* times failed to find space */
	u_long	m_wait; 	/* times waited for space */
	u_long	m_drain;	/* times drained protocols for space */
	u_short m_mtypes[32];	/* type specific mbuf allocations */
};

#ifdef	KERNEL
#if 0
extern struct mbstat mbstat;
extern struct mbuf *mfree, *mclfree;
extern int m_want;
struct  mbuf *m_get(),*m_getclr(),*m_free(),*m_more(),*m_copy(),*m_pullup();
caddr_t m_clalloc();
#endif
#endif

#endif
