Improved device tags and sample usage
[akaros.git] / kern / include / ip.h
index 3a5f97d..795a581 100644 (file)
@@ -1,5 +1,8 @@
 // INFERNO
 
+#ifndef ROS_KERN_IP_H
+#define ROS_KERN_IP_H
+
 enum
 {
        Addrlen=        64,
@@ -41,12 +44,13 @@ enum
 /*
  *  one per conversation directory
  */
+struct Proto;
 struct conv
 {
        qlock_t qlock;
 
        int     x;                      /* conversation index */
-       struct proto*   p;
+       struct Proto*   p;
 
        int     restricted;             /* remote port is restricted */
        uint32_t        ttl;                    /* max time to live */
@@ -76,7 +80,7 @@ struct conv
        struct queue*   wq;                     /* queued data waiting to be written */
        struct queue*   eq;                     /* returned error packets */
        struct queue*   sq;                     /* snooping queue */
-       struct kref     snoopers;               /* number of processes with snoop open */
+       atomic_t        snoopers;               /* number of processes with snoop open */
 
        struct rendez   cr;
        char    cerr[ERRMAX];
@@ -84,9 +88,9 @@ struct conv
        qlock_t listenq;
        struct rendez   listenr;
 
-       struct ipmulti  *multi;                 /* multicast bindings for this interface */
+       struct Ipmulti  *multi;                 /* multicast bindings for this interface */
 
-       void*   ptcl;                   /* protocol specific stuff */
+       void*   ptcl;                   /* Protocol specific stuff */
 
        struct route    *r;                     /* last route used */
        uint32_t        rgen;                   /* routetable generation for *r */
@@ -149,19 +153,19 @@ struct Iplifc
        long    preflt;         /* v6 preferred lifetime */
        long    origint;        /* time when addr was added */
        struct Iplink   *link;          /* addresses linked to this lifc */
-       struct iplifc   *next;
+       struct Iplifc   *next;
 };
 
 /* binding twixt Ipself and Iplifc */
 struct Iplink
 {
        struct Ipself   *self;
-       struct iplifc   *lifc;
+       struct Iplifc   *lifc;
        struct Iplink   *selflink;      /* next link for this local address */
        struct Iplink   *lifclink;      /* next link for this ifc */
        uint32_t        expire;
        struct Iplink   *next;          /* free list */
-       int     ref;
+       struct kref     ref;
 };
 
 /* rfc 2461, pp.40--43. */
@@ -237,7 +241,7 @@ enum
 };
 struct Iphash
 {
-       struct iphash   *next;
+       struct Iphash   *next;
        struct conv     *c;
        int     match;
 };
@@ -253,7 +257,7 @@ void iphtrem(struct Ipht*, struct conv*);
 struct conv* iphtlook(struct Ipht *ht, uint8_t *sa, uint16_t sp, uint8_t *da, uint16_t dp);
 
 /*
- *  one per multiplexed protocol
+ *  one per multiplexed Protocol
  */
 struct Proto
 {
@@ -268,14 +272,15 @@ struct Proto
        int             (*state)(struct conv*, char *unused_char_p_t, int);
        void            (*create)(struct conv*);
        void            (*close)(struct conv*);
-       void            (*rcv)(struct proto*, struct Ipifc*, struct block*);
+       void            (*rcv)(struct Proto*, struct Ipifc*, struct block*);
        char*           (*ctl)(struct conv*, char **unused_char_pp_t, int);
-       void            (*advise)(struct proto*, struct block*, char *unused_char_p_t);
-       int             (*stats)(struct proto*, char *unused_char_p_t, int);
+       void            (*advise)(struct Proto*, struct block*, char *unused_char_p_t);
+       int             (*stats)(struct Proto*, char *unused_char_p_t, int);
        int             (*local)(struct conv*, char *unused_char_p_t, int);
        int             (*remote)(struct conv*, char *unused_char_p_t, int);
        int             (*inuse)(struct conv*);
-       int             (*gc)(struct proto*);   /* returns true if any conversations are freed */
+       int             (*gc)(struct Proto*);   /* returns true if any conversations are freed */
+       void    (*newconv)(struct Proto *udp, struct conv *conv);
 
        struct Fs               *f;             /* file system this proto is part of */
        struct conv             **conv;         /* array of conversations */
@@ -307,10 +312,10 @@ struct Fs
        int     dev;
 
        int     np;
-       struct proto*   p[Maxproto+1];          /* list of supported protocols */
-       struct proto*   t2p[256];               /* vector of all protocols */
-       struct proto*   ipifc;                  /* kludge for ipifcremroute & ipifcaddroute */
-       struct proto*   ipmux;                  /* kludge for finding an ip multiplexor */
+       struct Proto*   p[Maxproto+1];          /* list of supported protocols */
+       struct Proto*   t2p[256];               /* vector of all protocols */
+       struct Proto*   ipifc;                  /* kludge for ipifcremroute & ipifcaddroute */
+       struct Proto*   ipmux;                  /* kludge for finding an ip multiplexor */
 
        struct IP       *ip;
        struct Ipselftab        *self;
@@ -322,7 +327,7 @@ struct Fs
        struct route    *v6root[1<<Lroot];      /* v6 routing forest */
        struct route    *queue;                 /* used as temp when reinjecting routes */
 
-       //Netlog        *alog;
+       struct Netlog   *alog;
        struct Ifclog   *ilog;
 
        char    ndb[1024];              /* an ndb entry for this interface */
@@ -333,7 +338,7 @@ struct Fs
 /* one per default router known to host */
 struct V6router {
        uint8_t inuse;
-       struct ipifc    *ifc;
+       struct Ipifc    *ifc;
        int     ifcid;
        uint8_t routeraddr[IPaddrlen];
        long    ltorigin;
@@ -359,9 +364,9 @@ struct conv*        Fsnewcall(struct conv*, uint8_t *unused_uint8_p_t, uint16_t, uint8_
 int    Fspcolstats( char *unused_char_p_t, int);
 int    Fsproto(struct Fs*, struct Proto*);
 int    Fsbuiltinproto(struct Fs*, uint8_t unused_uint8_t);
-struct conv*   Fsprotoclone(struct proto*, char *unused_char_p_t);
-struct proto*  Fsrcvpcol(struct Fs*, uint8_t unused_uint8_t);
-struct proto*  Fsrcvpcolx(struct Fs*, uint8_t unused_uint8_t);
+struct conv*   Fsprotoclone(struct Proto*, char *unused_char_p_t);
+struct Proto*  Fsrcvpcol(struct Fs*, uint8_t unused_uint8_t);
+struct Proto*  Fsrcvpcolx(struct Fs*, uint8_t unused_uint8_t);
 char*  Fsstdconnect(struct conv*, char **unused_char_pp_t, int);
 char*  Fsstdannounce(struct conv*, char **unused_char_pp_t, int);
 char*  Fsstdbind(struct conv*, char **unused_char_pp_t, int);
@@ -439,9 +444,9 @@ struct      RouteTree
        uint8_t depth;
        uint8_t type;
        uint8_t ifcid;          /* must match ifc->id */
-       struct ipifc    *ifc;
+       struct Ipifc    *ifc;
        char    tag[4];
-       int     ref;
+       struct kref     kref;
 };
 
 struct V4route
@@ -460,10 +465,10 @@ struct V6route
 
 struct route
 {
-       struct RouteTree RouteTree;;
+       struct RouteTree rt;
 
        union {
-               struct V6route  v6;
+               struct V6route v6;
                struct V4route v4;
        };
 };
@@ -515,14 +520,14 @@ struct arpent
        struct arpent   *nextrxt;               /* re-transmit chain */
        unsigned int    rtime;                  /* time for next retransmission */
        uint8_t rxtsrem;
-       struct ipifc    *ifc;
+       struct Ipifc    *ifc;
        uint8_t ifcid;                  /* must match ifc->id */
 };
 
 extern void    arpinit(struct Fs*);
 extern int     arpread(struct arp*, char *unused_char_p_t, uint32_t, int);
 extern int     arpwrite(struct Fs*, char *unused_char_p_t, int);
-extern struct arpent*  arpget(struct arp*, struct block *bp, int version, struct ipifc *ifc, uint8_t *ip,
+extern struct arpent*  arpget(struct arp*, struct block *bp, int version, struct Ipifc *ifc, uint8_t *ip,
                             uint8_t *h);
 extern void    arprelease(struct arp*, struct arpent *a);
 extern struct block*   arpresolve(struct arp*, struct arpent *a,
@@ -557,8 +562,6 @@ extern uint8_t IPnoaddr[IPaddrlen];
 extern uint8_t v4prefix[IPaddrlen];
 extern uint8_t IPallbits[IPaddrlen];
 
-#define        NOW     TK2MS(MACHP(0)->ticks)
-
 /*
  *  media
  */
@@ -576,28 +579,28 @@ extern int        ipforme(struct Fs*, uint8_t *addr);
 extern int     iptentative(struct Fs*, uint8_t *addr);
 extern int     ipisbm(uint8_t *);
 extern int     ipismulticast(uint8_t *);
-extern struct ipifc*   findipifc(struct Fs*, uint8_t *remote, int type);
+extern struct Ipifc*   findipifc(struct Fs*, uint8_t *remote, int type);
 extern void    findprimaryip(struct Fs*, uint8_t *unused_uint8_p_t);
 extern void    findlocalip(struct Fs*, uint8_t *local, uint8_t *remote);
-extern int     ipv4local(struct ipifc *ifc, uint8_t *addr);
-extern int     ipv6local(struct ipifc *ifc, uint8_t *addr);
-extern int     ipv6anylocal(struct ipifc *ifc, uint8_t *addr);
-extern struct iplifc*  iplocalonifc(struct ipifc *ifc, uint8_t *ip);
-extern int     ipproxyifc(struct Fs *f, struct ipifc *ifc, uint8_t *ip);
+extern int     ipv4local(struct Ipifc *ifc, uint8_t *addr);
+extern int     ipv6local(struct Ipifc *ifc, uint8_t *addr);
+extern int     ipv6anylocal(struct Ipifc *ifc, uint8_t *addr);
+extern struct Iplifc*  iplocalonifc(struct Ipifc *ifc, uint8_t *ip);
+extern int     ipproxyifc(struct Fs *f, struct Ipifc *ifc, uint8_t *ip);
 extern int     ipismulticast(uint8_t *ip);
 extern int     ipisbooting(void);
-extern int     ipifccheckin(struct ipifc *ifc, struct medium *med);
-extern void    ipifccheckout(struct ipifc *ifc);
-extern int     ipifcgrab(struct ipifc *ifc);
+extern int     ipifccheckin(struct Ipifc *ifc, struct medium *med);
+extern void    ipifccheckout(struct Ipifc *ifc);
+extern int     ipifcgrab(struct Ipifc *ifc);
 extern void    ipifcaddroute(struct Fs*, int unused_int, uint8_t *unused_uint8_p_t, uint8_t*, uint8_t*, int);
 extern void    ipifcremroute(struct Fs*, int unused_int, uint8_t *u8pt, uint8_t *u8pt2);
 extern void    ipifcremmulti(struct conv *c, uint8_t *ma, uint8_t *ia);
 extern void    ipifcaddmulti(struct conv *c, uint8_t *ma, uint8_t *ia);
-extern char*   ipifcrem(struct ipifc *ifc, char **argv, int argc);
-extern char*   ipifcadd(struct ipifc *ifc, char **argv, int argc, int tentative,
-                            struct iplifc *lifcp);
+extern char*   ipifcrem(struct Ipifc *ifc, char **argv, int argc);
+extern char*   ipifcadd(struct Ipifc *ifc, char **argv, int argc, int tentative,
+                            struct Iplifc *lifcp);
 extern long    ipselftabread(struct Fs*, char *a, uint32_t offset, int n);
-extern char*   ipifcaddpref6(struct ipifc *ifc, char**argv, int argc);
+extern char*   ipifcaddpref6(struct Ipifc *ifc, char**argv, int argc);
 extern void    ipsendra6(struct Fs *f, int on);
 
 /*
@@ -608,8 +611,8 @@ extern void icmpnoconv(struct Fs*, struct block*);
 extern void    icmpcantfrag(struct Fs*, struct block*, int);
 extern void    icmpttlexceeded(struct Fs*, uint8_t *unused_uint8_p_t, struct block*);
 extern uint16_t        ipcsum( uint8_t *unused_uint8_p_t);
-extern void    ipiput4(struct Fs*, struct ipifc *unused_ipifc, struct block*);
-extern void    ipiput6(struct Fs*, struct ipifc *unused_ipifc, struct block*);
+extern void    ipiput4(struct Fs*, struct Ipifc *unused_ipifc, struct block*);
+extern void    ipiput6(struct Fs*, struct Ipifc *unused_ipifc, struct block*);
 extern int     ipoput4(struct Fs*,
                          struct block*, int unused_int, int, int, struct conv*);
 extern int     ipoput6(struct Fs*,
@@ -624,13 +627,13 @@ extern uint32_t   restrict_mtu( uint8_t *unused_uint8_p_t, uint32_t);
 /*
  * bootp.c
  */
-char*  (*bootp)(struct ipifc *unused_ipifc);
+char*  (*bootp)(struct Ipifc *unused_ipifc);
 int    (*bootpread)( char *unused_char_p_t, uint32_t, int);
 
 /*
  *  iprouter.c
  */
-void   useriprouter(struct Fs*, struct ipifc *unused_ipifc, struct block*);
+void   useriprouter(struct Fs*, struct Ipifc *unused_ipifc, struct block*);
 void   iprouteropen(struct Fs*);
 void   iprouterclose(struct Fs*);
 long   iprouterread(struct Fs*, void*, int);
@@ -650,7 +653,7 @@ extern struct chan* chandial( char *u1, char*u2, char*u3, struct chan**c);
 /*
  *  global to all of the stack
  */
-extern void    (*igmpreportfn)(struct ipifc *unused_ipifc, uint8_t *unused_uint8_p_t);
+extern void    (*igmpreportfn)(struct Ipifc *unused_ipifc, uint8_t *unused_uint8_p_t);
 
 /* IPV6 */
 /* rfc 3513 defines the address prefices */
@@ -669,7 +672,7 @@ typedef struct Opthdr     Opthdr;
 typedef struct Routinghdr Routinghdr;
 typedef struct Fraghdr6    Fraghdr6;
 
-struct Ip6hdr {
+struct ip6hdr {
        uint8_t vcf[4];         // version:4, traffic class:8, flow label:20
        uint8_t ploadlen[2];    // payload length: packet length - 40
        uint8_t proto;          // next header type
@@ -690,7 +693,7 @@ struct Routinghdr {
        uint8_t segrem;
 };
 
-struct Fraghdr6 {
+struct fraghdr6 {
        uint8_t nexthdr;
        uint8_t res;
        uint8_t offsetRM[2];    // Offset, Res, M flag
@@ -805,11 +808,11 @@ extern void icmpns(struct Fs *f, uint8_t* src, int suni, uint8_t* targ, int tuni
                   uint8_t* mac);
 extern void icmpna(struct Fs *f, uint8_t* src, uint8_t* dst, uint8_t* targ, uint8_t* mac,
                   uint8_t flags);
-extern void icmpttlexceeded6(struct Fs *f, struct ipifc *ifc,
+extern void icmpttlexceeded6(struct Fs *f, struct Ipifc *ifc,
                             struct block *bp);
-extern void icmppkttoobig6(struct Fs *f, struct ipifc *ifc, struct block *bp);
+extern void icmppkttoobig6(struct Fs *f, struct Ipifc *ifc, struct block *bp);
 extern void icmphostunr(struct Fs *f,
-                       struct ipifc *ifc,
+                       struct Ipifc *ifc,
                        struct block *bp, int code, int free);
 
 extern uint8_t v6allnodesN[IPaddrlen];
@@ -841,3 +844,183 @@ extern int v6aNpreflen;
 extern int v6aLpreflen;
 
 extern int ReTransTimer;
+
+int kdial(char *dest, char *local, char *dir, int *cfdp);
+
+/* network interfaces and ethernet */
+// INFERNO
+
+enum
+{
+       Nmaxaddr=       64,
+       Nmhash=         31,
+
+       Ncloneqid=      1,
+       Naddrqid,
+       N2ndqid,
+       N3rdqid,
+       Ndataqid,
+       Nctlqid,
+       Nstatqid,
+       Ntypeqid,
+       Nifstatqid,
+};
+
+/*
+ *  Macros to manage Qid's used for multiplexed devices
+ */
+#define NETTYPE(x)     (((uint32_t)x)&0x1f)
+#define NETID(x)       ((((uint32_t)x))>>5)
+#define NETQID(i,t)    ((((uint32_t)i)<<5)|(t))
+
+/*
+ *  one per multiplexed connection
+ */
+struct netfile
+{
+       qlock_t qlock;
+
+       int     inuse;
+       uint32_t        mode;
+       char    owner[KNAMELEN];
+
+       int     type;                   /* multiplexor type */
+       int     prom;                   /* promiscuous mode */
+       int     scan;                   /* base station scanning interval */
+       int     bridge;                 /* bridge mode */
+       int     headersonly;            /* headers only - no data */
+       uint8_t maddr[8];               /* bitmask of multicast addresses requested */
+       int     nmaddr;                 /* number of multicast addresses */
+
+       struct queue    *in;                    /* input buffer */
+};
+
+/*
+ *  a network address
+ */
+struct netaddr
+{
+       struct netaddr  *next;          /* allocation chain */
+       struct netaddr  *hnext;
+       uint8_t addr[Nmaxaddr];
+       struct kref ref;
+};
+
+/*
+ *  a network interface
+ */
+struct netif
+{
+       qlock_t qlock;
+
+       /* multiplexing */
+       char    name[KNAMELEN];         /* for top level directory */
+       int     nfile;                  /* max number of Netfiles */
+       struct netfile  **f;
+
+       /* about net */
+       int     limit;                  /* flow control */
+       int     alen;                   /* address length */
+       int     mbps;                   /* megabits per sec */
+       int     link;                   /* link status */
+       uint8_t addr[Nmaxaddr];
+       uint8_t bcast[Nmaxaddr];
+       struct netaddr  *maddr;                 /* known multicast addresses */
+       int     nmaddr;                 /* number of known multicast addresses */
+       struct netaddr *mhash[Nmhash];          /* hash table of multicast addresses */
+       int     prom;                   /* number of promiscuous opens */
+       int     scan;                   /* number of base station scanners */
+       int     all;                    /* number of -1 multiplexors */
+
+       /* statistics */
+       int     misses;
+       int     inpackets;
+       int     outpackets;
+       int     crcs;           /* input crc errors */
+       int     oerrs;          /* output errors */
+       int     frames;         /* framing errors */
+       int     overflows;      /* packet overflows */
+       int     buffs;          /* buffering errors */
+       int     soverflows;     /* software overflow */
+
+       /* routines for touching the hardware */
+       void    *arg;
+       void    (*promiscuous)(void*, int);
+       void    (*multicast)(void*, uint8_t *unused_uint8_p_t, int);
+       void    (*scanbs)(void*, unsigned nt);  /* scan for base stations */
+};
+
+void   netifinit(struct netif*, char *, int , uint32_t);
+struct walkqid*        netifwalk(struct netif*, struct chan*, struct chan*, char **, int);
+struct chan*   netifopen(struct netif*, struct chan*, int);
+void   netifclose(struct netif*, struct chan*);
+long   netifread(struct netif*, struct chan*, void*, long, uint32_t);
+struct block*  netifbread(struct netif*, struct chan*, long, uint32_t);
+long   netifwrite(struct netif*, struct chan*, void*, long);
+int    netifwstat(struct netif*, struct chan*, uint8_t *, int);
+int    netifstat(struct netif*, struct chan*, uint8_t *, int);
+int    activemulti(struct netif*, uint8_t *, int);
+
+/*
+ *  Ethernet specific
+ */
+enum
+{
+       Eaddrlen=       6,
+       ETHERMINTU =    60,             /* minimum transmit size */
+       ETHERMAXTU =    1514,           /* maximum transmit size */
+       ETHERHDRSIZE =  14,             /* size of an ethernet header */
+};
+
+struct etherpkt
+{
+       uint8_t d[Eaddrlen];
+       uint8_t s[Eaddrlen];
+       uint8_t type[2];
+       uint8_t data[1500];
+};
+// INFERNO
+enum {
+       MaxEther        = 4,
+       MaxFID= 16,
+       Ntypes          = 8,
+};
+
+struct ether {
+       rwlock_t rwlock;
+       int     ctlrno;
+       int     tbdf;                   /* type+busno+devno+funcno */
+       int     minmtu;
+       int     maxmtu;
+       uint8_t ea[Eaddrlen];
+       int     encry;
+
+       void    (*attach)(struct ether*);       /* filled in by reset routine */
+       void    (*closed)(struct ether*);
+       void    (*detach)(struct ether*);
+       void    (*transmit)(struct ether*);
+       void    (*interrupt)(struct hw_trapframe*, void*);
+       long    (*ifstat)(struct ether*, void*, long, uint32_t);
+       long    (*ctl)(struct ether*, void*, long); /* custom ctl messages */
+       void    (*power)(struct ether*, int);   /* power on/off */
+       void    (*shutdown)(struct ether*);     /* shutdown hardware before reboot */
+       void    *ctlr;
+       int     pcmslot;                /* PCMCIA */
+       int     fullduplex;     /* non-zero if full duplex */
+       int     vlanid; /* non-zero if vlan */
+
+       struct queue*   oq;
+
+       qlock_t vlq;    /* array change */
+       int     nvlan;
+       struct ether*   vlans[MaxFID];
+
+       /* another case where we wish we had anon struct members. */
+       struct netif netif;
+};
+
+extern struct block* etheriq(struct ether*, struct block*, int);
+extern void addethercard( char *unused_char_p_t, int(*)(struct ether*));
+extern int archether( int unused_int, struct ether*);
+
+#endif /* ROS_KERN_IP_H */