109c7e63aSJakub Grajciar /* SPDX-License-Identifier: BSD-3-Clause 209c7e63aSJakub Grajciar * Copyright 2018-2019 Cisco Systems, Inc. All rights reserved. 309c7e63aSJakub Grajciar */ 409c7e63aSJakub Grajciar 509c7e63aSJakub Grajciar #ifndef _MEMIF_H_ 609c7e63aSJakub Grajciar #define _MEMIF_H_ 709c7e63aSJakub Grajciar 809c7e63aSJakub Grajciar #define MEMIF_COOKIE 0x3E31F20 909c7e63aSJakub Grajciar #define MEMIF_VERSION_MAJOR 2 1009c7e63aSJakub Grajciar #define MEMIF_VERSION_MINOR 0 1109c7e63aSJakub Grajciar #define MEMIF_VERSION ((MEMIF_VERSION_MAJOR << 8) | MEMIF_VERSION_MINOR) 1209c7e63aSJakub Grajciar #define MEMIF_NAME_SZ 32 1309c7e63aSJakub Grajciar 1409c7e63aSJakub Grajciar /* 15d250589dSStephen Hemminger * C2S: direction client -> server 16d250589dSStephen Hemminger * S2C: direction server -> client 1709c7e63aSJakub Grajciar */ 1809c7e63aSJakub Grajciar 1909c7e63aSJakub Grajciar /* 2009c7e63aSJakub Grajciar * Type definitions 2109c7e63aSJakub Grajciar */ 2209c7e63aSJakub Grajciar 2309c7e63aSJakub Grajciar typedef enum memif_msg_type { 2409c7e63aSJakub Grajciar MEMIF_MSG_TYPE_NONE, 2509c7e63aSJakub Grajciar MEMIF_MSG_TYPE_ACK, 2609c7e63aSJakub Grajciar MEMIF_MSG_TYPE_HELLO, 2709c7e63aSJakub Grajciar MEMIF_MSG_TYPE_INIT, 2809c7e63aSJakub Grajciar MEMIF_MSG_TYPE_ADD_REGION, 2909c7e63aSJakub Grajciar MEMIF_MSG_TYPE_ADD_RING, 3009c7e63aSJakub Grajciar MEMIF_MSG_TYPE_CONNECT, 3109c7e63aSJakub Grajciar MEMIF_MSG_TYPE_CONNECTED, 3209c7e63aSJakub Grajciar MEMIF_MSG_TYPE_DISCONNECT, 3309c7e63aSJakub Grajciar } memif_msg_type_t; 3409c7e63aSJakub Grajciar 3509c7e63aSJakub Grajciar typedef enum { 36d250589dSStephen Hemminger MEMIF_RING_C2S, /**< buffer ring in direction client -> server */ 37d250589dSStephen Hemminger MEMIF_RING_S2C, /**< buffer ring in direction server -> client */ 3809c7e63aSJakub Grajciar } memif_ring_type_t; 3909c7e63aSJakub Grajciar 4009c7e63aSJakub Grajciar typedef enum { 4109c7e63aSJakub Grajciar MEMIF_INTERFACE_MODE_ETHERNET, 4209c7e63aSJakub Grajciar MEMIF_INTERFACE_MODE_IP, 4309c7e63aSJakub Grajciar MEMIF_INTERFACE_MODE_PUNT_INJECT, 4409c7e63aSJakub Grajciar } memif_interface_mode_t; 4509c7e63aSJakub Grajciar 4609c7e63aSJakub Grajciar typedef uint16_t memif_region_index_t; 4709c7e63aSJakub Grajciar typedef uint32_t memif_region_offset_t; 4809c7e63aSJakub Grajciar typedef uint64_t memif_region_size_t; 4909c7e63aSJakub Grajciar typedef uint16_t memif_ring_index_t; 5009c7e63aSJakub Grajciar typedef uint32_t memif_interface_id_t; 5109c7e63aSJakub Grajciar typedef uint16_t memif_version_t; 5209c7e63aSJakub Grajciar typedef uint8_t memif_log2_ring_size_t; 5309c7e63aSJakub Grajciar 5409c7e63aSJakub Grajciar /* 5509c7e63aSJakub Grajciar * Socket messages 5609c7e63aSJakub Grajciar */ 5709c7e63aSJakub Grajciar 5809c7e63aSJakub Grajciar /** 59d250589dSStephen Hemminger * S2C 60d250589dSStephen Hemminger * Contains server interfaces configuration. 6109c7e63aSJakub Grajciar */ 62*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 6309c7e63aSJakub Grajciar uint8_t name[MEMIF_NAME_SZ]; /**< Client app name. In this case DPDK version */ 6409c7e63aSJakub Grajciar memif_version_t min_version; /**< lowest supported memif version */ 6509c7e63aSJakub Grajciar memif_version_t max_version; /**< highest supported memif version */ 6609c7e63aSJakub Grajciar memif_region_index_t max_region; /**< maximum num of regions */ 67d250589dSStephen Hemminger memif_ring_index_t max_s2c_ring; /**< maximum num of S2C ring */ 68d250589dSStephen Hemminger memif_ring_index_t max_c2s_ring; /**< maximum num of C2S rings */ 6909c7e63aSJakub Grajciar memif_log2_ring_size_t max_log2_ring_size; /**< maximum ring size (as log2) */ 70*e7750639SAndre Muezerie } __rte_packed_end memif_msg_hello_t; 7109c7e63aSJakub Grajciar 7209c7e63aSJakub Grajciar /** 73d250589dSStephen Hemminger * C2S 7409c7e63aSJakub Grajciar * Contains information required to identify interface 75d250589dSStephen Hemminger * to which the client wants to connect. 7609c7e63aSJakub Grajciar */ 77*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 7809c7e63aSJakub Grajciar memif_version_t version; /**< memif version */ 7909c7e63aSJakub Grajciar memif_interface_id_t id; /**< interface id */ 8009c7e63aSJakub Grajciar memif_interface_mode_t mode:8; /**< interface mode */ 8109c7e63aSJakub Grajciar uint8_t secret[24]; /**< optional security parameter */ 8209c7e63aSJakub Grajciar uint8_t name[MEMIF_NAME_SZ]; /**< Client app name. In this case DPDK version */ 83*e7750639SAndre Muezerie } __rte_packed_end memif_msg_init_t; 8409c7e63aSJakub Grajciar 8509c7e63aSJakub Grajciar /** 86d250589dSStephen Hemminger * C2S 87d250589dSStephen Hemminger * Request server to add new shared memory region to server interface. 8809c7e63aSJakub Grajciar * Shared files file descriptor is passed in cmsghdr. 8909c7e63aSJakub Grajciar */ 90*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 9109c7e63aSJakub Grajciar memif_region_index_t index; /**< shm regions index */ 9209c7e63aSJakub Grajciar memif_region_size_t size; /**< shm region size */ 93*e7750639SAndre Muezerie } __rte_packed_end memif_msg_add_region_t; 9409c7e63aSJakub Grajciar 9509c7e63aSJakub Grajciar /** 96d250589dSStephen Hemminger * C2S 97d250589dSStephen Hemminger * Request server to add new ring to server interface. 9809c7e63aSJakub Grajciar */ 99*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 10009c7e63aSJakub Grajciar uint16_t flags; /**< flags */ 101d250589dSStephen Hemminger #define MEMIF_MSG_ADD_RING_FLAG_C2S 1 /**< ring is in C2S direction */ 10209c7e63aSJakub Grajciar memif_ring_index_t index; /**< ring index */ 10309c7e63aSJakub Grajciar memif_region_index_t region; /**< region index on which this ring is located */ 10409c7e63aSJakub Grajciar memif_region_offset_t offset; /**< buffer start offset */ 10509c7e63aSJakub Grajciar memif_log2_ring_size_t log2_ring_size; /**< ring size (log2) */ 10609c7e63aSJakub Grajciar uint16_t private_hdr_size; /**< used for private metadata */ 107*e7750639SAndre Muezerie } __rte_packed_end memif_msg_add_ring_t; 10809c7e63aSJakub Grajciar 10909c7e63aSJakub Grajciar /** 110d250589dSStephen Hemminger * C2S 11109c7e63aSJakub Grajciar * Finalize connection establishment. 11209c7e63aSJakub Grajciar */ 113*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 114d250589dSStephen Hemminger uint8_t if_name[MEMIF_NAME_SZ]; /**< client interface name */ 115*e7750639SAndre Muezerie } __rte_packed_end memif_msg_connect_t; 11609c7e63aSJakub Grajciar 11709c7e63aSJakub Grajciar /** 118d250589dSStephen Hemminger * S2C 11909c7e63aSJakub Grajciar * Finalize connection establishment. 12009c7e63aSJakub Grajciar */ 121*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 122d250589dSStephen Hemminger uint8_t if_name[MEMIF_NAME_SZ]; /**< server interface name */ 123*e7750639SAndre Muezerie } __rte_packed_end memif_msg_connected_t; 12409c7e63aSJakub Grajciar 12509c7e63aSJakub Grajciar /** 126d250589dSStephen Hemminger * C2S & S2C 12709c7e63aSJakub Grajciar * Disconnect interfaces. 12809c7e63aSJakub Grajciar */ 129*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 13009c7e63aSJakub Grajciar uint32_t code; /**< error code */ 13109c7e63aSJakub Grajciar uint8_t string[96]; /**< disconnect reason */ 132*e7750639SAndre Muezerie } __rte_packed_end memif_msg_disconnect_t; 13309c7e63aSJakub Grajciar 134*e7750639SAndre Muezerie typedef struct __rte_aligned(128) __rte_packed_begin 13509c7e63aSJakub Grajciar { 13609c7e63aSJakub Grajciar memif_msg_type_t type:16; 13709c7e63aSJakub Grajciar union { 13809c7e63aSJakub Grajciar memif_msg_hello_t hello; 13909c7e63aSJakub Grajciar memif_msg_init_t init; 14009c7e63aSJakub Grajciar memif_msg_add_region_t add_region; 14109c7e63aSJakub Grajciar memif_msg_add_ring_t add_ring; 14209c7e63aSJakub Grajciar memif_msg_connect_t connect; 14309c7e63aSJakub Grajciar memif_msg_connected_t connected; 14409c7e63aSJakub Grajciar memif_msg_disconnect_t disconnect; 14509c7e63aSJakub Grajciar }; 146*e7750639SAndre Muezerie } __rte_packed_end memif_msg_t; 14709c7e63aSJakub Grajciar 14809c7e63aSJakub Grajciar /* 14909c7e63aSJakub Grajciar * Ring and Descriptor Layout 15009c7e63aSJakub Grajciar */ 15109c7e63aSJakub Grajciar 15209c7e63aSJakub Grajciar /** 15309c7e63aSJakub Grajciar * Buffer descriptor. 15409c7e63aSJakub Grajciar */ 155*e7750639SAndre Muezerie typedef struct __rte_packed_begin { 15609c7e63aSJakub Grajciar uint16_t flags; /**< flags */ 15709c7e63aSJakub Grajciar #define MEMIF_DESC_FLAG_NEXT 1 /**< is chained buffer */ 15809c7e63aSJakub Grajciar memif_region_index_t region; /**< region index on which the buffer is located */ 15909c7e63aSJakub Grajciar uint32_t length; /**< buffer length */ 16009c7e63aSJakub Grajciar memif_region_offset_t offset; /**< buffer offset */ 16109c7e63aSJakub Grajciar uint32_t metadata; 162*e7750639SAndre Muezerie } __rte_packed_end memif_desc_t; 16309c7e63aSJakub Grajciar 16409c7e63aSJakub Grajciar #define MEMIF_CACHELINE_ALIGN_MARK(mark) \ 16527595cd8STyler Retzlaff alignas(RTE_CACHE_LINE_SIZE) RTE_MARKER mark; 16609c7e63aSJakub Grajciar 16709c7e63aSJakub Grajciar typedef struct { 16809c7e63aSJakub Grajciar MEMIF_CACHELINE_ALIGN_MARK(cacheline0); 16909c7e63aSJakub Grajciar uint32_t cookie; /**< MEMIF_COOKIE */ 17009c7e63aSJakub Grajciar uint16_t flags; /**< flags */ 17109c7e63aSJakub Grajciar #define MEMIF_RING_FLAG_MASK_INT 1 /**< disable interrupt mode */ 172e12a0166STyler Retzlaff RTE_ATOMIC(uint16_t) head; /**< pointer to ring buffer head */ 17309c7e63aSJakub Grajciar MEMIF_CACHELINE_ALIGN_MARK(cacheline1); 174e12a0166STyler Retzlaff RTE_ATOMIC(uint16_t) tail; /**< pointer to ring buffer tail */ 17509c7e63aSJakub Grajciar MEMIF_CACHELINE_ALIGN_MARK(cacheline2); 17609c7e63aSJakub Grajciar memif_desc_t desc[0]; /**< buffer descriptors */ 17709c7e63aSJakub Grajciar } memif_ring_t; 17809c7e63aSJakub Grajciar 17909c7e63aSJakub Grajciar #endif /* _MEMIF_H_ */ 180