# Building SDN-Based Agricultural Vehicular Sensor Networks Based on Extended Open vSwitch
## 3 Module Implementation
### Connection-State Processing Module Implementation  
At present, the OpenFlow specification doesn't contain a match field named connection state between a controller and switches. Therefore, we need to modify the Open vSwitch source code including the kernel and user space codes to implement a connection-state processing module. The implementation process refers to the flow chart shown in Figure 4.  
Figure 4: Connection-state processing module. Step 1 is to track the connection state. Step 2 is to transmit the state detected to the kernel and user space. Step 3 is to support a stateful match in the kernel. Step 4 is to support a stateful match in user space. Firstly, as shown in step 1 (see Figure 4), we need to extend OVS to detect the real-time connection state. Connection state detection builds upon a finite state mechanism and the processing functions of different states are defined in the file lib/rconn.c. In the function run_ACTIVE, an echo message is added to be a keep-alive probe, whose interval and different states' timeout is adjusted dynamically according to the last round-trip time of echo messages. Besides, the last activity time of OpenFlow messages has to be recorded in function rcon_recv. Through the above mechanism, it will get real-time connected state value or disconnected state. When a packet matches a table-miss containing action Controller in the user OpenFlow pipeline, it will call ofproto_dpif_send_packet_in function and Packet-In message will be pushed in the transmit queues, so we detect the rate of enqueueing and then judge whether a state is idle or busy. The connection state enum is defined as follows (Algorithm 1):  
```
enumconnect_state{  connection=1;  disconnection;  busy;  idle; };
```  
**Algorithm 1**  
Secondly, as shown in step 2 (see Figure 4), the module will transfer the state value to both the user and kernel space for composing a lookup key in time. Connection state can be as a datapath attribute to be sent to the kernel datapath by General Netlink API. All of attributes supported by datapath are defined in the openvswitch.h file as mentioned below (Algorithm 2):  
```
enumovs_datapath_attr{  OVS_DP_ATTR_UNSPEC,  OVS_DP_ATTR_NAME, /* name of dp_ifindex netdev */  OVS_DP_ATTR_UPCALL_PID, /* Netlink PID to receive upcalls */  OVS_DP_ATTR_STATS, /* struct ovs_dp_stats */  OVS_DP_ATTR_MEGAFLOW_STATS, /* struct ovs_dp_megaflow_stats */  OVS_DP_ATTR_USER_FEATURES, /* OVS_DP_F_*/  OVS_DP_ATTR_MAX };
```  
**Algorithm 2**  
The new attributes are to be added the above enum definition like OVS_DP_ATTR_CONNECT_STATE. The attribute named OVS_DP_ATTR_CONNECT_STATE can transmit the connection state value into the kernel datapath. Then appropriate changes must be done to datapath/flow_netlink.c file. Thirdly, as shown in step 3 (see Figure 4), we should add the match field into the lookup key structure to support a new match field named connection_state in datapath. In the flow.h file, there is a definition named sw_flow_key concerning the lookup key structure. Sw_flow_key structure has many match field attributes, including L2-L4 fields and some metadata fields, such as ImPort. Part of the structure is shown below. Therefore, the new match field named connection_state has to be added in the above structure. In this case, datapath can call ovs_flow_key_extract function to get lookup key. The lookup key contains not only some fields extracted from packets, but also connection_state from datapath attributes. Then this key is used to match against the flow rules in the kernel datapath. Finally, as shown in step 4 (see Figure 4), the datapath will send up the lookup key and the packet to the user space for OpenFlow table lookup, if there is no match in the datapath. However, the connection state contained in lookup key is old, so we need to add a necessary ofproto-dpif-upcall.c function to update the connection state of the lookup key in user space.