X-Git-Url: http://git.onelab.eu/?a=blobdiff_plain;f=ofproto%2Fofproto-provider.h;h=6286d8197c72f9e03bd73a1631ff129e2ad0339d;hb=e1b1d06afdee407ccfa3c4c257b8dcfbcdd004ff;hp=a74bf9ad7147cb1fa7d5fb5c6bb52e585a883cbd;hpb=751c778501b0e0726cc0c715f3ad2628c19ba0bb;p=sliver-openvswitch.git diff --git a/ofproto/ofproto-provider.h b/ofproto/ofproto-provider.h index a74bf9ad7..6286d8197 100644 --- a/ofproto/ofproto-provider.h +++ b/ofproto/ofproto-provider.h @@ -27,8 +27,11 @@ #include "ofp-errors.h" #include "ofp-util.h" #include "shash.h" +#include "simap.h" #include "timeval.h" +struct match; +struct ofpact; struct ofputil_flow_mod; /* An OpenFlow switch. @@ -59,6 +62,10 @@ struct ofproto { /* Datapath. */ struct hmap ports; /* Contains "struct ofport"s. */ struct shash port_by_name; + unsigned long *ofp_port_ids;/* Bitmap of used OpenFlow port numbers. */ + struct simap ofp_requests; /* OpenFlow port number requests. */ + uint16_t alloc_port_no; /* Last allocated OpenFlow port number. */ + uint16_t max_ports; /* Max possible OpenFlow port num, plus one. */ /* Flow tables. */ struct oftable *tables; @@ -73,6 +80,12 @@ struct ofproto { unsigned int n_pending; /* list_size(&pending). */ struct hmap deletions; /* All OFOPERATION_DELETE "ofoperation"s. */ + /* Flow table operation logging. */ + int n_add, n_delete, n_modify; /* Number of unreported ops of each kind. */ + long long int first_op, last_op; /* Range of times for unreported ops. */ + long long int next_op_report; /* Time to report ops, or LLONG_MAX. */ + long long int op_backoff; /* Earliest time to report ops again. */ + /* Linux VLAN device support (e.g. "eth0.10" for VLAN 10.) * * This is deprecated. It is only for compatibility with broken device @@ -85,6 +98,7 @@ struct ofproto { }; void ofproto_init_tables(struct ofproto *, int n_tables); +void ofproto_init_max_ports(struct ofproto *, uint16_t max_ports); struct ofproto *ofproto_lookup(const char *name); struct ofport *ofproto_get_port(const struct ofproto *, uint16_t ofp_port); @@ -177,8 +191,13 @@ struct rule { struct heap_node evg_node; /* In eviction_group's "rules" heap. */ struct eviction_group *eviction_group; /* NULL if not in any group. */ - union ofp_action *actions; /* OpenFlow actions. */ - int n_actions; /* Number of elements in actions[]. */ + struct ofpact *ofpacts; /* Sequence of "struct ofpacts". */ + unsigned int ofpacts_len; /* Size of 'ofpacts', in bytes. */ + + /* Flow monitors. */ + enum nx_flow_monitor_flags monitor_flags; + uint64_t add_seqno; /* Sequence number when added. */ + uint64_t modify_seqno; /* Sequence number when changed. */ }; static inline struct rule * @@ -191,9 +210,15 @@ void ofproto_rule_update_used(struct rule *, long long int used); void ofproto_rule_expire(struct rule *, uint8_t reason); void ofproto_rule_destroy(struct rule *); +bool ofproto_rule_has_out_port(const struct rule *, uint16_t out_port); + void ofoperation_complete(struct ofoperation *, enum ofperr); struct rule *ofoperation_get_victim(struct ofoperation *); +bool ofoperation_has_out_port(const struct ofoperation *, uint16_t out_port); + +bool ofproto_rule_is_hidden(const struct rule *); + /* ofproto class structure, to be defined by each ofproto implementation. * * @@ -298,6 +323,16 @@ struct ofproto_class { /* ## Factory Functions ## */ /* ## ----------------- ## */ + /* Initializes provider. The caller may pass in 'iface_hints', + * which contains an shash of "struct iface_hint" elements indexed + * by the interface's name. The provider may use these hints to + * describe the startup configuration in order to reinitialize its + * state. The caller owns the provided data, so a provider must + * make copies of anything required. An ofproto provider must + * remove any existing state that is not described by the hint, and + * may choose to remove it all. */ + void (*init)(const struct shash *iface_hints); + /* Enumerates the types of all support ofproto types into 'types'. The * caller has already initialized 'types' and other ofproto classes might * already have added names to it. */ @@ -346,6 +381,11 @@ struct ofproto_class { * ->construct() should delete flows from the underlying datapath, if * necessary, rather than populating the tables. * + * If the ofproto knows the maximum port number that the datapath can have, + * then it can call ofproto_init_max_ports(). If it does so, then the + * client will ensure that the actions it allows to be used through + * OpenFlow do not refer to ports above that maximum number. + * * Only one ofproto instance needs to be supported for any given datapath. * If a datapath is already open as part of one "ofproto", then another * attempt to "construct" the same datapath as part of another ofproto is @@ -380,6 +420,9 @@ struct ofproto_class { * - Call ofproto_rule_expire() for each OpenFlow flow that has reached * its hard_timeout or idle_timeout, to expire the flow. * + * (But rules that are part of a pending operation, e.g. rules for + * which ->pending is true, may not expire.) + * * Returns 0 if successful, otherwise a positive errno value. */ int (*run)(struct ofproto *ofproto); @@ -396,6 +439,13 @@ struct ofproto_class { * poll-loop.h. */ void (*wait)(struct ofproto *ofproto); + /* Adds some memory usage statistics for the implementation of 'ofproto' + * into 'usage', for use with memory_report(). + * + * This function is optional. */ + void (*get_memory_usage)(const struct ofproto *ofproto, + struct simap *usage); + /* Every "struct rule" in 'ofproto' is about to be deleted, one by one. * This function may prepare for that, for example by clearing state in * advance. It should *not* actually delete any "struct rule"s from @@ -427,7 +477,17 @@ struct ofproto_class { * * - 'name' to "table#" where # is the table ID. * - * - 'wildcards' to OFPFW_ALL. + * - 'match' and 'wildcards' to OFPXMT12_MASK. + * + * - 'write_actions' and 'apply_actions' to OFPAT12_OUTPUT. + * + * - 'write_setfields' and 'apply_setfields' to OFPXMT12_MASK. + * + * - 'metadata_match' and 'metadata_write' to UINT64_MAX. + * + * - 'instructions' to OFPIT11_ALL. + * + * - 'config' to OFPTC11_TABLE_MISS_MASK. * * - 'max_entries' to 1,000,000. * @@ -443,6 +503,21 @@ struct ofproto_class { * - 'wildcards' to the set of wildcards actually supported by the table * (if it doesn't support all OpenFlow wildcards). * + * - 'instructions' to set the instructions actually supported by + * the table. + * + * - 'write_actions' to set the write actions actually supported by + * the table (if it doesn't support all OpenFlow actions). + * + * - 'apply_actions' to set the apply actions actually supported by + * the table (if it doesn't support all OpenFlow actions). + * + * - 'write_setfields' to set the write setfields actually supported by + * the table. + * + * - 'apply_setfields' to set the apply setfields actually supported by + * the table. + * * - 'max_entries' to the maximum number of flows actually supported by * the hardware. * @@ -452,10 +527,10 @@ struct ofproto_class { * - 'matched_count' to the number of packets looked up in this flow * table so far that matched one of the flow entries. * - * Keep in mind that all of the members of struct ofp_table_stats are in - * network byte order. + * All of the members of struct ofp12_table_stats are in network byte + * order. */ - void (*get_tables)(struct ofproto *ofproto, struct ofp_table_stats *ots); + void (*get_tables)(struct ofproto *ofproto, struct ofp12_table_stats *ots); /* ## ---------------- ## */ /* ## ofport Functions ## */ @@ -464,6 +539,8 @@ struct ofproto_class { /* Life-cycle functions for a "struct ofport" (see "Life Cycle" above). * * ->port_construct() should not modify any base members of the ofport. + * An ofproto implementation should use the 'ofp_port' member of + * "struct ofport" as the OpenFlow port number. * * ofports are managed by the base ofproto code. The ofproto * implementation should only create and destroy them in response to calls @@ -522,14 +599,14 @@ struct ofproto_class { const char *devname, struct ofproto_port *port); /* Attempts to add 'netdev' as a port on 'ofproto'. Returns 0 if - * successful, otherwise a positive errno value. If successful, sets - * '*ofp_portp' to the new port's port number. + * successful, otherwise a positive errno value. The caller should + * inform the implementation of the OpenFlow port through the + * ->port_construct() method. * * It doesn't matter whether the new port will be returned by a later call * to ->port_poll(); the implementation may do whatever is more * convenient. */ - int (*port_add)(struct ofproto *ofproto, struct netdev *netdev, - uint16_t *ofp_portp); + int (*port_add)(struct ofproto *ofproto, struct netdev *netdev); /* Deletes port number 'ofp_port' from the datapath for 'ofproto'. Returns * 0 if successful, otherwise a positive errno value. @@ -665,24 +742,22 @@ struct ofproto_class { /* ## OpenFlow Rule Functions ## */ /* ## ----------------------- ## */ - - - /* Chooses an appropriate table for 'cls_rule' within 'ofproto'. On + /* Chooses an appropriate table for 'match' within 'ofproto'. On * success, stores the table ID into '*table_idp' and returns 0. On * failure, returns an OpenFlow error code. * - * The choice of table should be a function of 'cls_rule' and 'ofproto''s + * The choice of table should be a function of 'match' and 'ofproto''s * datapath capabilities. It should not depend on the flows already in * 'ofproto''s flow tables. Failure implies that an OpenFlow rule with - * 'cls_rule' as its matching condition can never be inserted into - * 'ofproto', even starting from an empty flow table. + * 'match' as its matching condition can never be inserted into 'ofproto', + * even starting from an empty flow table. * * If multiple tables are candidates for inserting the flow, the function * should choose one arbitrarily (but deterministically). * * If this function is NULL then table 0 is always chosen. */ enum ofperr (*rule_choose_table)(const struct ofproto *ofproto, - const struct cls_rule *cls_rule, + const struct match *match, uint8_t *table_idp); /* Life-cycle functions for a "struct rule" (see "Life Cycle" above). @@ -767,13 +842,7 @@ struct ofproto_class { * registers, then it is an error if 'rule->cr' does not wildcard all * registers. * - * - Validate that 'rule->actions' and 'rule->n_actions' are well-formed - * OpenFlow actions that the datapath can correctly implement. The - * validate_actions() function (in ofp-util.c) can be useful as a model - * for action validation, but it accepts all of the OpenFlow actions - * that OVS understands. If your ofproto implementation only - * implements a subset of those, then you should implement your own - * action validation. + * - Validate that the datapath can correctly implement 'rule->ofpacts'. * * - If the rule is valid, update the datapath flow table, adding the new * rule or replacing the existing one. @@ -839,7 +908,7 @@ struct ofproto_class { * * 'flow' reflects the flow information for 'packet'. All of the * information in 'flow' is extracted from 'packet', except for - * flow->tun_id and flow->in_port, which are assigned the correct values + * flow->tunnel and flow->in_port, which are assigned the correct values * for the incoming packet. The register values are zeroed. 'packet''s * header pointers (e.g. packet->l3) are appropriately initialized. * @@ -855,8 +924,8 @@ struct ofproto_class { * * ->rule_modify_actions() should set the following in motion: * - * - Validate that the actions now in 'rule' are well-formed OpenFlow - * actions that the datapath can correctly implement. + * - Validate that the datapath can correctly implement the actions now + * in 'rule'. * * - Update the datapath flow table with the new actions. * @@ -904,33 +973,33 @@ struct ofproto_class { enum ofp_config_flags frag_handling); /* Implements the OpenFlow OFPT_PACKET_OUT command. The datapath should - * execute the 'n_actions' in the 'actions' array on 'packet'. + * execute the 'ofpacts_len' bytes of "struct ofpacts" in 'ofpacts'. * - * The caller retains ownership of 'packet', so ->packet_out() should not - * modify or free it. + * The caller retains ownership of 'packet' and of 'ofpacts', so + * ->packet_out() should not modify or free them. * - * This function must validate that the 'n_actions' elements in 'actions' - * are well-formed OpenFlow actions that can be correctly implemented by - * the datapath. If not, then it should return an OpenFlow error code. + * This function must validate that it can correctly implement 'ofpacts'. + * If not, then it should return an OpenFlow error code. * * 'flow' reflects the flow information for 'packet'. All of the * information in 'flow' is extracted from 'packet', except for - * flow->in_port (see below). flow->tun_id and its register values are + * flow->in_port (see below). flow->tunnel and its register values are * zeroed. * * flow->in_port comes from the OpenFlow OFPT_PACKET_OUT message. The * implementation should reject invalid flow->in_port values by returning - * OFPERR_NXBRC_BAD_IN_PORT. For consistency, the implementation should - * consider valid for flow->in_port any value that could possibly be seen - * in a packet that it passes to connmgr_send_packet_in(). Ideally, even - * an implementation that never generates packet-ins (e.g. due to hardware - * limitations) should still allow flow->in_port values for every possible - * physical port and OFPP_LOCAL. The only virtual ports (those above - * OFPP_MAX) that the caller will ever pass in as flow->in_port, other than - * OFPP_LOCAL, are OFPP_NONE and OFPP_CONTROLLER. The implementation - * should allow both of these, treating each of them as packets generated - * by the controller as opposed to packets originating from some switch - * port. + * OFPERR_OFPBRC_BAD_PORT. (If the implementation called + * ofproto_init_max_ports(), then the client will reject these ports + * itself.) For consistency, the implementation should consider valid for + * flow->in_port any value that could possibly be seen in a packet that it + * passes to connmgr_send_packet_in(). Ideally, even an implementation + * that never generates packet-ins (e.g. due to hardware limitations) + * should still allow flow->in_port values for every possible physical port + * and OFPP_LOCAL. The only virtual ports (those above OFPP_MAX) that the + * caller will ever pass in as flow->in_port, other than OFPP_LOCAL, are + * OFPP_NONE and OFPP_CONTROLLER. The implementation should allow both of + * these, treating each of them as packets generated by the controller as + * opposed to packets originating from some switch port. * * (Ordinarily the only effect of flow->in_port is on output actions that * involve the input port, such as actions that output to OFPP_IN_PORT, @@ -943,8 +1012,8 @@ struct ofproto_class { * Returns 0 if successful, otherwise an OpenFlow error code. */ enum ofperr (*packet_out)(struct ofproto *ofproto, struct ofpbuf *packet, const struct flow *flow, - const union ofp_action *actions, - size_t n_actions); + const struct ofpact *ofpacts, + size_t ofpacts_len); /* ## ------------------------- ## */ /* ## OFPP_NORMAL configuration ## */ @@ -989,6 +1058,15 @@ struct ofproto_class { * not support CFM. */ int (*get_cfm_fault)(const struct ofport *ofport); + /* Check the operational status reported by the remote CFM endpoint of + * 'ofp_port' Returns 1 if operationally up, 0 if operationally down, and + * -1 if CFM is not enabled on 'ofp_port' or does not support operational + * status. + * + * This function may be a null pointer if the ofproto implementation does + * not support CFM. */ + int (*get_cfm_opup)(const struct ofport *ofport); + /* Gets the MPIDs of the remote maintenance points broadcasting to * 'ofport'. Populates 'rmps' with a provider owned array of MPIDs, and * 'n_rmps' with the number of MPIDs in 'rmps'. Returns a number less than @@ -1180,9 +1258,11 @@ enum { OFPROTO_POSTPONE = 1 << 16 }; BUILD_ASSERT_DECL(OFPROTO_POSTPONE < OFPERR_OFS); int ofproto_flow_mod(struct ofproto *, const struct ofputil_flow_mod *); -void ofproto_add_flow(struct ofproto *, const struct cls_rule *, - const union ofp_action *, size_t n_actions); -bool ofproto_delete_flow(struct ofproto *, const struct cls_rule *); +void ofproto_add_flow(struct ofproto *, const struct match *, + unsigned int priority, + const struct ofpact *ofpacts, size_t ofpacts_len); +bool ofproto_delete_flow(struct ofproto *, + const struct match *, unsigned int priority); void ofproto_flush_flows(struct ofproto *); #endif /* ofproto/ofproto-provider.h */