/*
 * @DEC_COPYRIGHT@
 */
/*
 * HISTORY
 * $Log:	dli_var.h,v $
 * Revision 4.3.3.3  92/06/01  16:12:57  Benjamin_England
 * 	increase space reserved for DLI socket
 * 	add new dli_multi_op_fp for passing mcast addr info to NETMAN
 * 	change dli_portid to caddr_t from int to avoid pointer-int conversions
 * 	[92/05/20  09:21:15  Benjamin_England]
 * 
 * 	fix important 802.3 bug found by Matt Thomas
 * 	[92/05/18  14:38:25  Benjamin_England]
 * 
 * 	finish synching with DECnet-ULTRIX DLI
 * 	[92/05/14  09:03:40  Benjamin_England]
 * 
 * Revision 4.3.3.2  92/03/26  15:28:49  Benjamin_England
 * 	"DECnet/DLI hooks"
 * 
 * Revision 4.3.2.3  92/03/26  15:02:18  Benjamin_England
 * 	did merge with NEW
 * 
 * Revision 4.3.2.2  92/03/26  09:53:41  Benjamin_England
 * 	fix set problem
 * 
 * Revision 4.3.1.4  92/03/20  10:37:50  Benjamin_England
 * 	add additional function pointer to minimize DECnet-OSI specific code
 * 
 * Revision 4.3.1.3  92/03/18  17:09:02  Benjamin_England
 * 	get rid of dli_ifop and related structures, base system DLI doesn't
 * 	need to know about this.
 * 
 * Revision 4.3.1.2  92/03/16  18:03:06  Benjamin_England
 * 	Synchronize DECnet-OSI DLI with OSF/Silver DLI
 * 	add support for FDDI, token ring
 * 	permit base system DLI to utilize DECnet-OSI network management if present
 * 	get DLI-private data structures out of dli_var.h
 * 
 * Revision 4.3  91/11/26  11:09:29  devbld_zk3
 * 	Baselevel AG_BL0
 * 
 * Revision 4.2.2.2  91/11/05  10:33:40  William_Burns
 * 	Merge from ODE/TIN: revision 3.1.9.2
 * 	date: 91/10/24 16:29:00;  author: devrcs;  state: Exp;  lines added/del: 4/1
 * 	sccs rev: 3.2;  orig date: 91/10/10 14:07:54;  orig author: thomas
 * 	Fix outstanding QARs.
 * 	Add FDDI support
 * 	Fix sysid generation
 * 	Fix ethernet loopback.
 * 	Fix 802 packet parsing.
 * 	[91/10/29  10:20:07  William_Burns]
 * 
 * Revision 4.2  91/09/19  23:29:53  devbld
 * 	Adding ODE Headers
 * 
 * $EndLog$
 */
/*
 *		@(#)$RCSfile: dli_var.h,v $ $Revision: 4.3.3.3 $ (DEC) $Date: 92/06/01 16:12:57 $
 *
 *   COPYRIGHT (c) DIGITAL EQUIPMENT CORPORATION 1991.  ALL
 *   RIGHTS RESERVED.
 *
 *   THIS  SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY BE
 *   USED  AND  COPIED ONLY IN ACCORDANCE WITH THE TERMS OF
 *   SUCH  LICENSE  AND  WITH  THE  INCLUSION  OF THE ABOVE
 *   COPYRIGHT  NOTICE.   THIS SOFTWARE OR ANY OTHER COPIES
 *   THEREOF   MAY   NOT  BE  PROVIDED  OR  OTHERWISE  MADE
 *   AVAILABLE  TO  ANY  OTHER  PERSON.   NO  TITLE  TO AND
 *   OWNERSHIP OF THE SOFTWARE IS HEREBY TRANSFERRED.
 *
 *   THE  INFORMATION IN THIS SOFTWARE IS SUBJECT TO CHANGE
 *   WITHOUT  NOTICE  AND  SHOULD  NOT  BE  CONSTRUED  AS A
 *   COMMITMENT BY DIGITAL EQUIPMENT CORPORATION.
 *
 *   DIGITAL  ASSUMES  NO  RESPONSIBILITY  FOR  THE  USE OR
 *   RELIABILITY  OF  ITS SOFTWARE ON EQUIPMENT THAT IS NOT
 *   SUPPLIED BY DIGITAL.
 *
 *
 *   Telecommunications & Networks
 *
 *   EDIT HISTORY
 *
 *
 * 2.00 18-Apr-1986
 *      DECnet-ULTRIX, Created.
 *	DECnet-Ultrix	V2.0
 *
 * Added sysid and point-to-point support
 *
 * 2.01 18-Mar-1988
 *      DECnet-ULTRIX   V2.4
 *		- Allowed use of reserved bit in individual and group SAPs
 *
 *	21-Sep-1989	Matt Thomas
 *		- Added more definitions in preparition for DECnet/OSI.
 */

/* Data Structures and Literals applicable to DLI */

/*
 * Socket queue literals
 */
#define DLI_SENDSPACE 5000
#define DLI_RECVSPACE 10000


/*
 * DLI socket literals
 */
#define DLPROTO_DLI	0		/* user interface protocol number */

/*
 * DLI i/o control flag literals
 */
#define DLI_EXCLUSIVE	001		/* exclusive use of protocol */
#define DLI_NORMAL	002		/* prot/mcast filtering */
#define DLI_DEFAULT	004		/* unmatched packets go here */

/*
 * DLI literals corresponding to the following address structures
 * and/or frame types.
 */
#define	DLI_ETHERNET	0		/* sockaddr_edl format */
#define	DLI_POINTOPOINT	1		/* sockaddr_pdl format */
#define	DLI_802		2		/* sockaddr_802 format */
#define	DLI_LOOP	3		/* loop module format */
#define	DLI_HDLC	4		/* hdlc frame format */

#define DLI_EADDRSIZE	6		/* Ethernet address size */
#define DLI_DEVSIZE	16		/* device name size */

/*
*  802 support
*/

#define	ENOTFND		-1
#define	USER		(u_char)0	/* user supplied service */
#define	TYPE1		(u_char)1	/* class 1 service */
#define	OSI802		0X5DC		/* max value of 802 len field */
#define	VSAP		(u_char)0x01	/* mask for indiv/group sap bit */
#define SNAP_SAP	(u_char)0xAA
#define	NULL_SAP	(u_char)0x00
#define	GLOBAL_SAP	(u_char)0xFF
#define	XID		(u_char)0xAF	/* xid command w/out poll bit set */
#define	TEST		(u_char)0xE3	/* test command w/out poll bit set */
#define	XID_PCMD	(u_char)0xBF	/* xid command w/poll bit set */
#define	XID_NPCMD	(u_char)0xAF	/* xid command w/out poll bit set */
#define	XID_PRSP	(u_char)0xBF	/* xid response w/poll bit set */
#define	XID_NPRSP	(u_char)0xAF	/* xid response w/out poll bit set */
#define	TEST_PCMD	(u_char)0xF3	/* test command w/poll bit set */
#define	TEST_NPCMD	(u_char)0xE3	/* test command w/out poll bit set */
#define	TEST_PRSP	(u_char)0xF3	/* test response w/poll bit set */
#define	TEST_NPRSP	(u_char)0xE3	/* test response w/out poll bit set */
#define	UI_NPCMD	(u_char)0x03	/* unnumbered info cmd w/out poll bit */
#define LLC_FMT(c)	(((c) & 1) ? (((c) & 2) ? LLC_U_FMT : LLC_S_FMT) : LLC_I_FMT)
#define LLC_U_FMT	0x03		/* unnumbered commands and responses */
#define LLC_I_FMT	0x00		/* informational commands and responses */
#define LLC_S_FMT	0x01		/* supervisory commands and responses */
#define LLC_ISGSAP(s)	((s) & 1)
#define LLC_SAPIDX(s)	((s) >> 1)
#define LLC_SETSAP(s, t)  ((t)[(s) >> 4] |=  (1 << (LLC_SAPIDX(s) & 7)))
#define LLC_CLRSAP(s, t)  ((t)[(s) >> 4] &= ~(1 << (LLC_SAPIDX(s) & 7)))
#define LLC_TSTSAP(s, t) (((t)[(s) >> 4] &   (1 << (LLC_SAPIDX(s) & 7))) != 0)
#define LLC_TOGSAP(s)	(((s) << 1) | 1)
#define	MAX802DATANP	3		/* maximum user data without proto id */
#define	MAX802DATAP	8		/* maximum user data with proto id field */
#ifndef NISAPS
#define	NISAPS		128		/* also in <netinet/if_ether.h> */
#endif
#define	NGSAPS		NISAPS

struct osi_802hdr {
    u_char dst[DLI_EADDRSIZE];	/* where packet is going */
    u_char src[DLI_EADDRSIZE];	/* who packet is for (usually this node)*/
    u_short len;		/* length of user data plus 802.3 header */
    u_char dsap;		/* what dst sap the packet is going to */
    u_char ssap;		/* source individual sap */
    union {
	u_short U_fmt;		/* unnumbered format */
	u_short I_S_fmt;	/* information/supervisory format */
    } ctl;
    u_char osi_pi[5];		/* 802.3 protocol id */
    u_char priority;		/* 802.5/FDDI FC priority */
};

/*
 * address structures used by DLI
 */
struct dli_devid {
    u_char dli_devname[DLI_DEVSIZE+1];	/* device name */
    u_short dli_devnumber;		/* device number */
};

struct sockaddr_edl {
    u_char dli_ioctlflg;		/* i/o control flags */
    u_char dli_options;			/* Ethernet options */
    u_short dli_protype;		/* Ethernet protocol type */
    u_char dli_target[DLI_EADDRSIZE];	/* Ethernet address of target node */
    u_char dli_dest[DLI_EADDRSIZE];	/* Ethernet destination address */
};

struct sockaddr_802 {			/* 802.3 sockaddr struct */
    u_char ioctl;			/* i/o control flags */
    u_char svc;				/* service class for this portal */
    struct osi_802hdr eh_802;		/* OSI 802 header format */
};

struct sockaddr_dl {
    u_char dli_len;			/* length of sockaddr */
    u_char dli_family;			/* address family (AF_DLI) */
    struct dli_devid dli_device;	/* id of comm device to use */
    u_char dli_substructype;		/* id to interpret following structure */
    union {
	struct sockaddr_edl dli_eaddr;	/* Ethernet */
	struct sockaddr_802 dli_802addr; /* OSI 802 support */
	caddr_t	dli_aligner1;		/* this needs to have longword alignment */
    } choose_addr;
};

#define DLI_MAXPKT	1500	/* max number of user bytes per pkt */
#define DLI_MINPKT	46	/* min number of user bytes per pkt */
#define	DLI_ETHERPAD	0x01	/* Protocol is padded */

/*
 * DLI socket option literals
 */
#define DLI_STATE	0	/* state option requested */
#define DLI_MULTICAST	1	/* load multicast address(es) */
#define DLI_INTERNALOOP	2	/* change device to/from internal loopback */

#define	DLI_ENAGSAP		4	/* enable an 802.3 group sap */
#define	DLI_DISGSAP		6	/* disable an 802.3 group sap */
#define	DLI_GETGSAP		8	/* get 802.3 group saps that are enabled by user */
#define	DLI_SET802CTL		10	/* change control field format, 802 */

/* the following socket option is only there for DECnet-OSI */
#define DLI_LOCALENTITYNAME	11	/* set/get client/port name */

/*
 * The following ioctl translate a local entity name into a device id
 * suitable for use in a struct sockaddr_dl.
 */
#define SIOCXLATENAME2IF	_IOWR('s', 71, struct dli_xlatename2if)
struct dli_xlatename2if {
    caddr_t dlif_name;			/* ptr to local entity name */
    int dlif_namelen;			/* length of local entity name */
    struct dli_devid dlif_devid;	/* device id of local entity name */
};

/*
 * This ioctl is called from MOP to update the MOP Functions parameter
 * in the kernel so that the sysid generated reflects the current status of MOP
 * It is a one-byte, bitmapped field.
 */
#define SIOCMOPFUNCTIONS        _IOWR('i', 72, struct dli_mopfunc)
struct dli_mopfunc {
        char dev_name[IFNAMSIZ];                /* Physical device name */
        u_short function;                       /* Functions available */
        };

#define DLIFUNC_Loop            0x01            /* Loop Server (required) */
#define DLIFUNC_Dump            0x02            /* Dump Client */
#define DLIFUNC_PriLoader       0x04            /* Primary Loader Client */
#define DLIFUNC_MulLoader       0x08            /* Multi-block Loader Client */
#define DLIFUNC_Boot            0x10            /* Boot */
#define DLIFUNC_ConsCarrier     0x20            /* Console Carrier Server */
#define DLIFUNC_Counters        0x40            /* Data Link Counters (req'd)*/
#define DLIFUNC_CCReserved      0x80            /* Console Carrier Reserved */


/*
 * DLI state literals
 */
#define DLS_OFF		0	/* turn comm device off */
#define DLS_ON		1	/* turn comm device on */
#define DLS_SLEEP	2	/* process asleep in bind */

/*
 * DLI internal loopback literals
 */
#define DLP_IOFF	0	/* turn internal loopback on */
#define DLP_ION		1	/* turn internal loopback off */


/*
 * MOP literals used by DLI
 */
#ifndef ETHERTYPE_LBACK
#define ETHERTYPE_LBACK 0x9000          /* MOP loopback protocol type */
#endif
#define PROTOID_LBACK   {0x08, 0x00, 0x2b, 0x90, 0x00}
#define LBACKMCAST      {0xcf, 0x00, 0x00, 0x00, 0x00, 0x00}
#ifndef ETHERTYPE_MOPRC
#define ETHERTYPE_MOPRC 0x6002          /* MOP CCR protocol type */
#endif
#define PROTOID_MOPRC   {0x08, 0x00, 0x2b, 0x60, 0x02}
#define SYSIDMCAST      {0xab, 0x00, 0x00, 0x02, 0x00, 0x00}

/* MOP message type codes */
#define DLI_LBACK_FWD   0x2             /* MOP loopback forward data function */
#define DLI_LBACK_LOOP  24              /* MOP point to point loop code */
#define DLI_LBACK_LOOPED 26             /* MOP point to point looped code */
#define DLI_REQCTRS     9               /* MOP request counters code */
#define DLI_SYSID       7               /* MOP SYSID response code */
#define DLI_REQSYSID    5               /* MOP Request SYSID code */
#define DLI_CTRS        11              /* MOP counters code (CSMA-CD only) */
#define DLI_CTRS2       21              /* MOP counters code (non CSMA-CD) */

/* network controller type codes used in MOP SYSID messages */
#define UNA             1       /* DEUNA (Unibus) */
#define QNA             5       /* DEQNA (Q-Bus) */
#define LUA             11      /* DELUA (Unibus) */
#define BNA             23      /* DEBNA (BI) */
#define LQA             37      /* DELQA (Q-Bus) */
#define SVA             39      /* DESVA (MV2000) */
#define MF2             61      /* DECsystem 5400 (integral) */
#define BNI             65      /* DEBNI (BI) */
#define MNA             66      /* DEMNA (XMI) */
#define PMX             67      /* DECstation 3100 (integral) */
#define QTA             75      /* DEQTA (Q-Bus) */

/* MOP SYSID parameter tags */
#define MAINTV          1
#define VER3            3
#define VER4            4
#define ECO             0
#define USER_ECO        0
#define FUNCTIONS       2
#define FNC_LOOP        0x1
#define FNC_CTRS        0x40
#define HADDR           7
#define NODEID          9
#define SYSTIME         10
#define NODENAME1       11
#define NODENAME2       12
#define STATIONID       13
#define COMDEV          100
#define DATALINK        400
#define MCASTADDR       1

/* data link types used in MOP sysid messages */
#define DLI_DLTRN       6
#define DLI_DLFDDI      5
#define DLI_DLHDLC      4
#define DLI_DLLAPB      3
#define DLI_DLDDCMP     2
#define DLI_DLCSMACD    1


#ifdef KERNEL /* the following should not be used by applications */

/*
 * DLI socket option structure
 */
#define MCAST_MAXNUM	60	/* allowable number of multicast addresses */
#define MCAST_SIZE	6	/* size of mulicast address */
#define MCAST_INC	10	/* increment of storage used for mcast addrs */

struct dli_sopt {
    u_char dli_state;		/* state of device */
    u_char dli_iloop;		/* loopback state */
    u_char *dli_mcast;		/* pointer to multicast address array */
    u_char dli_mcabuffsize;	/* size of the current array */
};

struct dli_recv	{			/* received message prefix */
    u_int rcv_protocol;			/* protocol module number */
    struct ifnet *rcv_ifp;		/* received interface descriptor */
    union {
	struct ether_header rcv_ether;	/* ethernet header */
	struct osi_802hdr osi_header;	/* 802 */
    } rcv_hdr;				/* type of data link */
    u_int rcv_priority;			/* frame priority (0 for Ethernet) */
    u_int rcv_dltype;			/* DLI_{ETHERNET,802,POINTOPOINT} */
};


/*
 * DLI line table structure - one for each user;
 */
struct dli_line {
    struct sockaddr_dl dli_lineid;	/* link user to target */
    struct dli_sopt dli_sockopt;	/* user's socket options */
    struct ifnet *dli_ifp;		/* device interface to use */
    struct socket *dli_so;		/* back ptr to owning socket */
    caddr_t dli_portid;                   /* port id returned by data link */
    struct protosw *dli_proto;          /* proto of data link */
};

/*
 * DLI socket literals used only internal to the kernel
 */
#define DLPROTO_CSMACD  1               /* csmacd protocol number */
#define DLPROTO_LOOP    2               /* loopback protocol number */
#define DLPROTO_FDDI    4               /* fddi protocol number */
#define DLPROTO_HDLC    7               /* hdlc protocol number */
#define DLPROTO_LAPB    9               /* lapb protocol number */
#define DLPROTO_TRN     14              /* ISO 8802.5 (Token Ring) */

/*
 * Generic dli event codes from data link devices.
 */
#define DLIPROTO_DISABLED	0
#define DLIPROTO_ENABLED	1
#define DLIPROTO_HALTED		2
#define DLIPROTO_INITIALIZING	3
#define DLIPROTO_RUNNING	4
#define DLIPROTO_DATALOSS	5
#define DLIPROTO_ENTERMAINT	6
#define DLIPROTO_EXITMAINT	7
#define DLIPROTO_RETRYMAX       8

/*
 * Generic dli protocol operation i/f codes.
 */
#define DLIPIF_OPENPORT		0
#define DLIPIF_CLOSEPORT	1
#define DLIPIF_INITLINK		2
#define DLIPIF_STOPLINK		3
#define DLIPIF_SHOWLINK		4
#define DLIPIF_ENTERMAINT       5
#define DLIPIF_EXITMAINT        6
#define DLIPIF_NAMETOIF		7
#define DLIPIF_MAX		8


/*
 * Loopback module.
 */
#define DLOOP_OPENPORT	DLIPIF_OPENPORT
#define DLOOP_CLOSEPORT	DLIPIF_CLOSEPORT

struct dlp_port {
    struct protosw *dlp_pr;		/* user's protosw */
    u_int dlp_id;			/* id returned by loop module */
};

/*
 * ethernet address structure used as a cast to copy ethernet
 * physical addresses.
 */
struct ether_pa {
    u_char ether_addr_octet[6];
};

#define LE_PUT8(p,v)	(*(p)++ = (v))
#define LE_EXT8(p)	((unsigned) (*((u_char *) p)))
#define LE_GET8(p)	((unsigned) (*((u_char *) p)++))

#define LE_PUT16(p,v)	(*(p)++ = (v) & 0xFF, *(p)++ = (v) >> 8)
#define LE_EXT16(p)	((unsigned) (*((u_char *) p)) | (*((u_char *) p + 1) << 8))
#define LE_INS16(p,v)	(*(p) = (v) & 0xFF, *((p)+1) = (v) >> 8)

#define LE_PUT32(p,v)	(*(p)++ = (v) & 0xFF, *(p)++ = (v) >> 8, \
			 *(p)++ = (v) >> 16, *(p)++ = (v) >> 24)

extern int dli_mustberoot;
extern int dli_ifq_maxlen;
extern int dli_debug;
extern u_int dli_maxline;
extern struct domain dlidomain;
extern struct ifqueue dli_intrq;
extern u_char sysid_mcast[];
extern u_char loopback_mcast[];
extern u_char protoid_moprc[];
extern u_char protoid_lback[];
extern struct dli_line dli_ltable[];

/* protocol switch table addresses of drivers external to DLI 
 * are stored in these global variables, they are initialized via pffindproto
 */
extern struct protosw *dli_netmansw, *dli_fddisw, *dli_csmacdsw, *dli_trnsw;

/* these functions are present only if the NETMAN subset is installed */
extern caddr_t dli_openport(struct ifnet *, struct dli_line *);
extern int dli_prco_pif(int, struct socket *, int, int, struct mbuf **);
extern int dli_name2if(caddr_t, struct ifnet *);
extern void dli_sysid_extra(struct ifnet *, struct ether_pa *, int, u_char *);
extern int dli_output_netman
        ( struct dli_line *, struct ifnet *, struct mbuf *, struct sockaddr * );
extern int dli_multi_op(struct dli_line *, int cmd, u_char *mcast);

/* these function pointers are nonzero only if the NETMAN subset is installed */
extern caddr_t (* dli_openport_fp)(struct ifnet *, struct dli_line *);
extern int (* dli_name2if_fp)(caddr_t, struct ifnet *);
extern int (* dli_prco_pif_fp)(int, struct socket *, int, int, struct mbuf **);
extern void (* dli_sysid_extra_fp)
		( struct ifnet *, struct ether_pa *, int, u_char * );
extern int (* dli_output_netman_fp)
        ( struct dli_line *, struct ifnet *, struct mbuf *, struct sockaddr * );
extern int (* dli_multi_op_fp)(struct dli_line *, int cmd, u_char *mcast);

/* translate from socket structure to DLI line table entry pointer */
#define so2dliline(so)	((struct dli_line *)(so)->so_pcb)

#endif /* KERNEL */
