wimax-tools 1.4.4
|
00001 /* 00002 * Linux WiMax 00003 * Internal API and declarations 00004 * 00005 * 00006 * Copyright (C) 2007-2008 Intel Corporation. All rights reserved. 00007 * Inaky Perez-Gonzalez <inaky.perez-gonzalez@intel.com> 00008 * 00009 * Redistribution and use in source and binary forms, with or without 00010 * modification, are permitted provided that the following conditions 00011 * are met: 00012 * 00013 * * Redistributions of source code must retain the above copyright 00014 * notice, this list of conditions and the following disclaimer. 00015 * * Redistributions in binary form must reproduce the above copyright 00016 * notice, this list of conditions and the following disclaimer in 00017 * the documentation and/or other materials provided with the 00018 * distribution. 00019 * * Neither the name of Intel Corporation nor the names of its 00020 * contributors may be used to endorse or promote products derived 00021 * from this software without specific prior written permission. 00022 * 00023 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00024 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00025 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 00026 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 00027 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 00028 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 00029 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 00030 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 00031 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00032 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 00033 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00034 * 00035 * 00036 */ 00037 #ifndef __lib_internal_h__ 00038 #define __lib_internal_h__ 00039 00040 #include <wimaxll.h> 00041 00042 struct nl_msg; 00043 struct nlmsgerr; 00044 struct sockaddr_nl; 00045 00046 enum { 00047 #define __WIMAXLL_IFNAME_LEN 32 00048 /** 00049 * WIMAXLL_IFNAME_LEN - Maximum size of a wimax interface 00050 * name. 00051 */ 00052 WIMAXLL_IFNAME_LEN = __WIMAXLL_IFNAME_LEN, 00053 }; 00054 00055 00056 /** 00057 * General structure for storing callback context 00058 * 00059 * \ingroup callbacks 00060 * 00061 * Callbacks set by the user receive a user-set pointer to a context 00062 * structure. The user can wrap this struct in a bigger context struct 00063 * and use wimaxll_container_of() during the callback to obtain its 00064 * pointer. 00065 * 00066 * Usage: 00067 * 00068 * \code 00069 * ... 00070 * struct wimaxll_handle *wmx; 00071 * ... 00072 * struct my_context { 00073 * struct wimaxll_cb_ctx ctx; 00074 * <my data> 00075 * } my_ctx = { 00076 * .ctx = WIMAXLL_CB_CTX_INIT(wmx), 00077 * <my data initialization> 00078 * }; 00079 * ... 00080 * wimaxll_set_cb_SOMECALLBACK(wmx, my_callback, &my_ctx.ctx); 00081 * ... 00082 * result = wimaxll_pipe_read(wmx); 00083 * ... 00084 * 00085 * // When my_callback() is called 00086 * my_callback(wmx, ctx, ...) 00087 * { 00088 * struct my_context *my_ctx = wimaxll_container_of( 00089 * ctx, struct my_callback, ctx); 00090 * ... 00091 * // do stuff with my_ctx 00092 * } 00093 * \endcode 00094 * 00095 * \param wmx WiMAX handle this context refers to (for usage by the 00096 * callback). 00097 * \param result Result of the handling of the message. For usage by 00098 * the callback. Should not be set to -EINPROGRESS, as this will 00099 * be interpreted by the message handler as no processing was done 00100 * on the message. 00101 * 00102 * \internal 00103 * 00104 * \param msg_done This is used internally to mark when the acks (or 00105 * errors) for a message have been received and the message 00106 * receiving loop can be considered done. 00107 */ 00108 struct wimaxll_cb_ctx { 00109 struct wimaxll_handle *wmx; 00110 ssize_t result; 00111 unsigned msg_done:1; /* internal */ 00112 }; 00113 00114 00115 /** 00116 * Initialize a definition of struct wimaxll_cb_ctx 00117 * 00118 * \param _wmx pointer to the WiMAX device handle this will be 00119 * associated to 00120 * 00121 * Use as: 00122 * 00123 * \code 00124 * struct wimaxll_handle *wmx; 00125 * ... 00126 * struct wimaxll_cb_ctx my_context = WIMAXLL_CB_CTX_INIT(wmx); 00127 * \endcode 00128 * 00129 * \ingroup callbacks 00130 */ 00131 #define WIMAXLL_CB_CTX_INIT(_wmx) { \ 00132 .wmx = (_wmx), \ 00133 .result = -EINPROGRESS, \ 00134 } 00135 00136 00137 static inline // ugly workaround for doxygen 00138 /** 00139 * Initialize a struct wimaxll_cb_ctx 00140 * 00141 * \param ctx Pointer to the struct wimaxll_cb_ctx. 00142 * \param wmx pointer to the WiMAX device handle this will be 00143 * associated to 00144 * 00145 * Use as: 00146 * 00147 * \code 00148 * struct wimaxll_handle *wmx; 00149 * ... 00150 * struct wimaxll_cb_ctx my_context; 00151 * ... 00152 * wimaxll_cb_ctx(&my_context, wmx); 00153 * \endcode 00154 * 00155 * \ingroup callbacks 00156 * \fn static void wimaxll_cb_ctx_init(struct wimaxll_cb_ctx *ctx, struct wimaxll_handle *wmx) 00157 */ 00158 void wimaxll_cb_ctx_init(struct wimaxll_cb_ctx *ctx, struct wimaxll_handle *wmx) 00159 { 00160 ctx->wmx = wmx; 00161 ctx->result = -EINPROGRESS; 00162 } 00163 00164 00165 static inline // ugly workaround for doxygen 00166 /** 00167 * Set the result value in a callback context 00168 * 00169 * \param ctx Context where to set -- if NULL, no action will be taken 00170 * \param val value to set for \a result 00171 * 00172 * \ingroup callbacks 00173 * \fn static void wimaxll_cb_maybe_set_result(struct wimaxll_cb_ctx *ctx, int val) 00174 */ 00175 void wimaxll_cb_maybe_set_result(struct wimaxll_cb_ctx *ctx, int val) 00176 { 00177 if (ctx != NULL && ctx->result == -EINPROGRESS) 00178 ctx->result = val; 00179 } 00180 00181 00182 /** 00183 * A WiMax control pipe handle 00184 * 00185 * This type is opaque to the user 00186 * 00187 * \internal 00188 * 00189 * In order to simplify multithread support, we use to different \a 00190 * libnl handles, one for sending to the kernel, one for receiving 00191 * from the kernel (multicast group). This allows us to parallelize \c 00192 * wimaxll_msg_write() and \c wimaxll_msg_read() at the same time in a 00193 * multithreaded environment, for example. 00194 * 00195 * \param ifidx Interface Index (of the network interface); if 0, the 00196 * interface name will be \c "any" and this means that this handle 00197 * works for \e any WiMAX interface. 00198 * \param gnl_family_id Generic Netlink Family ID assigned to the 00199 * device; we maintain it here (for each interface) because we 00200 * want to discover it every time we open. This solves the case of 00201 * the WiMAX modules being reloaded (and the ID changing) while 00202 * this library is running; this way it takes only a new open when 00203 * the new device is discovered. 00204 * \param mcg_id Id of the 'msg' multicast group 00205 * \param name name of the wimax interface 00206 * \param priv Private pointer set with wimaxll_priv_set() or other 00207 * accessors. Use wimaxll_priv_get() to access it. 00208 * \param nlh_tx handle for writing to the kernel. 00209 * Internal note: You \b have \b to set the handlers for 00210 * %NL_CB_VALID and nl_cb_err() callbacks, as each callsite will 00211 * do it to suit their needs. See wimaxll_rfkill() for an 00212 * example. Any other callback you are supposed to restore to what 00213 * it was before. 00214 * \param nlh_rx handle for reading from the kernel. 00215 * \param nl_rx_cb Callbacks for the nlh_rx handle 00216 * 00217 * FIXME: add doc on callbacks 00218 */ 00219 struct wimaxll_handle { 00220 unsigned ifidx; 00221 int gnl_family_id, mcg_id; 00222 char name[__WIMAXLL_IFNAME_LEN]; 00223 void *priv; 00224 00225 struct nl_handle *nlh_tx; 00226 struct nl_handle *nlh_rx; 00227 00228 wimaxll_msg_to_user_cb_f msg_to_user_cb; 00229 void *msg_to_user_priv; 00230 00231 wimaxll_state_change_cb_f state_change_cb; 00232 void *state_change_priv; 00233 }; 00234 00235 00236 /* Utilities */ 00237 int wimaxll_wait_for_ack(struct wimaxll_handle *); 00238 int wimaxll_gnl_handle_msg_to_user(struct wimaxll_handle *, struct nl_msg *); 00239 int wimaxll_gnl_handle_state_change(struct wimaxll_handle *, struct nl_msg *); 00240 int wimaxll_gnl_error_cb(struct sockaddr_nl *, struct nlmsgerr *, void *); 00241 int wimaxll_gnl_ack_cb(struct nl_msg *msg, void *_mch); 00242 00243 /* 00244 * wimaxll_family_id - Return the associated Generic Netlink family ID 00245 * 00246 * @wmx: WiMax interface for which to provide the ID. 00247 */ 00248 static inline 00249 int wimaxll_family_id(struct wimaxll_handle *wmx) 00250 { 00251 return wmx->gnl_family_id; 00252 } 00253 00254 00255 void wimaxll_msg(struct wimaxll_handle *, const char *fmt, ...) 00256 __attribute__ ((format(printf, 2, 3))); 00257 00258 /* Generic Netlink utilities */ 00259 00260 int nl_get_multicast_groups(struct nl_handle *, const char *, 00261 void (*cb)(void *, const char *, int), 00262 void *); 00263 int genl_ctrl_get_version(struct nl_handle *, const char *); 00264 00265 #endif /* #ifndef __lib_internal_h__ */