1 /* -*- Mode: C; c-basic-offset:4 ; -*- */ 2 /* 3 * Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana 4 * University Research and Technology 5 * Corporation. All rights reserved. 6 * Copyright (c) 2004-2005 The University of Tennessee and The University 7 * of Tennessee Research Foundation. All rights 8 * reserved. 9 * Copyright (c) 2004-2005 High Performance Computing Center Stuttgart, 10 * University of Stuttgart. All rights reserved. 11 * Copyright (c) 2004-2005 The Regents of the University of California. 12 * All rights reserved. 13 * Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved. 14 * Copyright (c) 2013-2018 Intel, Inc. All rights reserved. 15 * Copyright (c) 2015 Research Organization for Information Science 16 * and Technology (RIST). All rights reserved. 17 * Copyright (c) 2016 Mellanox Technologies, Inc. 18 * All rights reserved. 19 * $COPYRIGHT$ 20 * 21 * Additional copyrights may follow 22 * 23 * $HEADER$ 24 */ 25 /** 26 * @file 27 * 28 * Data packing subsystem. 29 */ 30 31 #ifndef PMIX_PTL_H_ 32 #define PMIX_PTL_H_ 33 34 #include <src/include/pmix_config.h> 35 36 #include <src/include/types.h> 37 38 #include "src/mca/mca.h" 39 #include "src/mca/base/pmix_mca_base_var.h" 40 #include "src/mca/base/pmix_mca_base_framework.h" 41 #include "src/mca/bfrops/bfrops_types.h" 42 43 #include "ptl_types.h" 44 45 BEGIN_C_DECLS 46 47 /* forward declaration */ 48 struct pmix_peer_t; 49 50 /* The overall objective of this framework is to provide transport 51 * options by which a server can communicate with a client: 52 * 53 * (a) across different versions of the library - e.g., when the 54 * connection handshake changes. 55 * 56 * (b) using different transports as necessitated by different 57 * environments. 58 * 59 * This is a mult-select framework - i.e., multiple components 60 * are selected and "active" at the same time. The intent is 61 * to have one component for each use-case, with the 62 * expectation that the community will do its best not to revise 63 * communications in manners that expand components to support (a). 64 * Thus, new variations should be rare, and only a few components 65 * will exist. 66 * 67 * The framework itself reflects the fact that any given peer 68 * will utilize only one messaging method. 69 * Thus, once a peer is identified, it will pass its version string 70 * to this framework's "assign_module" function, which will then 71 * pass it to each component until one returns a module capable of 72 * processing the given version. This module is then "attached" to 73 * the pmix_peer_t object so it can be used for all subsequent 74 * communication to/from that peer. 75 * 76 * Accordingly, there are two levels of APIs defined for this 77 * framework: 78 * 79 * (a) component level - these allow for init/finalize of the 80 * component, and assignment of a module to a given peer 81 * based on the version that peer is using 82 * 83 * (b) module level - implement send/recv/etc. Note that the 84 * module only needs to provide those functions that differ 85 * from the base functions - they don't need to duplicate 86 * all that code! 87 */ 88 89 /**** MODULE INTERFACE DEFINITION ****/ 90 91 /* initialize an active plugin - note that servers may have 92 * multiple active plugins, while clients can only have one */ 93 typedef pmix_status_t (*pmix_ptl_init_fn_t)(void); 94 95 /* finalize an active plugin */ 96 typedef void (*pmix_ptl_finalize_fn_t)(void); 97 98 /* (TWO-WAY) send a message to the peer, and get a response delivered 99 * to the specified callback function. The buffer will be free'd 100 * at the completion of the send, and the cbfunc will be called 101 * when the corresponding reply is received */ 102 typedef pmix_status_t (*pmix_ptl_send_recv_fn_t)(struct pmix_peer_t *peer, 103 pmix_buffer_t *bfr, 104 pmix_ptl_cbfunc_t cbfunc, 105 void *cbdata); 106 107 /* (ONE-WAY) send a message to the peer. The buffer will be free'd 108 * at the completion of the send */ 109 typedef pmix_status_t (*pmix_ptl_send_fn_t)(struct pmix_peer_t *peer, 110 pmix_buffer_t *bfr, 111 pmix_ptl_tag_t tag); 112 113 /* (ONE-WAY) register a persistent recv */ 114 typedef pmix_status_t (*pmix_ptl_recv_fn_t)(struct pmix_peer_t *peer, 115 pmix_ptl_cbfunc_t cbfunc, 116 pmix_ptl_tag_t tag); 117 118 /* Cancel a persistent recv */ 119 typedef pmix_status_t (*pmix_ptl_cancel_fn_t)(struct pmix_peer_t *peer, 120 pmix_ptl_tag_t tag); 121 122 /* connect to a peer - this is a blocking function 123 * to establish a connection to a peer. It assigns 124 * the corresponding module to the peer's compat 125 * structure for future use */ 126 typedef pmix_status_t (*pmix_ptl_connect_to_peer_fn_t)(struct pmix_peer_t *peer, 127 pmix_info_t info[], size_t ninfo); 128 129 130 /** 131 * Base structure for a PTL module 132 */ 133 struct pmix_ptl_module_t { 134 pmix_ptl_init_fn_t init; 135 pmix_ptl_finalize_fn_t finalize; 136 pmix_ptl_send_recv_fn_t send_recv; 137 pmix_ptl_send_fn_t send; 138 pmix_ptl_recv_fn_t recv; 139 pmix_ptl_cancel_fn_t cancel; 140 pmix_ptl_connect_to_peer_fn_t connect_to_peer; 141 }; 142 typedef struct pmix_ptl_module_t pmix_ptl_module_t; 143 144 145 /***** MACROS FOR EXECUTING PTL FUNCTIONS *****/ 146 #define PMIX_PTL_SEND_RECV(r, p, b, c, d) \ 147 do { \ 148 if ((p)->finalized) { \ 149 (r) = PMIX_ERR_UNREACH; \ 150 } else { \ 151 (r) = (p)->nptr->compat.ptl->send_recv((struct pmix_peer_t*)(p), b, c, d); \ 152 } \ 153 } while(0) 154 155 #define PMIX_PTL_SEND_ONEWAY(r, p, b, t) \ 156 do { \ 157 if ((p)->finalized) { \ 158 (r) = PMIX_ERR_UNREACH; \ 159 } else { \ 160 (r) = (p)->nptr->compat.ptl->send((struct pmix_peer_t*)(p), b, t); \ 161 } \ 162 } while(0) 163 164 #define PMIX_PTL_RECV(r, p, c, t) \ 165 (r) = (p)->nptr->compat.ptl->recv((struct pmix_peer_t*)(p), c, t) 166 167 #define PMIX_PTL_CANCEL(r, p, t) \ 168 (r) = (p)->nptr->compat.ptl->cancel((struct pmix_peer_t*)(p), t) 169 170 extern pmix_status_t pmix_ptl_base_connect_to_peer(struct pmix_peer_t* peer, 171 pmix_info_t info[], size_t ninfo); 172 173 174 /**** COMPONENT STRUCTURE DEFINITION ****/ 175 176 /* define a component-level API for establishing a 177 * communication rendezvous point for local procs. Each active component 178 * would be given an opportunity to register a listener with the 179 * PTL base, and/or to establish their own method for handling 180 * connection requests. The component sets the need_listener flag 181 * to true if a listener thread is required - otherwise, it does _not_ 182 * modify this parameter */ 183 typedef pmix_status_t (*pmix_ptl_base_setup_listener_fn_t)(pmix_info_t info[], size_t ninfo, 184 bool *need_listener); 185 186 /* define a component-level API for obtaining any envars that are to 187 * be passed to client procs upon fork */ 188 typedef pmix_status_t (*pmix_ptl_base_setup_fork_fn_t)(const pmix_proc_t *proc, char ***env); 189 190 /* 191 * the standard component data structure 192 */ 193 struct pmix_ptl_base_component_t { 194 pmix_mca_base_component_t base; 195 pmix_mca_base_component_data_t data; 196 int priority; 197 char* uri; 198 pmix_ptl_base_setup_listener_fn_t setup_listener; 199 pmix_ptl_base_setup_fork_fn_t setup_fork; 200 201 }; 202 typedef struct pmix_ptl_base_component_t pmix_ptl_base_component_t; 203 204 205 /* 206 * Macro for use in components that are of type ptl 207 */ 208 #define PMIX_PTL_BASE_VERSION_1_0_0 \ 209 PMIX_MCA_BASE_VERSION_1_0_0("ptl", 1, 0, 0) 210 211 END_C_DECLS 212 213 #endif /* PMIX_PTL_H */