trema 0.3.16 → 0.3.17

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (51) hide show
  1. checksums.yaml +5 -5
  2. data/.gitignore +1 -0
  3. data/.rvmrc +52 -0
  4. data/.travis.yml +3 -0
  5. data/Gemfile +1 -1
  6. data/Rakefile +259 -1
  7. data/Rantfile +79 -216
  8. data/features/.nav +12 -0
  9. data/features/dsl/switch_port_specifier.feature +15 -0
  10. data/features/examples/switch-event/C-add_forward_entry.feature +130 -0
  11. data/features/examples/switch-event/C-delete_forward_entry.feature +97 -0
  12. data/features/examples/switch-event/C-dump_forward_entries.feature +80 -0
  13. data/features/examples/switch-event/C-set_forward_entries.feature +85 -0
  14. data/features/examples/switch-event/README.md +40 -0
  15. data/features/examples/switch-event/add_forward_entry.feature +142 -0
  16. data/features/examples/switch-event/delete_forward_entry.feature +142 -0
  17. data/features/examples/switch-event/dump_forward_entries.feature +91 -0
  18. data/features/examples/switch-event/set_forward_entries.feature +90 -0
  19. data/features/support/hooks.rb +1 -0
  20. data/ruby/rake/c/dependency.rb +42 -0
  21. data/ruby/rake/c/library-task.rb +142 -0
  22. data/ruby/rake/c/shared-library-task.rb +38 -0
  23. data/ruby/rake/c/static-library-task.rb +32 -0
  24. data/ruby/trema/path.rb +1 -0
  25. data/ruby/trema/switch-event.c +647 -0
  26. data/{src/switch_manager/management_interface.h → ruby/trema/switch-event.h} +7 -21
  27. data/ruby/trema/trema.c +2 -0
  28. data/ruby/trema/version.rb +1 -1
  29. data/spec/spec_helper.rb +26 -2
  30. data/src/examples/switch_event_config/.gitignore +7 -0
  31. data/src/examples/switch_event_config/add_forward_entry.c +227 -0
  32. data/src/examples/switch_event_config/delete_forward_entry.c +226 -0
  33. data/src/examples/switch_event_config/dump_forward_entries.c +190 -0
  34. data/src/examples/switch_event_config/set_forward_entries.c +210 -0
  35. data/src/lib/event_forward_interface.c +783 -0
  36. data/src/lib/event_forward_interface.h +138 -0
  37. data/src/lib/trema.h +1 -0
  38. data/src/lib/utility.c +13 -1
  39. data/src/lib/utility.h +3 -0
  40. data/src/switch_manager/event_forward_entry_manipulation.c +120 -0
  41. data/src/switch_manager/event_forward_entry_manipulation.h +31 -0
  42. data/src/switch_manager/secure_channel_listener.c +23 -3
  43. data/src/switch_manager/switch.c +99 -29
  44. data/src/switch_manager/switch_manager.c +176 -3
  45. data/src/switch_manager/switch_manager.h +4 -0
  46. data/src/switch_manager/switch_option.c +30 -0
  47. data/src/switch_manager/switch_option.h +41 -0
  48. data/trema.gemspec +2 -1
  49. data/unittests/lib/event_forward_interface_test.c +1646 -0
  50. data/unittests/lib/utility_test.c +23 -1
  51. metadata +48 -10
@@ -0,0 +1,138 @@
1
+ /*
2
+ * Copyright (C) 2013 NEC Corporation
3
+ *
4
+ * This program is free software; you can redistribute it and/or modify
5
+ * it under the terms of the GNU General Public License, version 2, as
6
+ * published by the Free Software Foundation.
7
+ *
8
+ * This program is distributed in the hope that it will be useful,
9
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
10
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11
+ * GNU General Public License for more details.
12
+ *
13
+ * You should have received a copy of the GNU General Public License along
14
+ * with this program; if not, write to the Free Software Foundation, Inc.,
15
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
16
+ */
17
+
18
+ #ifndef EVENT_FORWARD_INTERFACE_H_
19
+ #define EVENT_FORWARD_INTERFACE_H_
20
+
21
+
22
+ #include "buffer.h"
23
+ #include "linked_list.h"
24
+
25
+ // management interface application_ids
26
+ enum switch_management_command {
27
+ // switch only
28
+ DUMP_XID_TABLE = 0,
29
+ DUMP_COOKIE_TABLE,
30
+ TOGGLE_COOKIE_AGING,
31
+
32
+ // switch manager/daemon
33
+ EVENT_FORWARD_ENTRY_ADD,
34
+ EVENT_FORWARD_ENTRY_DELETE,
35
+ EVENT_FORWARD_ENTRY_DUMP,
36
+ EVENT_FORWARD_ENTRY_SET,
37
+
38
+ // switch manager only
39
+ EFI_GET_SWLIST,
40
+ };
41
+
42
+ enum efi_event_type {
43
+ EVENT_FORWARD_TYPE_VENDOR = 0,
44
+ EVENT_FORWARD_TYPE_PACKET_IN,
45
+ EVENT_FORWARD_TYPE_PORT_STATUS,
46
+ EVENT_FORWARD_TYPE_STATE_NOTIFY
47
+ };
48
+
49
+ enum efi_result {
50
+ EFI_OPERATION_SUCCEEDED = 0,
51
+ EFI_OPERATION_FAILED,
52
+ };
53
+
54
+ // messenger message data structure
55
+ typedef struct {
56
+ // enum efi_event_type
57
+ uint8_t type;
58
+ uint8_t pad[3];
59
+ // Number of element in service_list. 0 for dump, 1 for add/delete, N for set operation.
60
+ uint32_t n_services;
61
+ // e.g. "service1\0service2\0"
62
+ char service_list[0];
63
+ } __attribute__( ( packed ) ) event_forward_operation_request;
64
+
65
+ typedef struct {
66
+ // enum efi_event_type
67
+ uint8_t type;
68
+ // enum efi_result
69
+ uint8_t result;
70
+ uint8_t pad[2];
71
+ uint32_t n_services;
72
+ // service list after operation
73
+ char service_list[0];
74
+ } __attribute__( ( packed ) ) event_forward_operation_reply;
75
+
76
+
77
+ // struct for user API
78
+ typedef struct {
79
+ enum efi_result result;
80
+ uint32_t n_services;
81
+ // service list after operation.
82
+ const char **services;
83
+ } event_forward_operation_result;
84
+
85
+
86
+ // High level API callback function signature
87
+ typedef void ( *event_forward_entry_to_all_callback )(
88
+ enum efi_result result,
89
+ void *user_data
90
+ );
91
+
92
+
93
+ // Low level API callback function signature
94
+ typedef void ( *event_forward_entry_operation_callback )(
95
+ event_forward_operation_result result,
96
+ void *user_data
97
+ );
98
+
99
+
100
+ typedef void ( *switch_list_request_callback )(
101
+ // NULL if failed
102
+ uint64_t* dpids,
103
+ size_t n_dpids,
104
+ void *user_data
105
+ );
106
+
107
+
108
+ // setup/teardown messenger channel
109
+ bool init_event_forward_interface( void );
110
+ bool finalize_event_forward_interface( void );
111
+
112
+
113
+ // High level API (calls Low level API for switch manager and existing switch daemons)
114
+ bool add_event_forward_entry_to_all_switches( enum efi_event_type type, const char* service_name, event_forward_entry_to_all_callback callback, void* user_data );
115
+ bool delete_event_forward_entry_to_all_switches( enum efi_event_type type, const char* service_name, event_forward_entry_to_all_callback callback, void* user_data );
116
+
117
+
118
+ // Low level API for switch manager
119
+ bool set_switch_manager_event_forward_entries( enum efi_event_type type, list_element* service_list, event_forward_entry_operation_callback callback, void* user_data );
120
+ bool add_switch_manager_event_forward_entry( enum efi_event_type type, const char* service_name, event_forward_entry_operation_callback callback, void* user_data );
121
+ bool delete_switch_manager_event_forward_entry( enum efi_event_type type, const char* service_name, event_forward_entry_operation_callback callback, void* user_data );
122
+ bool dump_switch_manager_event_forward_entries( enum efi_event_type type, event_forward_entry_operation_callback callback, void* user_data );
123
+
124
+
125
+ // Low level API for switch daemon
126
+ bool set_switch_event_forward_entries( uint64_t dpid, enum efi_event_type type, list_element* service_list, event_forward_entry_operation_callback callback, void* user_data );
127
+ bool add_switch_event_forward_entry( uint64_t dpid, enum efi_event_type type, const char* service_name, event_forward_entry_operation_callback callback, void* user_data );
128
+ bool delete_switch_event_forward_entry( uint64_t dpid, enum efi_event_type type, const char* service_name, event_forward_entry_operation_callback callback, void* user_data );
129
+ bool dump_switch_event_forward_entries( uint64_t dpid, enum efi_event_type type, event_forward_entry_operation_callback callback, void* user_data );
130
+
131
+
132
+ // internal utilities
133
+ buffer* create_event_forward_operation_request( buffer* buf, enum efi_event_type, list_element* service_list );
134
+ buffer* create_event_forward_operation_reply( enum efi_event_type, enum efi_result, list_element* service_list );
135
+
136
+ bool send_efi_switch_list_request( switch_list_request_callback callback, void* user_data );
137
+
138
+ #endif /* EVENT_FORWARD_INTERFACE_H_ */
data/src/lib/trema.h CHANGED
@@ -28,6 +28,7 @@
28
28
  #include "checks.h"
29
29
  #include "doubly_linked_list.h"
30
30
  #include "etherip.h"
31
+ #include "event_forward_interface.h"
31
32
  #include "event_handler.h"
32
33
  #include "hash_table.h"
33
34
  #include "linked_list.h"
data/src/lib/utility.c CHANGED
@@ -31,7 +31,7 @@
31
31
  #include "log.h"
32
32
  #include "trema_wrapper.h"
33
33
  #include "utility.h"
34
-
34
+ #include "wrapper.h"
35
35
 
36
36
  static void
37
37
  _die( const char *format, ... ) {
@@ -594,6 +594,18 @@ get_checksum( uint16_t *pos, uint32_t size ) {
594
594
  }
595
595
 
596
596
 
597
+ void
598
+ xfree_data( void *data, void *user_data ) {
599
+ UNUSED( user_data );
600
+ xfree( data );
601
+ }
602
+
603
+
604
+ bool
605
+ string_equal( void *data, void *user_data ) {
606
+ return strcmp( data, user_data ) == 0;
607
+ }
608
+
597
609
  /*
598
610
  * Local variables:
599
611
  * c-basic-offset: 2
data/src/lib/utility.h CHANGED
@@ -54,6 +54,9 @@ bool actions_to_string( const struct ofp_action_header *actions, uint16_t action
54
54
 
55
55
  uint16_t get_checksum( uint16_t *pos, uint32_t size );
56
56
 
57
+ void xfree_data( void *data, void *user_data );
58
+
59
+ bool string_equal( void *data, void *user_data );
57
60
 
58
61
  #endif // UTILITY_H
59
62
 
@@ -0,0 +1,120 @@
1
+ /*
2
+ * Copyright (C) 2013 NEC Corporation
3
+ *
4
+ * This program is free software; you can redistribute it and/or modify
5
+ * it under the terms of the GNU General Public License, version 2, as
6
+ * published by the Free Software Foundation.
7
+ *
8
+ * This program is distributed in the hope that it will be useful,
9
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
10
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11
+ * GNU General Public License for more details.
12
+ *
13
+ * You should have received a copy of the GNU General Public License along
14
+ * with this program; if not, write to the Free Software Foundation, Inc.,
15
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
16
+ */
17
+
18
+ #include <assert.h>
19
+ #include "trema.h"
20
+ #include "event_forward_entry_manipulation.h"
21
+
22
+
23
+ void
24
+ management_event_forward_entry_add( list_element **service_list,
25
+ const event_forward_operation_request *request, size_t request_len ) {
26
+ if ( request->n_services == 0 ) return;
27
+ if ( request->n_services > 1 ) {
28
+ warn( "Only 1 service name expected for EVENT_FWD_ENTRY_ADD. Ignoring others." );
29
+ }
30
+ const size_t service_name_len = request_len - offsetof( event_forward_operation_request, service_list );
31
+ if ( service_name_len == 0 ) return;
32
+
33
+ char *service_name = xcalloc( service_name_len + 1, sizeof( char ) );
34
+ strncpy( service_name, request->service_list, service_name_len );
35
+
36
+ const char *match = find_list_custom( *service_list, string_equal, service_name );
37
+ if ( match == NULL ) {
38
+ info( "Adding '%s' to event filter.", service_name );
39
+ insert_in_front( service_list, service_name );
40
+ }
41
+ else {
42
+ // already there
43
+ xfree( service_name );
44
+ }
45
+ }
46
+
47
+
48
+ void
49
+ management_event_forward_entry_delete( list_element **service_list,
50
+ const event_forward_operation_request *request, size_t request_len ) {
51
+ if ( request->n_services == 0 ) return;
52
+ if ( request->n_services > 1 ) {
53
+ warn( "Only 1 service name expected for EVENT_FWD_ENTRY_DELETE. Ignoring others." );
54
+ }
55
+ const size_t service_name_len = request_len - offsetof( event_forward_operation_request, service_list );
56
+ if ( service_name_len == 0 ) return;
57
+
58
+ char *service_name = xcalloc( service_name_len + 1, sizeof( char ) );
59
+ strncpy( service_name, request->service_list, service_name_len );
60
+
61
+ const char *match = find_list_custom( *service_list, string_equal, service_name );
62
+ if ( match == NULL ) {
63
+ // didn't exist
64
+ xfree( service_name );
65
+ }
66
+ else {
67
+ info( "Deleting '%s' from event filter.", service_name );
68
+ bool success = delete_element( service_list, match );
69
+ assert( success );
70
+ }
71
+ }
72
+
73
+
74
+ void
75
+ management_event_forward_entries_set( list_element **service_list,
76
+ const event_forward_operation_request *request, size_t request_len ) {
77
+ const size_t service_name_list_len = request_len - offsetof( event_forward_operation_request, service_list );
78
+
79
+ const char **service_name_list = xcalloc( request->n_services, sizeof( char * ) );
80
+
81
+ // split null terminated string list.
82
+ unsigned int n_services = 0;
83
+ const char *name_begin = request->service_list;
84
+ for ( size_t i = 0 ; i < service_name_list_len ; ++i ) {
85
+ if ( request->service_list[ i ] == '\0' ) {
86
+ service_name_list[ n_services++ ] = name_begin;
87
+ if ( n_services == request->n_services ) {
88
+ if ( i + 1 != service_name_list_len ) {
89
+ warn( "Expecting %d name(s) for EVENT_FWD_ENTRY_SET, but more exist. Ignoring.", request->n_services );
90
+ }
91
+ break;
92
+ }
93
+ name_begin = &request->service_list[ i + 1 ];
94
+ }
95
+ }
96
+ if ( n_services != request->n_services ) {
97
+ warn( "Expected %d name(s) for EVENT_FWD_ENTRY_SET, but found %d.", request->n_services, n_services );
98
+ }
99
+
100
+ info( "Resetting event filter(s)." );
101
+ // clear current list
102
+ iterate_list( *service_list, xfree_data, NULL );
103
+ delete_list( *service_list );
104
+ create_list( service_list );
105
+
106
+ // set new list
107
+ for ( unsigned int i = 0 ; i < n_services ; ++i ) {
108
+ const size_t service_name_len = strlen( service_name_list[ i ] );
109
+ if ( service_name_len == 0 ) {
110
+ warn( "Ignoring 0 length service name in EVENT_FWD_ENTRY_SET" );
111
+ continue;
112
+ }
113
+ info( " Adding '%s' to event filter.", service_name_list[ i ] );
114
+ append_to_tail( service_list, xstrdup( service_name_list[ i ] ) );
115
+ }
116
+
117
+ xfree( service_name_list );
118
+ }
119
+
120
+
@@ -0,0 +1,31 @@
1
+ /*
2
+ * Copyright (C) 2013 NEC Corporation
3
+ *
4
+ * This program is free software; you can redistribute it and/or modify
5
+ * it under the terms of the GNU General Public License, version 2, as
6
+ * published by the Free Software Foundation.
7
+ *
8
+ * This program is distributed in the hope that it will be useful,
9
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
10
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11
+ * GNU General Public License for more details.
12
+ *
13
+ * You should have received a copy of the GNU General Public License along
14
+ * with this program; if not, write to the Free Software Foundation, Inc.,
15
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
16
+ */
17
+
18
+ #ifndef EVENT_FORWARD_ENTRY_MANIPULATION_H_
19
+ #define EVENT_FORWARD_ENTRY_MANIPULATION_H_
20
+
21
+ #include "event_forward_interface.h"
22
+
23
+ void management_event_forward_entry_add( list_element** service_list,
24
+ const event_forward_operation_request* request, size_t request_len );
25
+ void management_event_forward_entry_delete( list_element** service_list,
26
+ const event_forward_operation_request* request, size_t request_len );
27
+ void management_event_forward_entries_set( list_element** service_list,
28
+ const event_forward_operation_request* request, size_t request_len );
29
+
30
+
31
+ #endif /* EVENT_FORWARD_ENTRY_MANIPULATION_H_ */
@@ -30,6 +30,7 @@
30
30
  #include "trema.h"
31
31
  #include "secure_channel_listener.h"
32
32
  #include "switch_manager.h"
33
+ #include "switch_option.h"
33
34
 
34
35
 
35
36
  const int LISTEN_SOCK_MAX = 128;
@@ -165,7 +166,13 @@ secure_channel_listen_start( struct listener_info *listener_info ) {
165
166
 
166
167
  static char **
167
168
  make_switch_daemon_args( struct listener_info *listener_info, struct sockaddr_in *addr, int accept_fd ) {
168
- int argc = SWITCH_MANAGER_DEFAULT_ARGC + listener_info->switch_daemon_argc + 1;
169
+ const int argc = SWITCH_MANAGER_DEFAULT_ARGC
170
+ + listener_info->switch_daemon_argc
171
+ + ( int ) list_length_of( listener_info->vendor_service_name_list )
172
+ + ( int ) list_length_of( listener_info->packetin_service_name_list )
173
+ + ( int ) list_length_of( listener_info->portstatus_service_name_list )
174
+ + ( int ) list_length_of( listener_info->state_service_name_list )
175
+ + 1;
169
176
  char **argv = xcalloc( ( size_t ) argc, sizeof( char * ) );
170
177
  char *command_name = xasprintf( "%s%s:%u", SWITCH_MANAGER_COMMAND_PREFIX,
171
178
  inet_ntoa( addr->sin_addr ),
@@ -191,6 +198,19 @@ make_switch_daemon_args( struct listener_info *listener_info, struct sockaddr_in
191
198
  argv[ i ] = xstrdup( listener_info->switch_daemon_argv[ j ] );
192
199
  }
193
200
 
201
+ for ( list_element *e = listener_info->vendor_service_name_list; e != NULL; e = e->next, ++i ) {
202
+ argv[ i ] = xasprintf( VENDOR_PREFIX "%s", e->data );
203
+ }
204
+ for ( list_element *e = listener_info->packetin_service_name_list; e != NULL; e = e->next, ++i ) {
205
+ argv[ i ] = xasprintf( PACKET_IN_PREFIX "%s", e->data );
206
+ }
207
+ for ( list_element *e = listener_info->portstatus_service_name_list; e != NULL; e = e->next, ++i ) {
208
+ argv[ i ] = xasprintf( PORTSTATUS_PREFIX "%s", e->data );
209
+ }
210
+ for ( list_element *e = listener_info->state_service_name_list; e != NULL; e = e->next, ++i ) {
211
+ argv[ i ] = xasprintf( STATE_PREFIX "%s", e->data );
212
+ }
213
+
194
214
  return argv;
195
215
  }
196
216
 
@@ -199,9 +219,9 @@ static void
199
219
  free_switch_daemon_args( char **argv ) {
200
220
  int i;
201
221
  for ( i = 0; argv[ i ] != NULL; i++ ) {
202
- free( argv[ i ] );
222
+ xfree( argv[ i ] );
203
223
  }
204
- free( argv );
224
+ xfree( argv );
205
225
  }
206
226
 
207
227
 
@@ -26,9 +26,9 @@
26
26
  #include <stdio.h>
27
27
  #include <string.h>
28
28
  #include <unistd.h>
29
+ #include <assert.h>
29
30
  #include "trema.h"
30
31
  #include "cookie_table.h"
31
- #include "management_interface.h"
32
32
  #include "message_queue.h"
33
33
  #include "messenger.h"
34
34
  #include "ofpmsg_send.h"
@@ -38,7 +38,8 @@
38
38
  #include "service_interface.h"
39
39
  #include "switch.h"
40
40
  #include "xid_table.h"
41
-
41
+ #include "switch_option.h"
42
+ #include "event_forward_entry_manipulation.h"
42
43
 
43
44
  #define SUB_TIMESPEC( _a, _b, _return ) \
44
45
  do { \
@@ -52,23 +53,6 @@
52
53
  while ( 0 )
53
54
 
54
55
 
55
- enum long_options_val {
56
- NO_FLOW_CLEANUP_LONG_OPTION_VALUE = 1,
57
- NO_COOKIE_TRANSLATION_LONG_OPTION_VALUE = 2,
58
- NO_PACKET_IN_LONG_OPTION_VALUE = 3,
59
- };
60
-
61
- static struct option long_options[] = {
62
- { "socket", 1, NULL, 's' },
63
- { "no-flow-cleanup", 0, NULL, NO_FLOW_CLEANUP_LONG_OPTION_VALUE },
64
- { "no-cookie-translation", 0, NULL, NO_COOKIE_TRANSLATION_LONG_OPTION_VALUE },
65
- { "no-packet_in", 0, NULL, NO_PACKET_IN_LONG_OPTION_VALUE },
66
- { NULL, 0, NULL, 0 },
67
- };
68
-
69
- static char short_options[] = "s:";
70
-
71
-
72
56
  struct switch_info switch_info;
73
57
 
74
58
  static const time_t COOKIE_TABLE_AGING_INTERVAL = 3600; // sec.
@@ -138,7 +122,7 @@ option_parser( int argc, char *argv[] ) {
138
122
  switch_info.flow_cleanup = true;
139
123
  switch_info.cookie_translation = true;
140
124
  switch_info.deny_packet_in_on_startup = false;
141
- while ( ( c = getopt_long( argc, argv, short_options, long_options, NULL ) ) != -1 ) {
125
+ while ( ( c = getopt_long( argc, argv, switch_short_options, switch_long_options, NULL ) ) != -1 ) {
142
126
  switch ( c ) {
143
127
  case 's':
144
128
  switch_info.secure_channel_fd = strtofd( optarg );
@@ -498,6 +482,20 @@ switch_event_disconnected( struct switch_info *sw_info ) {
498
482
  }
499
483
  flush_messenger();
500
484
 
485
+ // free service name list
486
+ iterate_list( sw_info->vendor_service_name_list, xfree_data, NULL );
487
+ delete_list( sw_info->vendor_service_name_list );
488
+ sw_info->vendor_service_name_list = NULL;
489
+ iterate_list( sw_info->packetin_service_name_list, xfree_data, NULL );
490
+ delete_list( sw_info->packetin_service_name_list );
491
+ sw_info->packetin_service_name_list = NULL;
492
+ iterate_list( sw_info->portstatus_service_name_list, xfree_data, NULL );
493
+ delete_list( sw_info->portstatus_service_name_list );
494
+ sw_info->portstatus_service_name_list = NULL;
495
+ iterate_list( sw_info->state_service_name_list, xfree_data, NULL );
496
+ delete_list( sw_info->state_service_name_list );
497
+ sw_info->state_service_name_list = NULL;
498
+
501
499
  stop_trema();
502
500
 
503
501
  return 0;
@@ -539,10 +537,75 @@ switch_event_recv_error( struct switch_info *sw_info ) {
539
537
  }
540
538
 
541
539
 
540
+ static void
541
+ management_event_forward_entry_operation( const messenger_context_handle *handle, uint32_t command, event_forward_operation_request *req, size_t data_len ) {
542
+
543
+ debug( "management efi command:%#x, type:%#x, n_services:%d", command, req->type, req->n_services );
544
+
545
+ list_element **subject = NULL;
546
+ switch ( req->type ) {
547
+ case EVENT_FORWARD_TYPE_VENDOR:
548
+ info( "Managing vendor event." );
549
+ subject = &switch_info.vendor_service_name_list;
550
+ break;
551
+
552
+ case EVENT_FORWARD_TYPE_PACKET_IN:
553
+ info( "Managing packet_in event." );
554
+ subject = &switch_info.packetin_service_name_list;
555
+ break;
556
+
557
+ case EVENT_FORWARD_TYPE_PORT_STATUS:
558
+ info( "Managing port_status event." );
559
+ subject = &switch_info.portstatus_service_name_list;
560
+ break;
561
+
562
+ case EVENT_FORWARD_TYPE_STATE_NOTIFY:
563
+ info( "Managing state_notify event." );
564
+ subject = &switch_info.state_service_name_list;
565
+ break;
566
+
567
+ default:
568
+ error( "Invalid EVENT_FWD_TYPE ( %#x )", req->type );
569
+ event_forward_operation_reply res;
570
+ memset( &res, 0, sizeof( event_forward_operation_reply ) );
571
+ res.type = req->type;
572
+ res.result = EFI_OPERATION_FAILED;
573
+ management_application_reply *reply = create_management_application_reply( MANAGEMENT_REQUEST_FAILED, command, &res, sizeof( event_forward_operation_reply ) );
574
+ send_management_application_reply( handle, reply );
575
+ xfree( reply );
576
+ return;
577
+ }
578
+ assert( subject != NULL );
579
+
580
+ switch ( command ) {
581
+ case EVENT_FORWARD_ENTRY_ADD:
582
+ management_event_forward_entry_add( subject, req, data_len );
583
+ break;
584
+
585
+ case EVENT_FORWARD_ENTRY_DELETE:
586
+ management_event_forward_entry_delete( subject, req, data_len );
587
+ break;
588
+
589
+ case EVENT_FORWARD_ENTRY_DUMP:
590
+ info( "Dumping current event filter." );
591
+ // do nothing
592
+ break;
593
+
594
+ case EVENT_FORWARD_ENTRY_SET:
595
+ management_event_forward_entries_set( subject, req, data_len );
596
+ break;
597
+ }
598
+
599
+ buffer *buf = create_event_forward_operation_reply( req->type, EFI_OPERATION_SUCCEEDED, *subject );
600
+ management_application_reply *reply = create_management_application_reply( MANAGEMENT_REQUEST_SUCCEEDED, command, buf->data, buf->length );
601
+ free_buffer( buf );
602
+ send_management_application_reply( handle, reply );
603
+ xfree( reply );
604
+ }
605
+
606
+
542
607
  static void
543
608
  management_recv( const messenger_context_handle *handle, uint32_t command, void *data, size_t data_len, void *user_data ) {
544
- UNUSED( data );
545
- UNUSED( data_len );
546
609
  UNUSED( user_data );
547
610
 
548
611
  switch ( command ) {
@@ -577,6 +640,18 @@ management_recv( const messenger_context_handle *handle, uint32_t command, void
577
640
  }
578
641
  break;
579
642
 
643
+ case EVENT_FORWARD_ENTRY_ADD:
644
+ case EVENT_FORWARD_ENTRY_DELETE:
645
+ case EVENT_FORWARD_ENTRY_DUMP:
646
+ case EVENT_FORWARD_ENTRY_SET:
647
+ {
648
+ event_forward_operation_request *req = data;
649
+ req->n_services = ntohl( req->n_services );
650
+ management_event_forward_entry_operation( handle, command, req, data_len );
651
+ return;
652
+ }
653
+ break;
654
+
580
655
  default:
581
656
  {
582
657
  error( "Undefined management command ( %#x )", command );
@@ -623,14 +698,9 @@ main( int argc, char *argv[] ) {
623
698
  create_list( &switch_info.portstatus_service_name_list );
624
699
  create_list( &switch_info.state_service_name_list );
625
700
 
626
- // FIXME
627
- #define VENDER_PREFIX "vendor::"
628
- #define PACKET_IN_PREFIX "packet_in::"
629
- #define PORTSTATUS_PREFIX "port_status::"
630
- #define STATE_PREFIX "state_notify::"
631
701
  for ( i = optind; i < argc; i++ ) {
632
- if ( strncmp( argv[ i ], VENDER_PREFIX, strlen( VENDER_PREFIX ) ) == 0 ) {
633
- service_name = xstrdup( argv[ i ] + strlen( VENDER_PREFIX ) );
702
+ if ( strncmp( argv[ i ], VENDOR_PREFIX, strlen( VENDOR_PREFIX ) ) == 0 ) {
703
+ service_name = xstrdup( argv[ i ] + strlen( VENDOR_PREFIX ) );
634
704
  insert_in_front( &switch_info.vendor_service_name_list, service_name );
635
705
  }
636
706
  else if ( strncmp( argv[ i ], PACKET_IN_PREFIX, strlen( PACKET_IN_PREFIX ) ) == 0 ) {