1 /* 2 * Copyright (c) 2015-2022 Apple Inc. All rights reserved. 3 * 4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. The rights granted to you under the License 10 * may not be used to create, or enable the creation or redistribution of, 11 * unlawful or unlicensed copies of an Apple operating system, or to 12 * circumvent, violate, or enable the circumvention or violation of, any 13 * terms of an Apple operating system software license agreement. 14 * 15 * Please obtain a copy of the License at 16 * http://www.opensource.apple.com/apsl/ and read it before using this file. 17 * 18 * The Original Code and all software distributed under the License are 19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 23 * Please see the License for the specific language governing rights and 24 * limitations under the License. 25 * 26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@ 27 */ 28 29 #ifndef _SKYWALK_OS_NEXUS_H_ 30 #define _SKYWALK_OS_NEXUS_H_ 31 32 #ifdef PRIVATE 33 34 #include <stdint.h> 35 #include <sys/types.h> 36 #include <sys/cdefs.h> 37 #include <uuid/uuid.h> 38 #include <mach/boolean.h> 39 40 #ifdef KERNEL_PRIVATE 41 struct ifnet_interface_advisory; 42 typedef uint64_t kern_packet_t __kernel_ptr_semantics; 43 #endif /* KERNEL_PRIVATE */ 44 45 struct ifnet_traffic_descriptor_common; 46 struct ifnet_traffic_rule_action; 47 48 /* 49 * Nexus terminology and overview. The relationship between the objects are 50 * as follows: 51 * 52 * domain --> domain_provider --> nexus_provider --> nexus 53 * 54 * Skywalk comes with several nexus domains (types). Each domain has one or 55 * more domain providers; the system comes with a built-in (default) domain 56 * provider per domain. Additional domain providers may be attached, but 57 * this ability is reserved to kernel subsystems. The domain specifies the 58 * nexus semantics, including the permitted topology, number and definition 59 * of ports, memory regions, etc. 60 * 61 * Each domain provider may have one or more nexus providers registered to it. 62 * This allows different parameters (rings, slots, buffer metadata) to be 63 * configured on a per-nexus provider basis. 64 * 65 * Nexus instances can then be allocated based on a registered nexus provider. 66 * All instances associated with a given nexus provider share the same set of 67 * parameters that are configured for that nexus provider. 68 * 69 * Channels are then opened to nexus instances. 70 */ 71 72 /* 73 * Nexus types. 74 * 75 * Userland code may only register Nexus providers against the USER_PIPE 76 * and FLOW_SWITCH types. The rest are reserved for kernel subsystems. 77 */ 78 typedef enum { 79 NEXUS_TYPE_USER_PIPE, /* pipe (user) */ 80 NEXUS_TYPE_KERNEL_PIPE, /* pipe (kernel) */ 81 NEXUS_TYPE_NET_IF, /* network interface (kernel) */ 82 NEXUS_TYPE_FLOW_SWITCH, /* flow switch (user/kernel) */ 83 #ifdef BSD_KERNEL_PRIVATE 84 NEXUS_TYPE_MAX, /* this needs to be last */ 85 NEXUS_TYPE_UNDEFINED = -1, /* for kernel internal use */ 86 #endif /* BSD_KERNEL_PRIVATE */ 87 } nexus_type_t; 88 89 /* 90 * Nexus provider name. 91 */ 92 typedef uint8_t nexus_name_t[64]; 93 94 /* 95 * Nexus instance port. 96 */ 97 typedef uint16_t nexus_port_t; 98 99 /* 100 * User pipe Nexus has at most two ports: one client and server. 101 */ 102 #define NEXUS_PORT_USER_PIPE_CLIENT 0 103 #define NEXUS_PORT_USER_PIPE_SERVER 1 104 105 /* 106 * Kernel pipe Nexus has at most one port for the client. 107 */ 108 #define NEXUS_PORT_KERNEL_PIPE_CLIENT 0 109 110 /* 111 * Network Interface Nexus can have any number of ports. 112 * Port 0 and 1 are reserved for DEV and HOST. The other ports 113 * (2 and above) can be of the types: filter, custom ethertype, 114 * or low latency. 115 */ 116 #define NEXUS_PORT_NET_IF_DEV 0 117 #define NEXUS_PORT_NET_IF_HOST 1 118 #define NEXUS_PORT_NET_IF_CLIENT 2 119 120 /* 121 * Flow switch has its first N ports reserved; the following is the first 122 * client usable port. The last usable depends on the configured number 123 * of nexus ports. 124 */ 125 #define NEXUS_PORT_FLOW_SWITCH_CLIENT 2 126 127 /* 128 * Opaque handles. 129 */ 130 struct nexus_controller; 131 struct nexus_attr; 132 133 typedef struct nexus_controller *nexus_controller_t; 134 typedef struct nexus_attr *nexus_attr_t; 135 136 /* 137 * Nexus attribute types. 138 */ 139 typedef enum { 140 NEXUS_ATTR_TX_RINGS, /* (g/s) # of transmit rings */ 141 NEXUS_ATTR_RX_RINGS, /* (g/s) # of receive rings */ 142 NEXUS_ATTR_TX_SLOTS, /* (g/s) # of slots per transmit ring */ 143 NEXUS_ATTR_RX_SLOTS, /* (g/s) # of slots per receive ring */ 144 NEXUS_ATTR_SLOT_BUF_SIZE, /* (g/s) buffer per slot (bytes) */ 145 NEXUS_ATTR_SLOT_META_SIZE, /* (g) metadata per slot (bytes) */ 146 NEXUS_ATTR_ANONYMOUS, /* (g/s) allow anonymous clients */ 147 NEXUS_ATTR_MHINTS, /* (g/s) memory usage hints */ 148 NEXUS_ATTR_PIPES, /* (g/s) # of pipes */ 149 NEXUS_ATTR_EXTENSIONS, /* (g/s) extension-specific attr */ 150 NEXUS_ATTR_IFINDEX, /* (g) network interface index */ 151 NEXUS_ATTR_STATS_SIZE, /* (g) statistics region size (bytes) */ 152 NEXUS_ATTR_FLOWADV_MAX, /* (g) max flow advisory entries */ 153 NEXUS_ATTR_QMAP, /* (g/s) queue mapping type */ 154 NEXUS_ATTR_CHECKSUM_OFFLOAD, /* (g) partial checksum offload */ 155 NEXUS_ATTR_USER_PACKET_POOL, /* (g) user packet pool */ 156 NEXUS_ATTR_ADV_SIZE, /* (g) nexus advisory region size */ 157 NEXUS_ATTR_USER_CHANNEL, /* (g/s) allow user channel open */ 158 NEXUS_ATTR_MAX_FRAGS, /* (g/s) max fragments in a packets */ 159 /* 160 * (g/s) reject channel operations on nexus if the peer has closed 161 * the channel. 162 * The os channel will appear as defunct to the active peer. 163 */ 164 NEXUS_ATTR_REJECT_ON_CLOSE, 165 NEXUS_ATTR_LARGE_BUF_SIZE, /* (g/s) size of large buffer (bytes) */ 166 } nexus_attr_type_t; 167 168 /* 169 * XXX: this is temporary and should be removed later. 170 */ 171 #define OS_NEXUS_HAS_USER_PACKET_POOL 1 172 173 /* 174 * Memory usage hint attributes that can be specified for NEXUS_ATTR_MHINTS 175 * These can be OR'ed to specified multiple hints 176 */ 177 /* No hint, default behaviour */ 178 #define NEXUS_MHINTS_NORMAL 0x0 179 /* Application expects to access the channels soon */ 180 #define NEXUS_MHINTS_WILLNEED 0x1 181 /* Application expects low latency for bursty traffic */ 182 #define NEXUS_MHINTS_LOWLATENCY 0x2 183 /* Application expects high usage of channel memory */ 184 #define NEXUS_MHINTS_HIUSE 0x4 185 186 /* 187 * Extension attributes. 188 */ 189 typedef enum { 190 NEXUS_EXTENSION_TYPE_MAXTYPE = 0, 191 } nexus_extension_t; 192 193 /* 194 * Nexus queue mapping types. 195 */ 196 typedef enum { 197 NEXUS_QMAP_TYPE_INVALID = 0, /* invalid type */ 198 NEXUS_QMAP_TYPE_DEFAULT, /* 10:1 mapping */ 199 NEXUS_QMAP_TYPE_WMM, /* 802.11 WMM */ 200 } nexus_qmap_type_t; 201 202 #define NEXUS_NUM_WMM_QUEUES 4 /* number of WMM access categories */ 203 204 /* 205 * Nexus buffer metadata template. 206 * 207 * Each Nexus provider implementation will define an overlay of this structure; 208 * the top of the structure always begins with this common area. The contents 209 * of this common area, as well as the rest of the per-buffer metadata region 210 * are left to the provider to define. 211 * 212 * This structure is aligned for efficient copy and accesses. 213 */ 214 typedef struct nexus_mdata { 215 union { 216 uuid_t __uuid; /* flow UUID */ 217 uint8_t __val8[16]; 218 uint16_t __val16[8]; 219 uint32_t __val32[4]; 220 uint64_t __val64[2]; 221 } __flowid_u; 222 #define nm_flowid_uuid __flowid_u.__uuid 223 #define nm_flowid_val8 __flowid_u.__val8 224 #define nm_flowid_val16 __flowid_u.__val16 225 #define nm_flowid_val32 __flowid_u.__val32 226 #define nm_flowid_val64 __flowid_u.__val64 227 } nexus_mdata_t __attribute((aligned(8))); 228 229 /* 230 * Nexus bind flags. 231 */ 232 #define NEXUS_BIND_PID 0x1 /* bind to a process ID */ 233 #define NEXUS_BIND_EXEC_UUID 0x2 /* bind to a process exec's UUID */ 234 #define NEXUS_BIND_KEY 0x4 /* bind to a key blob */ 235 236 /* 237 * Maximum length of key blob (in bytes). 238 */ 239 #define NEXUS_MAX_KEY_LEN 1024 240 241 #ifndef KERNEL 242 /* 243 * User APIs. 244 */ 245 #if !defined(_POSIX_C_SOURCE) || defined(_DARWIN_C_SOURCE) 246 __BEGIN_DECLS 247 /* 248 * Creates a Nexus attribute object. 249 * 250 * This must be paired with a os_nexus_attr_destroy() on the handle. 251 */ 252 extern nexus_attr_t os_nexus_attr_create(void); 253 254 /* 255 * Clones a Nexus attribute object. If source attribute is NULL 256 * it behaves just like os_nexus_attr_create(); 257 * 258 * This must be paired with a os_nexus_attr_destroy() on the handle. 259 */ 260 extern nexus_attr_t os_nexus_attr_clone(const nexus_attr_t attr); 261 262 /* 263 * Sets a value for a given attribute type on a Nexus attribute object. 264 */ 265 extern int os_nexus_attr_set(nexus_attr_t attr, 266 const nexus_attr_type_t type, const uint64_t value); 267 268 /* 269 * Gets a value for a given attribute type on a Nexus attribute object. 270 */ 271 extern int os_nexus_attr_get(const nexus_attr_t attr, 272 const nexus_attr_type_t type, uint64_t *value); 273 274 /* 275 * Destroys a Nexus attribute object. 276 */ 277 extern void os_nexus_attr_destroy(nexus_attr_t attr); 278 279 /* 280 * Opens a handle to the Nexus controller. 281 * 282 * This must be paired with a os_nexus_controller_destroy() on the handle, in 283 * order to remove any remaining active providers and free resources. 284 */ 285 extern nexus_controller_t os_nexus_controller_create(void); 286 287 /* 288 * Retrieves the file descriptor associated with the Nexus controller. 289 */ 290 extern int os_nexus_controller_get_fd(const nexus_controller_t ctl); 291 292 /* 293 * Registers a Nexus provider. 294 * 295 * Anonymous Nexus provider mode implies the freedom to connect to the Nexus 296 * instance from any channel client. Alternatively, named mode requires the 297 * Nexus provider to explicitly bind a Nexus instance port to a set of client 298 * attributes. This mode (named) is the default behavior, and is done so to 299 * encourage Nexus providers to explicitly know about the clients that it's 300 * communicating with. Specifying anonymous mode can be done via the Nexus 301 * attribute NEXUS_ATTR_ANONYMOUS, by setting it to a non-zero value. 302 * 303 * The client binding attributes include the process ID, the executable UUID, 304 * and/or a key blob. Only a client possessing those will be allowed to open 305 * a channel to the Nexus instance port. 306 */ 307 extern int os_nexus_controller_register_provider(const nexus_controller_t ctl, 308 const nexus_name_t name, const nexus_type_t type, const nexus_attr_t attr, 309 uuid_t *prov_uuid); 310 311 /* 312 * Deregisters a Nexus provider. 313 */ 314 extern int os_nexus_controller_deregister_provider(const nexus_controller_t ctl, 315 const uuid_t prov_uuid); 316 317 /* 318 * Creates a Nexus instance of a registered provider. 319 */ 320 extern int os_nexus_controller_alloc_provider_instance( 321 const nexus_controller_t ctl, const uuid_t prov_uuid, uuid_t *nx_uuid); 322 323 /* 324 * Destroys a Nexus instance. 325 */ 326 extern int os_nexus_controller_free_provider_instance( 327 const nexus_controller_t ctl, const uuid_t nx_uuid); 328 329 /* 330 * Bind a port of a Nexus instance to one or more attributes associated with 331 * a channel client: process ID, process executable's UUID, or key blob. 332 * This is only applicable to named Nexus provider. 333 * 334 * Binding to a process ID implies allowing only a channel client with such 335 * PID to open the Nexus port. 336 * 337 * Binding to an executable UUID allows a channel client (regardless of PID 338 * or instance) with such executable UUID to open the Nexus port. When this 339 * is requested by a provider that doesn't have the client's executable UUID, 340 * a valid client PID must be provided (with the executable UUID zeroed out) 341 * in order for the kernel to retrieve the executable UUID from the process 342 * and to use that as the bind attribute. Else, a non-zero executable UUID 343 * can be specified (PID is ignored in this case) by the provider. 344 * 345 * Binding to a key blob allows a channel client possessing the identical 346 * key blob to open the Nexus port. The key blob is opaque to the system, 347 * and is left to the Nexus provider to interpret and relay to its client. 348 * 349 * A Nexus provider must choose to select one or a combination of those 350 * attributes for securing access to a port of a named Nexus instance. 351 * The provider is also responsible for detecting if the client has gone 352 * away, and either to unbind the Nexus instance port indefinitely, or 353 * reissue another bind with the new client binding attributes for that 354 * same port. This is to handle cases where the client terminates and 355 * is expected to reattach to the same port. 356 * 357 * All port bindings belonging to a Nexus instance will be automatically 358 * removed when the Nexus instance is destroyed. 359 */ 360 extern int os_nexus_controller_bind_provider_instance( 361 const nexus_controller_t ctl, const uuid_t nx_uuid, const nexus_port_t port, 362 const pid_t pid, const uuid_t exec_uuid, const void *key, 363 const uint32_t key_len, const uint32_t bind_flags); 364 365 /* 366 * Unbind a previously-bound port of a Nexus instance. This is only 367 * applicable to named Nexus provider. A previously-bound Nexus instance 368 * port cannot be bound again until this call is issued. 369 */ 370 extern int os_nexus_controller_unbind_provider_instance( 371 const nexus_controller_t ctl, const uuid_t nx_uuid, 372 const nexus_port_t port); 373 374 /* 375 * Retrieves current Nexus provider attributes into the nexus_attr_t handle. 376 */ 377 extern int os_nexus_controller_read_provider_attr(const nexus_controller_t ctl, 378 const uuid_t prov_uuid, nexus_attr_t attr); 379 380 /* 381 * Traffic rules APIs. 382 */ 383 384 /* Persist after controller close. */ 385 #define NXCTL_ADD_TRAFFIC_RULE_FLAG_PERSIST 0x0001 386 extern int os_nexus_controller_add_traffic_rule(const nexus_controller_t ctl, 387 const char *ifname, const struct ifnet_traffic_descriptor_common *td, 388 const struct ifnet_traffic_rule_action *ra, const uint32_t flags, 389 uuid_t *rule_uuid); 390 391 extern int os_nexus_controller_remove_traffic_rule(const nexus_controller_t ctl, 392 const uuid_t rule_uuid); 393 394 struct nexus_traffic_rule_info { 395 uuid_t *nri_rule_uuid; 396 char *nri_owner; 397 char *nri_ifname; 398 struct ifnet_traffic_descriptor_common *nri_td; 399 struct ifnet_traffic_rule_action *nri_ra; 400 uint32_t nri_flags; 401 }; 402 /* Return TRUE to continue, FALSE to exit. */ 403 typedef boolean_t (nexus_traffic_rule_iterator_t)(void *, 404 const struct nexus_traffic_rule_info *); 405 406 extern int os_nexus_controller_iterate_traffic_rules(const nexus_controller_t ctl, 407 nexus_traffic_rule_iterator_t itr, void *itr_arg); 408 409 /* 410 * Destroys a Nexus controller handle. 411 */ 412 extern void os_nexus_controller_destroy(nexus_controller_t ctl); 413 __END_DECLS 414 #endif /* (!_POSIX_C_SOURCE || _DARWIN_C_SOURCE) */ 415 #else /* KERNEL */ 416 /* 417 * Kernel APIs. 418 */ 419 #include <sys/proc.h> 420 #include <IOKit/skywalk/IOSkywalkSupport.h> 421 422 /* 423 * Nexus domain provider name. 424 */ 425 typedef uint8_t nexus_domain_provider_name_t[64]; 426 427 /* 428 * Opaque handles. 429 */ 430 struct nxctl; 431 struct kern_slot_prop; 432 struct kern_nexus; 433 struct kern_nexus_provider; 434 struct kern_nexus_domain_provider; 435 struct kern_channel; 436 struct __kern_channel_ring; 437 struct __slot_desc; 438 struct __pbufpool; 439 440 typedef struct kern_pbufpool *kern_pbufpool_t; 441 typedef struct kern_nexus *kern_nexus_t; 442 typedef struct kern_nexus_provider *kern_nexus_provider_t; 443 typedef struct kern_nexus_domain_provider *kern_nexus_domain_provider_t; 444 typedef struct kern_channel *kern_channel_t; 445 typedef struct __kern_channel_ring *kern_channel_ring_t; 446 typedef struct __slot_desc *kern_channel_slot_t; 447 typedef struct netif_llink *kern_netif_llink_t; 448 typedef struct netif_qset *kern_netif_qset_t; 449 typedef struct netif_queue *kern_netif_queue_t; 450 451 /* 452 * Domain provider callback routines. 453 */ 454 455 /* 456 * @typedef nxdom_prov_init_fn_t 457 * @abstract Domain provider initializer callback. 458 * @param domprov Domain provider handle. 459 * @discussion This will be called after kern_nexus_register_domain_provider(). 460 * @result Non-zero result will abort the domain provider registration. 461 */ 462 typedef errno_t (*nxdom_prov_init_fn_t)(kern_nexus_domain_provider_t domprov); 463 464 /* 465 * @typedef nxdom_prov_fini_fn_t 466 * @abstract Domain provider teardown callback. 467 * @param domprov Domain provider handle. 468 * @discussion This will happen after kern_nexus_deregister_domain_provider(). 469 * A provider must not unload or free resources associated to the domain 470 * provider instance until this callback is invoked. 471 */ 472 typedef void (*nxdom_prov_fini_fn_t)(kern_nexus_domain_provider_t domprov); 473 474 /* 475 * Domain provider init. 476 */ 477 struct kern_nexus_domain_provider_init { 478 uint32_t nxdpi_version; /* current version */ 479 uint32_t nxdpi_flags; /* for future */ 480 nxdom_prov_init_fn_t nxdpi_init; /* required */ 481 nxdom_prov_fini_fn_t nxdpi_fini; /* required */ 482 }; 483 484 #define KERN_NEXUS_DOMAIN_PROVIDER_VERSION_1 1 485 #define KERN_NEXUS_DOMAIN_PROVIDER_NETIF 2 486 #define KERN_NEXUS_DOMAIN_PROVIDER_CURRENT_VERSION \ 487 KERN_NEXUS_DOMAIN_PROVIDER_VERSION_1 488 489 /* 490 * Nexus provider callback routines. 491 */ 492 493 /* 494 * @typedef nxprov_pre_connect_fn_t 495 * @abstract Nexus provider channel connecting callback. 496 * @param nexus_prov Nexus provider handle. 497 * @param proc The process associated with the channel. 498 * @param nexus The nexus instance. 499 * @param channel The channel that has been created and being connected 500 * to the nexus instances's port. 501 * @param channel_context Pointer to provider-specific context that can be 502 * associated with the channel. Upon a successful return, this can 503 * later be retrieved via subsequent calls to kern_channel_get_context(). 504 * @result Non-zero result will deny the channel from being connected. 505 * @discussion This is invoked when a channel is opened to the nexus port. 506 * Upon success, client's ring and slot callbacks will be called. 507 * The channel is not usable until the nxprov_connected_fn_t() is 508 * invoked. Client must refrain from channel activities until then. 509 */ 510 typedef errno_t (*nxprov_pre_connect_fn_t)(kern_nexus_provider_t nexus_prov, 511 proc_t proc, kern_nexus_t nexus, nexus_port_t port, kern_channel_t channel, 512 void **channel_context); 513 514 /* 515 * @typedef nxprov_connected_fn_t 516 * @abstract Nexus provider channel connected callback. 517 * @param nexus_prov Nexus provider handle. 518 * @param nexus The nexus instance. 519 * @param channel The channel that has been created and fully connected 520 * to the nexus instances's port. 521 * @result Non-zero result will deny the channel from being connected. 522 * @discussion This is invoked when all ring and slot initializations have 523 * been completed, and that the channel is ready for activities. 524 */ 525 typedef errno_t (*nxprov_connected_fn_t)(kern_nexus_provider_t nexus_prov, 526 kern_nexus_t nexus, kern_channel_t channel); 527 528 /* 529 * @typedef nxprov_pre_disconnect_fn_t 530 * @abstract Nexus provider channel disconnecting callback. 531 * @param nexus_prov Nexus provider handle. 532 * @param nexus The nexus instance. 533 * @param channel The channel that has been decommissioned. 534 * @param channel_context The context that was originally set o the channel 535 * at the time nxprov_pre_connect_fn_t() callback was invoked. 536 * @discussion Following this call, all ring and slot finish callbacks will 537 * be invoked. Client must quiesce all channel activities upon getting 538 * this callback. The final disconnect completion will be indicated 539 * through a call to the nxprov_disconnected_fn_t() callback. 540 */ 541 typedef void (*nxprov_pre_disconnect_fn_t)(kern_nexus_provider_t nexus_prov, 542 kern_nexus_t nexus, kern_channel_t channel); 543 544 /* 545 * @typedef nxprov_disconnected_fn_t 546 * @abstract Nexus provider channel disconnect callback. 547 * @param nexus_prov Nexus provider handle. 548 * @param nexus The nexus instance. 549 * @param channel The channel that has been decommissioned. 550 * @param channel_context The context that was originally set o the channel 551 * at the time nxprov_pre_connect_fn_t() callback was invoked. 552 * @discussion The provider must free any resources associated with the 553 * channel context set at nxprov_pre_connect_fn_t() time, since the channel 554 * instance is no longer valid upon return. 555 */ 556 typedef void (*nxprov_disconnected_fn_t)(kern_nexus_provider_t nexus_prov, 557 kern_nexus_t nexus, kern_channel_t channel); 558 559 /* 560 * @typedef nxprov_ring_init_fn_t 561 * @abstract Nexus provider ring setup callback. 562 * @param nexus_prov Nexus provider handle. 563 * @param nexus The nexus instance. 564 * @param channel The channel associated with the ring. 565 * @param ring The ring that has been prepared. 566 * @param is_tx_ring True if ring is used for TX direction, otherwise RX. 567 * @param ring_id Ring identification number. 568 * @param ring_context Pointer to provider-specific context that can be 569 * associated with the ring. Upon a successful return, this context 570 * can later be retrieved via subsequent calls to 571 * kern_channel_ring_get_context(). 572 * @result Non-zero result will abort the ring initialization. 573 */ 574 typedef errno_t (*nxprov_ring_init_fn_t)(kern_nexus_provider_t nexus_prov, 575 kern_nexus_t nexus, kern_channel_t channel, kern_channel_ring_t ring, 576 boolean_t is_tx_ring, void **ring_context); 577 578 /* 579 * @typedef nxprov_ring_fini_fn_t 580 * @abstract Nexus provider ring teardown callback. 581 * @param nexus_prov Nexus provider handle. 582 * @param nexus The nexus instance. 583 * @param channel The channel associated with the ring. 584 * @param ring The ring that has been decommissioned. 585 * @discussion The provider must free any resources associated with the 586 * ring context set at nxprov_ring_init_fn_t() time, since the ring is 587 * no longer valid upon return. This call will be issued after all 588 * slots belonging to the ring has been decommisioned, via 589 * nxprov_slot_fini_fn_t(). 590 */ 591 typedef void (*nxprov_ring_fini_fn_t)(kern_nexus_provider_t nexus_prov, 592 kern_nexus_t nexus, kern_channel_ring_t ring); 593 594 /* 595 * @typedef nxprov_slot_init_fn_t 596 * @abstract Nexus provider channel slot setup callback. 597 * @param nexus_prov Nexus provider handle. 598 * @param nexus The nexus instance. 599 * @param ring The ring associated with the slot. 600 * @param slot The slot that has been prepared. 601 * @param slot_index The index of the slot in the ring. 602 * @param slot_prop_addr This has been deprecated; callee must set to NULL. 603 * @param slot_context Pointer to provider-specific context that can be 604 * associated with the slot in the given ring. Upon a successful return, 605 * this context can later be retrieved via subsequent calls to 606 * kern_channel_slot_get_context(). 607 * @result Non-zero result will abort the slot initialization. 608 */ 609 typedef errno_t (*nxprov_slot_init_fn_t)(kern_nexus_provider_t nexus_prov, 610 kern_nexus_t nexus, kern_channel_ring_t ring, kern_channel_slot_t slot, 611 uint32_t slot_index, struct kern_slot_prop **slot_prop_addr, 612 void **slot_context); 613 614 /* 615 * @typedef nxprov_slot_fini_fn_t 616 * @abstract Nexus provider channel slot teardown callback. 617 * @param nexus_prov Nexus provider handle. 618 * @param nexus The nexus instance. 619 * @param ring The ring associated with the slot. 620 * @param slot The slot that has been decommissioned. 621 * @param slot_index The index of the slot in the ring. 622 * @discussion The provider must free any resources associated with the 623 * slot context set at nxprov_slot_init_fn_t() time, since the slot 624 * instance is no longer valid upon return. 625 */ 626 typedef void (*nxprov_slot_fini_fn_t)(kern_nexus_provider_t nexus_prov, 627 kern_nexus_t nexus, kern_channel_ring_t ring, kern_channel_slot_t slot, 628 uint32_t slot_index); 629 630 /* 631 * @typedef nxprov_sync_tx_fn_t 632 * @abstract Nexus provider channel sync (TX) callback. 633 * @param nexus_prov Nexus provider handle. 634 * @param nexus The nexus instance. 635 * @param ring The ring associated with the slot. 636 * @param flags See KERN_NEXUS_SYNCF flags. 637 */ 638 typedef errno_t (*nxprov_sync_tx_fn_t)(kern_nexus_provider_t nexus_prov, 639 kern_nexus_t nexus, kern_channel_ring_t ring, uint32_t flags); 640 641 /* 642 * @typedef nxprov_sync_rx_fn_t 643 * @abstract Nexus provider channel sync (RX) callback. 644 * @param nexus_prov Nexus provider handle. 645 * @param nexus The nexus instance. 646 * @param ring The ring associated with the slot. 647 * @param flags See KERN_NEXUS_SYNCF flags. 648 */ 649 typedef errno_t (*nxprov_sync_rx_fn_t)(kern_nexus_provider_t nexus_prov, 650 kern_nexus_t nexus, kern_channel_ring_t ring, uint32_t flags); 651 652 /* 653 * Valid flags for {tx,rx}sync callbacks. 654 */ 655 #define KERN_NEXUS_SYNCF_COMMIT 0x1 /* force reclaim/update */ 656 657 /* 658 * @typedef nxprov_tx_doorbell_fn_t 659 * @abstract Nexus provider TX doorbell callback, required for netif. 660 * @param nexus_prov Nexus provider handle. 661 * @param nexus The nexus instance. 662 * @param ring The ring associated with the doorbell. 663 * @param flags See KERN_NEXUS_TXDOORBELLF flags. 664 */ 665 typedef errno_t (*nxprov_tx_doorbell_fn_t)(kern_nexus_provider_t nexus_prov, 666 kern_nexus_t nexus, kern_channel_ring_t ring, uint32_t flags); 667 668 /* 669 * Valid flags for tx doorbell callback. 670 */ 671 /* call kern_channel_tx_refill() in async context */ 672 #define KERN_NEXUS_TXDOORBELLF_ASYNC_REFILL 0x1 673 674 /* 675 * @typedef nxprov_sync_packets_fn_t 676 * @abstract Nexus provider get packets callback, required for netif. 677 * @param nexus_prov Nexus provider handle. 678 * @param nexus The nexus instance. 679 * @param ring The device ring. 680 * @param packets Array of packet chains 681 * @param count: 682 * RX: caller sets this to the array size. on return, this count 683 * is set to actual number of packets returned. 684 * TX: not implemented 685 * @param flags none for now. 686 */ 687 typedef errno_t (*nxprov_sync_packets_fn_t)(kern_nexus_provider_t nexus_prov, 688 kern_nexus_t nexus, kern_channel_ring_t ring, uint64_t packets[], 689 uint32_t *count, uint32_t flags); 690 691 692 /* 693 * @typedef nxprov_capab_config_fn_t 694 * @abstract Nexus provider capabilities configuration callback, 695 * required for netif. 696 * @param nexus_prov Nexus provider handle. 697 * @param nexus The nexus instance. 698 * @param capab The capability being queried. 699 * @param contents Structure describing the capability. 700 * @param len Input: length of buffer for holding contents. 701 * Output: length of actual size of contents. 702 */ 703 typedef enum { 704 /* periodic interface advisory notifications */ 705 KERN_NEXUS_CAPAB_INTERFACE_ADVISORY = 1, 706 /* extends queue set functionality: e.g. notify steering info */ 707 KERN_NEXUS_CAPAB_QSET_EXTENSIONS, 708 /* Rx flow steering to support AOP offload traffic */ 709 KERN_NEXUS_CAPAB_RX_FLOW_STEERING, 710 } kern_nexus_capab_t; 711 712 typedef errno_t (*nxprov_capab_config_fn_t)(kern_nexus_provider_t nexus_prov, 713 kern_nexus_t nexus, kern_nexus_capab_t capab, void *contents, 714 uint32_t *len); 715 716 /* 717 * struct kern_nexus_capab_interface_advisory 718 * @abstract Interface advisory capability configuration callback. 719 * @param kncia_version Version of the capability structure. 720 * @param kncia_notify The notification interface provided by kernel. 721 * @param kncia_config The configuration interface provided by nexus provider. 722 */ 723 #define KERN_NEXUS_CAPAB_INTERFACE_ADVISORY_VERSION_1 1 724 typedef errno_t (*kern_nexus_capab_interface_advisory_config_fn_t)( 725 void *provider_context, bool enable); 726 typedef errno_t (*kern_nexus_capab_interface_advisory_notify_fn_t)( 727 void *kern_context, const struct ifnet_interface_advisory *adv_info); 728 struct kern_nexus_capab_interface_advisory { 729 uint32_t kncia_version; 730 void * const kncia_kern_context; 731 void *kncia_provider_context; 732 const kern_nexus_capab_interface_advisory_notify_fn_t kncia_notify; 733 kern_nexus_capab_interface_advisory_config_fn_t kncia_config; 734 }; 735 736 /* 737 * struct kern_nexus_capab_qset_extensions 738 * @abstract qset extensions configuration callback. 739 * @param cqe_version Version of the capability structure. 740 * @param cqe_notify_steering_info callback provided by nexus provider. 741 * @param cqe_prov_ctx provider context for the above callback. 742 */ 743 #define KERN_NEXUS_CAPAB_QSET_EXTENSIONS_VERSION_1 1 744 typedef errno_t (*kern_nexus_capab_qsext_notify_steering_info_fn_t)( 745 void *provider_context, void *qset_context, 746 struct ifnet_traffic_descriptor_common *td, bool add); 747 struct kern_nexus_capab_qset_extensions { 748 uint32_t cqe_version; 749 void *cqe_prov_ctx; 750 kern_nexus_capab_qsext_notify_steering_info_fn_t cqe_notify_steering_info; 751 }; 752 753 754 #define KERN_NEXUS_CAPAB_RX_FLOW_STEERING_VERSION_1 1 755 typedef errno_t (*kern_nexus_capab_rx_flow_steering_config_fn_t)( 756 void *provider_context, 757 uint32_t id, 758 struct ifnet_traffic_descriptor_common *td, 759 uint32_t action); 760 struct kern_nexus_capab_rx_flow_steering { 761 uint32_t kncrxfs_version; 762 void *kncrxfs_prov_ctx; 763 kern_nexus_capab_rx_flow_steering_config_fn_t kncrxfs_config; 764 }; 765 766 /* 767 * Nexus provider init (version 1) 768 */ 769 struct kern_nexus_provider_init { 770 uint32_t nxpi_version; /* current version */ 771 uint32_t nxpi_flags; /* see NXPIF_* */ 772 nxprov_pre_connect_fn_t nxpi_pre_connect; /* required */ 773 nxprov_connected_fn_t nxpi_connected; /* required */ 774 nxprov_pre_disconnect_fn_t nxpi_pre_disconnect; /* required */ 775 nxprov_disconnected_fn_t nxpi_disconnected; /* required */ 776 nxprov_ring_init_fn_t nxpi_ring_init; /* optional */ 777 nxprov_ring_fini_fn_t nxpi_ring_fini; /* optional */ 778 nxprov_slot_init_fn_t nxpi_slot_init; /* optional */ 779 nxprov_slot_fini_fn_t nxpi_slot_fini; /* optional */ 780 nxprov_sync_tx_fn_t nxpi_sync_tx; /* required */ 781 nxprov_sync_rx_fn_t nxpi_sync_rx; /* required */ 782 nxprov_tx_doorbell_fn_t nxpi_tx_doorbell; /* required (netif) */ 783 nxprov_sync_packets_fn_t nxpi_rx_sync_packets; /* DO NOT USE (netif) */ 784 nxprov_sync_packets_fn_t nxpi_tx_sync_packets; /* DO NOT USE (netif) */ 785 nxprov_capab_config_fn_t nxpi_config_capab; /* optional (netif) */ 786 }; 787 788 /* 789 * @typedef nxprov_qset_init_fn_t 790 * @abstract Nexus provider netif qset setup callback. 791 * @param nexus_prov Nexus provider handle. 792 * @param nexus The nexus instance. 793 * @param llink_ctx The context associated with the logical link owning this 794 * qset (provider owned). Retreived during logical link 795 * creation. 796 * @param qset_idx The index of the qset within this logical link. 797 * @param qset_id The encoded id of the qset. Meant to be propagated to userspace 798 * and passed down later during qset selection. 799 * @param qset The netif qset to be initialized (xnu owned). Meant to be 800 * used for upcalls to xnu. 801 * @param qset_ctx The qset context (provider owned output arg). Meant to 802 * be used for downcalls to the provider involving this qset. 803 * @result Non-zero result will abort the queue initialization. 804 */ 805 typedef errno_t (*nxprov_qset_init_fn_t)(kern_nexus_provider_t nexus_prov, 806 kern_nexus_t nexus, void *llink_ctx, uint8_t qset_idx, 807 uint64_t qset_id, kern_netif_qset_t qset, void **qset_ctx); 808 809 /* 810 * @typedef nxprov_qset_fini_fn_t 811 * @abstract Nexus provider netif qset teardown callback. 812 * @param nexus_prov Nexus provider handle. 813 * @param nexus The nexus instance. 814 * @param qset_ctx The qset context retrieved from nxprov_qset_init_fn_t 815 * (provider owned). 816 * @discussion The provider must free any resources associated with the 817 * qset context set at nxprov_qset_init_fn_t() time, since the qset is 818 * no longer valid upon return. 819 */ 820 typedef void (*nxprov_qset_fini_fn_t)(kern_nexus_provider_t nexus_prov, 821 kern_nexus_t nexus, void *qset_ctx); 822 823 /* 824 * @typedef nxprov_queue_init_fn_t 825 * @abstract Nexus provider netif queue setup callback. 826 * @param nexus_prov Nexus provider handle. 827 * @param nexus The nexus instance. 828 * @param qset_ctx The context associated with the qset owning this queue 829 * (provider owned). Retreived from nxprov_qset_init_fn_t. 830 * @param qidx The index of the queue within this qset. 831 * @param queue The netif queue to be initialized (xnu owned). Meant to be 832 * used for upcalls to xnu. 833 * @param tx True if the queue is used for TX direction, otherwise RX. 834 * @param queue_ctx The queue context (provider owned output arg). Meant to 835 * be used for downcalls to the provider involving this queue. 836 * @result Non-zero result will abort the queue initialization. 837 */ 838 typedef errno_t (*nxprov_queue_init_fn_t)(kern_nexus_provider_t nexus_prov, 839 kern_nexus_t nexus, void *qset_ctx, uint8_t qidx, bool tx, 840 kern_netif_queue_t queue, void **queue_ctx); 841 842 /* 843 * @typedef nxprov_queue_fini_fn_t 844 * @abstract Nexus provider netif queue teardown callback. 845 * @param nexus_prov Nexus provider handle. 846 * @param nexus The nexus instance. 847 * @param queue_ctx The queue context retrieved from nxprov_queue_init_fn_t 848 * (provider owned). 849 * @discussion The provider must free any resources associated with the 850 * queue context set at nxprov_queue_init_fn_t() time, since the queue is 851 * no longer valid upon return. 852 */ 853 typedef void (*nxprov_queue_fini_fn_t)(kern_nexus_provider_t nexus_prov, 854 kern_nexus_t nexus, void *queue_ctx); 855 856 /* 857 * @typedef nxprov_tx_qset_notify_fn_t 858 * @abstract Nexus provider TX notify callback, required for netif. 859 * @param nexus_prov Nexus provider handle. 860 * @param nexus The nexus instance. 861 * @param qset_ctx The qset_ctx owned by the qset to be notified (provider 862 * owned). Retrieved from nxprov_qset_init_fn_t. 863 * @param flags unused for now. 864 */ 865 typedef errno_t (*nxprov_tx_qset_notify_fn_t)(kern_nexus_provider_t 866 nexus_prov, kern_nexus_t nexus, void *qset_ctx, uint32_t flags); 867 868 /* 869 * @typedef nxprov_queue_tx_push_fn_t 870 * @abstract Nexus provider netif queue Tx push model callback. 871 * @param nexus_prov Nexus provider handle. 872 * @param nexus The nexus instance. 873 * @param queue_ctx The queue context retrieved from nxprov_queue_init_fn_t 874 * (provider owned). 875 * @param ph Chain of kern packet handles. 876 * @discussion If the provider consumes the entire chain, it must update ph 877 * to NULL and if consumes only partially, then it must update ph to 878 * the first unconsumed packet handle. 879 */ 880 typedef errno_t (*nxprov_queue_tx_push_fn_t)(kern_nexus_provider_t nexus_prov, 881 kern_nexus_t nexus, void *queue_ctx, kern_packet_t *ph, 882 uint32_t *pkt_count, uint32_t *byte_count); 883 /* 884 * Nexus provider initialization parameters specific to netif (version 2) 885 */ 886 struct kern_nexus_netif_provider_init { 887 uint32_t nxnpi_version; /* current version */ 888 uint32_t nxnpi_flags; /* see NXPIF_* */ 889 nxprov_pre_connect_fn_t nxnpi_pre_connect; /* required */ 890 nxprov_connected_fn_t nxnpi_connected; /* required */ 891 nxprov_pre_disconnect_fn_t nxnpi_pre_disconnect; /* required */ 892 nxprov_disconnected_fn_t nxnpi_disconnected; /* required */ 893 nxprov_qset_init_fn_t nxnpi_qset_init; /* required */ 894 nxprov_qset_fini_fn_t nxnpi_qset_fini; /* required */ 895 nxprov_queue_init_fn_t nxnpi_queue_init; /* required */ 896 nxprov_queue_fini_fn_t nxnpi_queue_fini; /* required */ 897 nxprov_tx_qset_notify_fn_t nxnpi_tx_qset_notify; /* required */ 898 nxprov_capab_config_fn_t nxnpi_config_capab; /* required */ 899 nxprov_queue_tx_push_fn_t nxnpi_queue_tx_push; /* required */ 900 }; 901 902 #define KERN_NEXUS_PROVIDER_VERSION_1 1 903 #define KERN_NEXUS_PROVIDER_VERSION_NETIF 2 /* specific to netif */ 904 #define KERN_NEXUS_PROVIDER_CURRENT_VERSION KERN_NEXUS_PROVIDER_VERSION_1 905 906 /* 907 * Valid values for nxpi_flags. 908 */ 909 #define NXPIF_VIRTUAL_DEVICE 0x1 /* device is virtual (no DMA) */ 910 #define NXPIF_MONOLITHIC 0x4 /* single segment mode */ 911 #define NXPIF_INHIBIT_CACHE 0x8 /* caching-inhibited */ 912 913 /* 914 * Network Interface Nexus instance callback routines. 915 */ 916 917 /* 918 * @typedef nxnet_prepare_fn_t 919 * @abstract Network Interface nexus instance preparer callback. 920 * @param nexus The nexus instance. 921 * @param ifp The interface associated with the nexus instance. 922 * @discussion The prepare callback routine specified by nxneti_prepare will 923 * be invoked on a newly-allocated interface that is not yet attached. 924 * A non-zero value returned by the callback routine will abort the 925 * operation; otherwise, the interface will then be associated with 926 * the nexus prior to being fully attached to the system. 927 */ 928 typedef errno_t (*nxnet_prepare_fn_t)(kern_nexus_t nexus, ifnet_t ifp); 929 930 /* 931 * Nexus (Non-Networking) instance init. 932 * 933 * If supplied, packet buffer pool must have been created as KBIF_QUANTUM. 934 */ 935 struct kern_nexus_init { 936 uint32_t nxi_version; /* current version */ 937 uint32_t nxi_flags; /* see NXIF_* */ 938 kern_pbufpool_t nxi_tx_pbufpool; /* optional */ 939 kern_pbufpool_t nxi_rx_pbufpool; /* optional */ 940 }; 941 942 #define KERN_NEXUS_VERSION_1 1 943 #define KERN_NEXUS_CURRENT_VERSION KERN_NEXUS_VERSION_1 944 945 /* 946 * Network Interface Nexus instance init. 947 * 948 * If supplied, packet buffer pool must NOT have been created as KBIF_QUANTUM. 949 * packet buffer pool is a required parameter if the nexus provider is 950 * operating in netif logical link mode. 951 */ 952 struct kern_nexus_net_init { 953 uint32_t nxneti_version; /* current version */ 954 uint32_t nxneti_flags; /* see NXNETF_* */ 955 struct ifnet_init_eparams *nxneti_eparams; /* required */ 956 struct sockaddr_dl *nxneti_lladdr; /* optional */ 957 nxnet_prepare_fn_t nxneti_prepare; /* optional */ 958 kern_pbufpool_t nxneti_tx_pbufpool; /* optional */ 959 kern_pbufpool_t nxneti_rx_pbufpool; /* optional */ 960 struct kern_nexus_netif_llink_init *nxneti_llink; /* optional */ 961 }; 962 963 #define KERN_NEXUS_NET_VERSION_1 1 964 #define KERN_NEXUS_NET_VERSION_2 2 965 #define KERN_NEXUS_NET_CURRENT_VERSION KERN_NEXUS_NET_VERSION_1 966 967 struct kern_nexus_netif_llink_qset_init { 968 uint32_t nlqi_flags; 969 uint8_t nlqi_num_rxqs; 970 uint8_t nlqi_num_txqs; 971 }; 972 973 /* 974 * nxnetllq_flags values. 975 */ 976 /* default qset of the logical link */ 977 #define KERN_NEXUS_NET_LLINK_QSET_DEFAULT 0x1 978 /* qset needs AQM */ 979 #define KERN_NEXUS_NET_LLINK_QSET_AQM 0x2 980 /* qset is low latency */ 981 #define KERN_NEXUS_NET_LLINK_QSET_LOW_LATENCY 0x4 982 /* qset in WMM mode */ 983 #define KERN_NEXUS_NET_LLINK_QSET_WMM_MODE 0x8 984 985 typedef uint64_t kern_nexus_netif_llink_id_t; 986 987 struct kern_nexus_netif_llink_init { 988 uint32_t nli_flags; 989 uint8_t nli_num_qsets; 990 void *nli_ctx; 991 kern_nexus_netif_llink_id_t nli_link_id; 992 struct kern_nexus_netif_llink_qset_init *__counted_by(nli_num_qsets) nli_qsets; 993 }; 994 995 /* 996 * nxnetll_flags values. 997 */ 998 /* default logical link */ 999 #define KERN_NEXUS_NET_LLINK_DEFAULT 0x1 1000 1001 __BEGIN_DECLS 1002 /* 1003 * Attributes. 1004 */ 1005 extern errno_t kern_nexus_attr_create(nexus_attr_t *); 1006 extern errno_t kern_nexus_attr_clone(const nexus_attr_t attr, 1007 nexus_attr_t *); 1008 extern errno_t kern_nexus_attr_set(nexus_attr_t attr, 1009 const nexus_attr_type_t type, const uint64_t value); 1010 extern errno_t kern_nexus_attr_get(const nexus_attr_t attr, 1011 const nexus_attr_type_t type, uint64_t *value); 1012 extern void kern_nexus_attr_destroy(nexus_attr_t attr); 1013 1014 /* 1015 * Domain provider. 1016 * 1017 * At present we allow only NEXUS_TYPE_{KERNEL_PIPE,NET_IF} external 1018 * providers to be registered. 1019 */ 1020 extern errno_t kern_nexus_register_domain_provider(const nexus_type_t type, 1021 const nexus_domain_provider_name_t name, 1022 const struct kern_nexus_domain_provider_init *init, 1023 const uint32_t init_len, uuid_t *dom_prov_uuid); 1024 extern errno_t kern_nexus_deregister_domain_provider( 1025 const uuid_t dom_prov_uuid); 1026 extern errno_t kern_nexus_get_default_domain_provider(const nexus_type_t type, 1027 uuid_t *dom_prov_uuid); 1028 1029 /* 1030 * Nexus provider. 1031 */ 1032 typedef void (*nexus_ctx_release_fn_t)(void *const ctx); 1033 1034 extern errno_t kern_nexus_controller_create(nexus_controller_t *ctl); 1035 extern errno_t kern_nexus_controller_register_provider( 1036 const nexus_controller_t ctl, const uuid_t dom_prov_uuid, 1037 const nexus_name_t, const struct kern_nexus_provider_init *init, 1038 const uint32_t init_len, const nexus_attr_t nxa, uuid_t *nx_prov_uuid); 1039 extern errno_t kern_nexus_controller_deregister_provider( 1040 const nexus_controller_t ctl, const uuid_t nx_prov_uuid); 1041 extern errno_t kern_nexus_controller_alloc_provider_instance( 1042 const nexus_controller_t ctl, const uuid_t nx_prov_uuid, 1043 const void *nexus_context, nexus_ctx_release_fn_t nexus_context_release, 1044 uuid_t *nx_uuid, const struct kern_nexus_init *init); 1045 extern errno_t kern_nexus_controller_alloc_net_provider_instance( 1046 const nexus_controller_t ctl, const uuid_t nx_prov_uuid, 1047 const void *nexus_context, nexus_ctx_release_fn_t nexus_context_release, 1048 uuid_t *nx_uuid, const struct kern_nexus_net_init *init, ifnet_t *); 1049 extern errno_t kern_nexus_controller_free_provider_instance( 1050 const nexus_controller_t ctl, const uuid_t nx_uuid); 1051 extern errno_t kern_nexus_controller_bind_provider_instance( 1052 const nexus_controller_t ctl, const uuid_t nx_uuid, nexus_port_t *port, 1053 const pid_t pid, const uuid_t exec_uuid, const void *key, 1054 const uint32_t key_len, const uint32_t bind_flags); 1055 extern errno_t kern_nexus_controller_unbind_provider_instance( 1056 const nexus_controller_t ctl, const uuid_t nx_uuid, 1057 const nexus_port_t port); 1058 extern errno_t kern_nexus_controller_read_provider_attr( 1059 const nexus_controller_t ctl, const uuid_t nx_prov_uuid, 1060 nexus_attr_t attr); 1061 extern void kern_nexus_controller_destroy(nexus_controller_t ctl); 1062 extern void kern_nexus_stop(const kern_nexus_t nx); 1063 1064 /* 1065 * Netif specific. 1066 */ 1067 extern void kern_netif_increment_queue_stats(kern_netif_queue_t, 1068 uint32_t, uint32_t); 1069 1070 extern errno_t kern_netif_queue_tx_dequeue(kern_netif_queue_t, uint32_t, 1071 uint32_t, boolean_t *, uint64_t *); 1072 1073 #define KERN_NETIF_QUEUE_RX_ENQUEUE_FLAG_FLUSH 0x0001 1074 extern void kern_netif_queue_rx_enqueue(kern_netif_queue_t, uint64_t, 1075 uint32_t, uint32_t); 1076 1077 extern errno_t kern_nexus_netif_llink_add(struct kern_nexus *, 1078 struct kern_nexus_netif_llink_init *); 1079 1080 extern errno_t kern_nexus_netif_llink_remove(struct kern_nexus *, 1081 kern_nexus_netif_llink_id_t); 1082 1083 extern errno_t kern_netif_qset_tx_queue_len(kern_netif_qset_t, 1084 uint32_t, uint32_t *, uint32_t *); 1085 1086 /* 1087 * Misc. 1088 */ 1089 extern void *kern_nexus_get_context(const kern_nexus_t nexus); 1090 extern errno_t kern_nexus_get_pbufpool(const kern_nexus_t nexus, 1091 kern_pbufpool_t *tx_pbufpool, kern_pbufpool_t *rx_pbufpool); 1092 1093 /* 1094 * Non-exported KPIs. 1095 */ 1096 extern int kern_nexus_ifattach(nexus_controller_t, const uuid_t nx_uuid, 1097 struct ifnet *ifp, const uuid_t nx_attachee, boolean_t host, 1098 uuid_t *nx_if_uuid); 1099 extern int kern_nexus_ifdetach(const nexus_controller_t ctl, 1100 const uuid_t nx_uuid, const uuid_t nx_if_uuid); 1101 extern int kern_nexus_get_netif_instance(struct ifnet *ifp, uuid_t nx_uuid); 1102 extern int kern_nexus_get_flowswitch_instance(struct ifnet *ifp, 1103 uuid_t nx_uuid); 1104 extern nexus_controller_t kern_nexus_shared_controller(void); 1105 extern void kern_nexus_register_netagents(void); 1106 extern void kern_nexus_deregister_netagents(void); 1107 extern void kern_nexus_update_netagents(void); 1108 extern int kern_nexus_interface_add_netagent(struct ifnet *); 1109 extern int kern_nexus_interface_remove_netagent(struct ifnet *); 1110 extern int kern_nexus_set_netif_input_tbr_rate(struct ifnet *ifp, 1111 uint64_t rate); 1112 extern int kern_nexus_set_if_netem_params( 1113 const nexus_controller_t ctl, const uuid_t nx_uuid, 1114 void *data, size_t data_len); 1115 extern int kern_nexus_flow_add(const nexus_controller_t ncd, 1116 const uuid_t nx_uuid, void *data, size_t data_len); 1117 extern int kern_nexus_flow_del(const nexus_controller_t ncd, 1118 const uuid_t nx_uuid, void *data, size_t data_len); 1119 1120 __END_DECLS 1121 #endif /* KERNEL */ 1122 #endif /* PRIVATE */ 1123 #endif /* !_SKYWALK_OS_NEXUS_H_ */ 1124