From: Ben Pfaff Date: Mon, 18 Jun 2012 22:12:57 +0000 (-0700) Subject: flow: Take advantage of zero-padding in struct flow and flow_wildcards. X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=16c6d0c38406d860027c12d7da5138f35f6264b5;p=openvswitch flow: Take advantage of zero-padding in struct flow and flow_wildcards. Since we know these bytes are always 0 in both structures, we can use faster functions that only work with full words. Signed-off-by: Ben Pfaff --- diff --git a/lib/flow.c b/lib/flow.c index c414e812..a16c8ef6 100644 --- a/lib/flow.c +++ b/lib/flow.c @@ -756,11 +756,7 @@ flow_wildcards_combine(struct flow_wildcards *dst, uint32_t flow_wildcards_hash(const struct flow_wildcards *wc, uint32_t basis) { - /* If you change struct flow_wildcards and thereby trigger this - * assertion, please check that the new struct flow_wildcards has no holes - * in it before you update the assertion. */ - BUILD_ASSERT_DECL(sizeof *wc == 120 + FLOW_N_REGS * 4); - return hash_bytes(wc, sizeof *wc, basis); + return hash_words((const uint32_t *) wc, sizeof *wc / 4, basis); } /* Returns true if 'a' and 'b' represent the same wildcards, false if they are diff --git a/lib/flow.h b/lib/flow.h index 30cd044d..3534fb48 100644 --- a/lib/flow.h +++ b/lib/flow.h @@ -77,6 +77,10 @@ struct flow { uint8_t nw_frag; /* FLOW_FRAG_* flags. */ uint8_t zeros[2]; /* Must be zero. */ }; +BUILD_ASSERT_DECL(sizeof(struct flow) % 8 == 0); + +/* Remember to update FLOW_WC_SEQ when changing 'struct flow'. */ +BUILD_ASSERT_DECL(sizeof(struct flow) == 152 && FLOW_WC_SEQ == 17); /* Represents the metadata fields of struct flow. */ struct flow_metadata { @@ -86,17 +90,6 @@ struct flow_metadata { uint16_t in_port; /* OpenFlow port or zero. */ }; -/* Assert that there are FLOW_SIG_SIZE bytes of significant data in "struct - * flow", followed by FLOW_PAD_SIZE bytes of padding. */ -#define FLOW_SIG_SIZE (118 + FLOW_N_REGS * 4) -#define FLOW_PAD_SIZE 2 -BUILD_ASSERT_DECL(offsetof(struct flow, nw_frag) == FLOW_SIG_SIZE - 1); -BUILD_ASSERT_DECL(sizeof(((struct flow *)0)->nw_frag) == 1); -BUILD_ASSERT_DECL(sizeof(struct flow) == FLOW_SIG_SIZE + FLOW_PAD_SIZE); - -/* Remember to update FLOW_WC_SEQ when changing 'struct flow'. */ -BUILD_ASSERT_DECL(FLOW_SIG_SIZE == 150 && FLOW_WC_SEQ == 17); - void flow_extract(struct ofpbuf *, uint32_t priority, ovs_be64 tun_id, uint16_t in_port, struct flow *); void flow_zero_wildcards(struct flow *, const struct flow_wildcards *); @@ -118,7 +111,7 @@ void flow_compose(struct ofpbuf *, const struct flow *); static inline int flow_compare_3way(const struct flow *a, const struct flow *b) { - return memcmp(a, b, FLOW_SIG_SIZE); + return memcmp(a, b, sizeof *a); } static inline bool @@ -130,7 +123,7 @@ flow_equal(const struct flow *a, const struct flow *b) static inline size_t flow_hash(const struct flow *flow, uint32_t basis) { - return hash_bytes(flow, FLOW_SIG_SIZE, basis); + return hash_words((const uint32_t *) flow, sizeof *flow / 4, basis); } /* Information on wildcards for a flow, as a supplement to "struct flow". */ @@ -160,6 +153,7 @@ struct flow_wildcards { uint8_t nw_ttl_mask; /* 1-bit in each significant nw_ttl bit. */ uint8_t zeros[6]; /* Padding field set to zero. */ }; +BUILD_ASSERT_DECL(sizeof(struct flow_wildcards) % 8 == 0); /* Remember to update FLOW_WC_SEQ when updating struct flow_wildcards. */ BUILD_ASSERT_DECL(sizeof(struct flow_wildcards) == 152 && FLOW_WC_SEQ == 17);