]> git.saurik.com Git - apple/xnu.git/blobdiff - bsd/netinet/ip_dummynet.h
xnu-4570.31.3.tar.gz
[apple/xnu.git] / bsd / netinet / ip_dummynet.h
index 83f38d24ec20c7ea2be7e45c88ab8310b26d257f..7472e958cce4471e3d48249ce2cf7a5a7fbcc9d1 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000-2008 Apple Inc. All rights reserved.
+ * Copyright (c) 2000-2013 Apple Inc. All rights reserved.
  *
  * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
  * 
 #include <sys/appleapiopts.h>
 
 #ifdef PRIVATE
+#include <netinet/ip_flowid.h>
+
+/* Apply ipv6 mask on ipv6 addr */
+#define APPLY_MASK(addr,mask)                          \
+    (addr)->__u6_addr.__u6_addr32[0] &= (mask)->__u6_addr.__u6_addr32[0]; \
+    (addr)->__u6_addr.__u6_addr32[1] &= (mask)->__u6_addr.__u6_addr32[1]; \
+    (addr)->__u6_addr.__u6_addr32[2] &= (mask)->__u6_addr.__u6_addr32[2]; \
+    (addr)->__u6_addr.__u6_addr32[3] &= (mask)->__u6_addr.__u6_addr32[3];
+
 /*
  * Definition of dummynet data structures. In the structures, I decided
  * not to use the macros in <sys/queue.h> in the hope of making the code
@@ -146,21 +155,52 @@ struct dn_heap {
  * processing requirements.
  */
 #ifdef KERNEL
+#include <net/if_var.h>
+#include <net/route.h>
 #include <netinet/ip_var.h>    /* for ip_out_args */
+#include <netinet/ip6.h>       /* for ip6_out_args */
+#include <netinet/in.h>
+#include <netinet6/ip6_var.h>  /* for ip6_out_args */
 
 struct dn_pkt_tag {
-    struct ip_fw *rule;                /* matching rule */
-    int dn_dir;                        /* action when packet comes out. */
+    struct ip_fw       *dn_ipfw_rule;          /* matching IPFW rule */
+    void               *dn_pf_rule;            /* matching PF rule */
+    int                        dn_dir;                 /* action when packet comes out. */
 #define DN_TO_IP_OUT   1
 #define DN_TO_IP_IN    2
 #define DN_TO_BDG_FWD  3
-
-    dn_key output_time;                /* when the pkt is due for delivery     */
-    struct ifnet *ifp;         /* interface, for ip_output             */
-    struct sockaddr_in *dn_dst ;
-    struct route ro;           /* route, for ip_output. MUST COPY      */
-    int flags ;                        /* flags, for ip_output (IPv6 ?)        */
-    struct ip_out_args ipoa;   /* output args, for ip_output. MUST COPY */
+#define DN_TO_IP6_IN    4
+#define DN_TO_IP6_OUT   5
+    dn_key             dn_output_time;         /* when the pkt is due for delivery     */
+    struct ifnet       *dn_ifp;                /* interface, for ip[6]_output          */
+    union {
+       struct sockaddr_in      _dn_dst;
+       struct sockaddr_in6     _dn_dst6 ;
+    }                  dn_dst_;
+#define dn_dst dn_dst_._dn_dst
+#define dn_dst6 dn_dst_._dn_dst6
+    union {
+       struct route            _dn_ro;         /* route, for ip_output. MUST COPY      */
+       struct route_in6        _dn_ro6;        /* route, for ip6_output. MUST COPY     */
+       }               dn_ro_;
+#define dn_ro dn_ro_._dn_ro
+#define dn_ro6 dn_ro_._dn_ro6
+    struct route_in6   dn_ro6_pmtu;            /* for ip6_output */
+    struct ifnet       *dn_origifp;            /* for ip6_output */
+    u_int32_t          dn_mtu;                 /* for ip6_output */
+    int                        dn_alwaysfrag;          /* for ip6_output */
+    u_int32_t          dn_unfragpartlen;       /* for ip6_output */
+    struct ip6_exthdrs         dn_exthdrs;             /* for ip6_output */
+    int                        dn_flags ;              /* flags, for ip[6]_output */
+    int                        dn_client;
+#define DN_CLIENT_IPFW 1
+#define DN_CLIENT_PF   2
+    union {
+       struct ip_out_args      _dn_ipoa;       /* output args, for ip_output. MUST COPY */
+       struct ip6_out_args     _dn_ip6oa;      /* output args, for ip_output. MUST COPY */
+    }                  dn_ipoa_;
+#define dn_ipoa dn_ipoa_._dn_ipoa
+#define dn_ip6oa dn_ipoa_._dn_ip6oa
 };
 #else
 struct dn_pkt;
@@ -236,7 +276,7 @@ flow using a number of heaps defined into the pipe itself.
  */
 struct dn_flow_queue {
     struct dn_flow_queue *next ;
-    struct ipfw_flow_id id ;
+    struct ip_flow_id id ;
 
     struct mbuf *head, *tail ; /* queue of packets */
     u_int len ;
@@ -299,7 +339,7 @@ struct dn_flow_set {
     int qsize ;                        /* queue size in slots or bytes */
     int plr ;                  /* pkt loss rate (2^31-1 means 100%) */
 
-    struct ipfw_flow_id flow_mask ;
+    struct ip_flow_id flow_mask ;
 
     /* hash table of queues onto this flow_set */
     int rq_size ;              /* number of slots */
@@ -379,17 +419,16 @@ struct dn_pipe {          /* a pipe */
 
 SLIST_HEAD(dn_pipe_head, dn_pipe);
 
-#ifdef KERNEL
-
+#ifdef BSD_KERNEL_PRIVATE
+extern uint32_t my_random(void);
 void ip_dn_init(void); /* called from raw_ip.c:load_ipfw() */
 
 typedef        int ip_dn_ctl_t(struct sockopt *); /* raw_ip.c */
-typedef        void ip_dn_ruledel_t(void *); /* ip_fw.c */
 typedef        int ip_dn_io_t(struct mbuf *m, int pipe_nr, int dir,
-       struct ip_fw_args *fwa);
+       struct ip_fw_args *fwa, int );
 extern ip_dn_ctl_t *ip_dn_ctl_ptr;
-extern ip_dn_ruledel_t *ip_dn_ruledel_ptr;
 extern ip_dn_io_t *ip_dn_io_ptr;
+void dn_ipfw_rule_delete(void *);
 #define        DUMMYNET_LOADED (ip_dn_io_ptr != NULL)
 
 #pragma pack(4)
@@ -403,7 +442,7 @@ struct dn_heap_32 {
 
 struct dn_flow_queue_32 {
     user32_addr_t next ;
-    struct ipfw_flow_id id ;
+    struct ip_flow_id id ;
 
     user32_addr_t head, tail ; /* queue of packets */
     u_int len ;
@@ -454,7 +493,7 @@ struct dn_flow_set_32 {
     int qsize ;                        /* queue size in slots or bytes */
     int plr ;                  /* pkt loss rate (2^31-1 means 100%) */
        
-    struct ipfw_flow_id flow_mask ;
+    struct ip_flow_id flow_mask ;
        
     /* hash table of queues onto this flow_set */
     int rq_size ;              /* number of slots */
@@ -528,7 +567,7 @@ struct dn_heap_64 {
 
 struct dn_flow_queue_64 {
     user64_addr_t next ;
-    struct ipfw_flow_id id ;
+    struct ip_flow_id id ;
 
     user64_addr_t head, tail ; /* queue of packets */
     u_int len ;
@@ -579,7 +618,7 @@ struct dn_flow_set_64 {
     int qsize ;                        /* queue size in slots or bytes */
     int plr ;                  /* pkt loss rate (2^31-1 means 100%) */
        
-    struct ipfw_flow_id flow_mask ;
+    struct ip_flow_id flow_mask ;
        
     /* hash table of queues onto this flow_set */
     int rq_size ;              /* number of slots */
@@ -641,8 +680,6 @@ struct dn_pipe_64 {         /* a pipe */
     struct dn_flow_set_64 fs ; /* used with fixed-rate flows */
 };
 
-
-
 /*
  * Return the IPFW rule associated with the dummynet tag; if any.
  * Make sure that the dummynet tag is not reused by lower layers.
@@ -654,11 +691,68 @@ ip_dn_claim_rule(struct mbuf *m)
                                                                          KERNEL_TAG_TYPE_DUMMYNET, NULL);
        if (mtag != NULL) {
                mtag->m_tag_type = KERNEL_TAG_TYPE_NONE;
-               return (((struct dn_pkt_tag *)(mtag+1))->rule);
+               return (((struct dn_pkt_tag *)(mtag+1))->dn_ipfw_rule);
        } else
                return (NULL);
 }
-#endif /* KERNEL */
 
+#include <sys/eventhandler.h>
+/* Dummynet event handling declarations */
+extern struct eventhandler_lists_ctxt dummynet_evhdlr_ctxt;
+extern void dummynet_init(void);
+
+struct dn_pipe_mini_config {
+       uint32_t bandwidth;
+       uint32_t delay;
+       uint32_t plr;
+};
+
+struct dn_rule_mini_config {
+       uint32_t dir;
+       uint32_t af;
+       uint32_t proto;
+       /*
+        * XXX PF rules actually define ranges of ports and
+        * along with range goes an opcode ((not) equal to, less than
+        * greater than, etc.
+        * For now the following works assuming there's no port range
+        * and the rule is for specific port.
+        * Also the operation is assumed as equal to.
+        */
+       uint32_t src_port;
+       uint32_t dst_port;
+       char ifname[IFXNAMSIZ];
+};
+
+struct dummynet_event {
+       uint32_t dn_event_code;
+       union {
+               struct dn_pipe_mini_config _dnev_pipe_config;
+               struct dn_rule_mini_config _dnev_rule_config;
+       } dn_event;
+};
+
+#define        dn_event_pipe_config    dn_event._dnev_pipe_config
+#define        dn_event_rule_config    dn_event._dnev_rule_config
+
+extern void dummynet_event_enqueue_nwk_wq_entry(struct dummynet_event *);
+
+enum {
+       DUMMYNET_RULE_CONFIG,
+       DUMMYNET_RULE_DELETE,
+       DUMMYNET_PIPE_CONFIG,
+       DUMMYNET_PIPE_DELETE,
+       DUMMYNET_NLC_DISABLED,
+};
+
+enum    { DN_INOUT, DN_IN, DN_OUT };
+/*
+ * The signature for the callback is:
+ * eventhandler_entry_arg      __unused
+ * dummynet_event              pointer to dummynet event object
+ */
+typedef void (*dummynet_event_fn) (struct eventhandler_entry_arg, struct dummynet_event *);
+EVENTHANDLER_DECLARE(dummynet_event, dummynet_event_fn);
+#endif /* BSD_KERNEL_PRIVATE */
 #endif /* PRIVATE */
 #endif /* _IP_DUMMYNET_H */