1 /*
2  *  Programming interface for wl_api.
3  *  Copyright (C) 2010 HD Wireless AB
4  *
5  *  You should have received a copy of the license along with this library.
6  */
7 
8 /*! \file wl_api.h *************************************************************
9  *
10  * \brief Basic WiFi API
11  *
12  * This file provides the wl_api interface.
13  *
14  * - Compiler:           GNU GCC for AVR32
15  * - Supported devices:
16  *  \li SPB104 + EVK1100
17  *  \li SPB104 + EVK1101
18  *  \li SPB104 + EVK1104
19  *  \li SPB104 + EVK1105 (SPI)
20  *  \li SPB104 + EVK1105 (SPI + irq)
21  *  \li SPB105 + EVK1105 (SPI)
22  * - AppNote:
23  *
24  * \author               H&D Wireless AB: \n
25  *
26  *****************************************************************************
27  *
28  * \section intro Introduction
29  * This is the documentation for the generic WiFi Driver API \a wl_api.
30  *
31  * \section files Main Files
32  * - wl_api.h : WiFi driver interface.
33  * - lib_ucr*_hd_wifi_standalone_v*.*.a - Driver library.
34  *
35  */
36 /** \mainpage wl_api Reference Manual
37 
38 \image html images/wl_api_block_diagram_small.png "wl_api Architecture"
39 
40 (o)WL API © is a programming interface for WiFi (802.11). It aims
41 to be a complete interface for embedded applications wanting to use
42 wireless as a communications interface. (o)WL API © is shortened
43 "wl_api" in this document.
44 
45 wl_api has been designed to meet the following goals :
46  \li Simple : The API is as simple as is practicable
47    to make it easy to use.
48  \li Minimal size : The API is usable on very resource constrained
49    platforms.
50  \li Portable : The API is deployable on any platform with a standards
51    compliant C compiler.
52  \li OS independent : The API is deployable on systems using a real time
53    operating system as well as with applications running on the
54    "bare metal" of a hardware platform (that is without an operating system).
55 
56 As a consequence of these design goals wl_api does not allow very fine
57 grained control of most parameters relating to 802.11 networks. That
58 would increase the flexibility of the API while also increasing
59 complexity and code size. When the underlying WiFi hardware can
60 support a richer feature set the extra features can be offered as a
61 add-on library if required.
62 
63 The wl_api is implemented by two libraries. The core library is
64 compiled for a hardware platform and is independent of operating
65 system or IP stack.  The core library contains all WiFi
66 functionality. The core library is supported by a suite of transport
67 libraries. The transport libraries implements the hardware
68 communication layer and are specific to the type of hardware interface
69 used to connect the host platform to the WiFi hardware. For example,
70 there are transport libraries for SPI and for SDIO. Only the core
71 library has a public interface (wl_api.h) but applications will need
72 to link with both the core library and a transport library matching
73 the hardware configuration.
74 
75 \section wl_api_princ Operation Principles
76 
77 There are three important properties of wl_api to keep in mind when
78 programming with it.
79 
80 The first is that wl_api is \b asynchronous. For instance, when the
81 \a wl_connect() function is called to attempt connection with an access
82 point it will trigger a sequence of packets being exchanged with the
83 access point after which, if everything is okay, a connection has been
84 established. The \a wl_connect() call is asynchronous (or non-blocking)
85 which means that you don't know if the connection attempt has
86 succeeded after the call returns. You only know if the sequence was
87 successfully started or not. To find out if, and when, the connection
88 attempt was successful you must register an event handler using the
89 function \a wl_register_event_cb(). This is true of a number of API calls
90 (which is indicated in their documentation).
91 
92 The second important property is that wl_api is \b polled.  wl_api
93 never executes "by itself", since it would then have to support
94 interrupts, timers, locks and other operating system dependent
95 features.  Instead all asynchronous processes proceed when wl_api is
96 polled by calling the \a wl_tick() function. When \a wl_tick() is called
97 wl_api reacts to any received management frames, expires any internal timers and
98 performs any other tasks necessary for forward progress. After
99 \a wl_tick() returns nothing will happen unless it or some other wl_api
100 function is called again. Also, to send and receive data, the \a wl_process_rx()
101 and \a wl_process_tx() must be invoked upon reception and transmission of data.
102 
103 The third important property is that wl_api is \b not \b thread \b safe.
104 All wl_api calls must execute in the same context since the
105 library has no knowledge of the locking mechanisms available (if any).
106 
107 \section wl_api_code_examples A note on the code examples
108 
109 The code examples illustrate how to call the different wl_api functions.
110 They do not constitute a complete program. Functions with the prefix "app_"
111 in the code examples are application specific calls that illustrate a
112 particular action. These functions are not part of the API and will have
113 to be implemented if needed. For a complete working code example see
114 one of the H&D Wireless software reference designs, such as the WiFi HTTP
115 server demo code in the Atmel Software Framework.
116 
117 The API is structured into these functional groups:
118 
119 \li \ref wl_api
120 \li \ref wl_wifi
121 \li \ref wl_data
122 \li \ref wl_transport
123 \li \ref wl_custom
124 
125 Also documented here is the transport layers for SPI and SDIO.
126 There interfaces are only necessary when porting the library to
127 a new hardware platform.
128 
129 \li \ref wl_spi
130 \li \ref wl_sdio
131 
132  * \section contactinfo Contact Information
133  * For further information, visit
134  * <A href="http://www.hd-wireless.se/">H&D Wireless</A>.\n
135  * Support and FAQ: http://www.atmel.com/
136  */
137 
138 #ifndef WL_API_H
139 #define WL_API_H
140 
141 #define WL_API_RELEASE_NAME "v2.7.0"
142 
143 /*! Maximum size of a SSID */
144 #define WL_SSID_MAX_LENGTH 32
145 /*! Size of a MAC-address or BSSID */
146 #define WL_MAC_ADDR_LENGTH 6
147 /*! Maximum length of a passphrase */
148 #define WL_MAX_PASS_LEN 64
149 /*! Indicates that there is no SNR information */
150 #define WL_SNR_UNKNOWN -128
151 
152 #define SPB104 104
153 #define SPB105 105
154 
155 /*! \ingroup wl_api
156  * API Error codes */
157 typedef enum {
158         WL_FAILURE = -1,
159         WL_SUCCESS = 1,
160         WL_NOEFFECT,
161         WL_OOM,
162         WL_INVALID_LENGTH,
163         WL_NOT_SUPPORTED,
164         WL_ABSORBED,
165         WL_RESOURCES,
166         WL_BUSY,
167         WL_RETRY, /*!< Retry the operation later. The driver is busy
168                     resolving an operation that conflicts with the
169                     request. */
170         WL_INVALID_ARGS,
171         WL_AVAIL,
172         WL_CARD_FAILURE,        /*!< Could not detect SPB device */
173         WL_FIRMWARE_INVALID,    /*!< Invalid firmware data */
174 
175 } wl_err_t;
176 
177 /*! \ingroup wl_wifi
178  * Event identifiers */
179 enum wl_event_id_t {
180         WL_EVENT_MEDIA_CONNECTED = 0,
181         WL_EVENT_CONN_FAILURE,
182         WL_EVENT_MEDIA_DISCONNECTED,
183         WL_EVENT_SCAN_COMPLETE,
184         WL_EVENT_FAILURE,
185         MAX_WL_EVENT
186 };
187 
188 /*! \ingroup wl_wifi
189  * Authentication modes */
190 enum wl_auth_mode {
191         AUTH_MODE_INVALID,
192         AUTH_MODE_AUTO,
193         AUTH_MODE_OPEN_SYSTEM,
194         AUTH_MODE_SHARED_KEY,
195         AUTH_MODE_WPA,
196         AUTH_MODE_WPA2,
197         AUTH_MODE_WPA_PSK,
198         AUTH_MODE_WPA2_PSK
199 };
200 
201 /*! \ingroup wl_wifi
202  * Encryption modes */
203 enum wl_enc_type {  /* Values map to 802.11 encryption suites... */
204         ENC_TYPE_WEP  = 5,
205         ENC_TYPE_TKIP = 2,
206         ENC_TYPE_CCMP = 4,
207         /* ... except these two, 7 and 8 are reserved in 802.11-2007 */
208         ENC_TYPE_NONE = 7,
209         ENC_TYPE_AUTO = 8
210 };
211 
212 enum wl_host_attention_mode {
213         WL_HOST_ATTENTION_SDIO = 0x1, /*!< For SDIO or polled SPI */
214         WL_HOST_ATTENTION_SPI  = 0x5a /*!< For SPI with interrupt line */
215 };
216 
217 /*! \ingroup wl_wifi
218  * Event descriptor
219 */
220 struct wl_event_t {
221         enum wl_event_id_t id;  /**< Event identifier. */
222 
223 };
224 
225 /*! \ingroup wl_wifi
226  * Infrastructure (ESS) or Ad-hoc (IBSS) connection modes.
227  */
228 enum wl_conn_type_t {
229         WL_CONN_TYPE_INFRA, /*!< For infrastructure mode (default) */
230         WL_CONN_TYPE_ADHOC  /*!< For ad-hoc mode */
231 };
232 
233 /* Note:
234  * If your environment does not have stdint.h you will have to
235  * define the fixed-width integer types specified in that file
236  * yourself, make sure that those definitions are included
237  * before any inclusions of wl_api.h, and build with the macro
238  * WITHOUT_STDINT defined. In this case the wl_api library
239  * must have been built with the same integer type definitions.
240  */
241 
242 #ifndef WITHOUT_STDINT
243 #include <stdint.h>
244 #endif
245 
246 /* Note:
247  * If your environment does not have stdio.h you will have to define
248  * the size_t type yourself, make sure that that definition is
249  * included before any inclusions of wl_api.h, and build with the
250  * macro WITHOUT_STDIO defined. In this case the wl_api library must
251  * have been built with the same size_t type definition.
252  */
253 #ifndef WITHOUT_STDIO
254 #include <stdio.h>
255 #endif
256 
257 /*! \ingroup wl_wifi
258  *
259  * \brief SSID representation.
260  *
261  * The SSID is a binary string and cannot be treated as a
262  * C-string safely. An empty SSID is represented by a
263  * SSID struct with the len field set to 0.
264  */
265 struct wl_ssid_t
266 {
267         char ssid[WL_SSID_MAX_LENGTH]; /**< Octet array containing the SSID data. */
268         uint8_t len; /**< Length of valid data in ssid member.
269                       *   Cannot be longer than WL_SSID_MAX_LENGTH. */
270 };
271 
272 /*! \ingroup wl_wifi
273  *
274  * MAC-address/BSSID representation
275  *
276  * A broadcast BSSID is one with all octets set to 0xFF.
277  */
278 struct wl_mac_addr_t
279 {
280         uint8_t octet[WL_MAC_ADDR_LENGTH]; /**< Octet array containing the MAC address
281                                             * data. This array is always WL_MAC_ADDR_LENGTH bytes.
282                                             */
283 };
284 
285 /*! \ingroup wl_wifi
286  *
287  * Network representation
288  *
289  */
290 struct wl_network_t
291 {
292         struct wl_ssid_t ssid; /**< The SSID of the network. */
293         struct wl_mac_addr_t bssid; /**<  The BSSID of the network. */
294         uint8_t channel; /**< The wlan channel which the network uses */
295         uint32_t beacon_period; /**< Beacon period for the network */
296         uint16_t dtim_period; /**< DTIM period for the network */
297         int32_t rssi; /**< Received Signal Strength in dBm (measured on beacons) */
298         int32_t snr; /**< Received Signal to noise ratio in dBm (measured on beacons) */
299         uint8_t enc_type; /**< The encryption type used in the network. */
300 
301         enum wl_conn_type_t net_type; /**< Type of network (Infrastructure or Ad-Hoc */
302         size_t ie_len;    /**< Always 0 unless wl_api has been built with WL_CONFIG_WPA_SUPPLICANT */
303 
304         uint8_t ie[0]; /**< Not used unless wl_api has been built with WL_CONFIG_WPA_SUPPLICANT */
305 };
306 
307 /*! \ingroup wl_wifi
308  * Network list representation. Array of pointers to wl_network_t entries.
309  *
310  */
311 struct wl_network_list_t
312 {
313         struct wl_network_t **net; /**< The list of pointers to networks */
314         size_t cnt;                /**< Number of networks */
315 };
316 
317 #define WL_RATE_1MBIT      2
318 #define WL_RATE_2MBIT      4
319 #define WL_RATE_5_5MBIT    11
320 #define WL_RATE_6MBIT      12
321 #define WL_RATE_9MBIT      18
322 #define WL_RATE_11MBIT     22
323 #define WL_RATE_12MBIT     24
324 #define WL_RATE_18MBIT     36
325 #define WL_RATE_22MBIT     44
326 #define WL_RATE_24MBIT     48
327 #define WL_RATE_33MBIT     66
328 #define WL_RATE_36MBIT     72
329 #define WL_RATE_48MBIT     96
330 #define WL_RATE_54MBIT     108
331 #define WL_RATE_NUM_RATES  14
332 #define WL_RATE_INVALID    WL_RATE_NUM_RATES
333 
334 /*! \ingroup wl_wifi
335  *
336  * Rate representation
337  *
338  */
339 typedef uint8_t wl_rate_t;
340 
341 /** \defgroup wl_api Library support functions
342  *
343  * These functions manage the library in general. They concern initalizing
344  * the library, downloading firmware to the WiFi chip and handling events
345  * from the library.
346 
347 For this example we assume that the application is running stand-alone
348 without an operating system.
349 
350 Before the library can do anything it needs to start up the WiFi
351 hardware by downloading a firmware image. The firmware image is
352 relatively big (around 144kB) and is therefore not included in the library
353 it is only needed once. It is up to the application to decide where to
354 store the firmware image and how to read it into the wl_api library.
355 
356 Step one is to write a function of the type \a ::wl_fw_read_cb_t
357 that wl_api will call to retrive the firmware image. Assuming that you
358 have some spare RAM (or whatever memory type is used for read only
359 data, such as FLASH memory) on your platform you can simply include
360 the firmware image from the \a wl_fw.h header file and write a
361 firmware read function like this
362 
363 \code
364 static size_t fw_read_cb(void* ctx,
365                          uint8_t** buf,
366                          size_t offset,
367                          size_t len)
368 {
369         if ( NULL == buf ) {
370                 return 0;
371         }
372         *buf = ((uint8_t*) fw_buf) + offset;
373         if ( len > ( fw_len - offset ) ) {
374                 return fw_len - offset;
375         }
376         return len;
377 }
378 
379 \endcode
380 
381 If the firmware image is stored in ROM this function may have to read
382 it back block by block instead.
383 
384 First, firmware must be downloaded to the device
385 
386 \code
387 if ( wl_transport_init(fw_read_cb, NULL, &mode) != WL_SUCCESS ) {
388         app_error("Firmware download failed");
389         return 0;
390 }
391 \endcode
392 
393 The wl_api library is then initialized like this
394 
395 \code
396 if ( wl_init(NULL, init_complete_cb, mode) != WL_SUCCESS ) {
397         app_error("Init failed");
398         return 0;
399 }
400 \endcode
401 
402 The library startup process will now require \a wl_poll() to be called
403 a number of times before it can complete. In addition, if the
404 application needs to know when the startup process has completed so
405 that it can, for example, start up an IP stack it will have to supply
406 a valid callback function of the type \a ::wl_init_complete_cb_t as a parameter
407 to the \a wl_init() call and start polling the wl_api library.
408 
409 The init complete callback will only be executed during a call to \a wl_poll()
410 or another wl_api function. This simplifies the implementation since no
411 internal locking is required and the wl_api library becomes OS-independent.
412 
413 \code
414 static void init_complete_cb(void* ctx) {
415        init_ip_stack();
416 }
417 \endcode
418 
419 Registering the event callback is straightforward :
420 
421 \code
422 if (wl_register_event_cb(event_cb, NULL) != WL_SUCCESS) {
423        app_error("Failed to register event handler");
424        return 0;
425 }
426 \endcode
427 
428 Similar to \a wl_poll(), there is also a \a wl_tick() function that takes a
429 free running "tick" counter with millisecond resolution as an argument so
430 that it can trigger internal timers when necessary. Assuming that such a tick
431 counter is provided by the macro GET_MS_TICK() the wl_api execution loop becomes
432 
433 \code
434 while (TRUE) {
435        wl_tick(GET_MS_TICK());
436        wl_poll();
437 }
438 \endcode
439 
440 In a stand-alone application this loop would usually be the main application
441 loop and include application specific calls as well.
442 
443 After some number of main loop iterations the init_complete_cb will be
444 invoked and the application can initialize its IP stack.
445 
446  *  @{
447  */
448 
449 /*! \brief WiFi event callback.
450  *
451  * This function receives WiFi events that the application
452  * wants notification of. This function is supplied by the user
453  * of the API.
454  *
455  * @param event Struct describing the type of event and, for some
456  *              events, additional information regarding the
457  *              status of the event. See wl_event_t for additional
458  *              information.
459  * @param ctx   A context handle. This handle is passed
460  *              untouched to the callback and has the same value
461  *              as the context registered with the callback in
462  *              wl_register_event_cb().
463  */
464 typedef void (*wl_event_cb_t) (struct wl_event_t event, void* ctx);
465 
466 
467 /*! \brief Initialization complete callback function.
468  *
469  * Invoked when WiFi initialization is complete.
470  *
471  * @param ctx Opaque context pointer as provided to \a wl_init() that will be
472  *            passed back to the callback.
473  */
474 typedef void (wl_init_complete_cb_t)(void* ctx);
475 
476 
477 /*! \brief Register an event handler.
478  *
479  * Register an event handler with the driver. This
480  * event handler will be called whenever a event
481  * listed in #wl_event_id_t occurs.
482  * See #wl_event_cb_t and #wl_event_id_t for more details.
483  *
484  * @param cb Event callback function to register.
485  * @param ctx Opaque context pointer that will be
486  *            passed to the callback when it is
487  *            invoked. This parameter is never
488  *            accessed by the API.
489  * @return WL_SUCCESS
490  */
491 wl_err_t wl_register_event_cb(wl_event_cb_t cb, void* ctx);
492 
493 /*! \brief Initialize the wl_api library.
494  *
495  * Note that \a wl_poll() must be called for this function to progress
496  * towards complete init
497  *
498  * The startup process will proceed asynchronously and will inkove
499  * init_complete_cb when completed. The callback will not be invoked if any
500  * error occurs during initialization.
501  *
502  * This function should be called after firmware has been downloaded to the
503  * device.
504  *
505  * @param ctx Opaque context pointer that will be passed to the callback
506  *            when invoked. This parameter is never accessed by the API.
507  * @param init_complete_cb callback function to invoke when initialization is
508  *        complete.
509  * @param mode Indicates the host attention mode used by the device. If
510  *         \a wl_transport_init() was used to download the firmware image to the
511  *         device, the proper mode can be obtained from the mode parameter of
512  *         that function.
513  *
514  * @return
515  * - WL_SUCCESS
516  * - WL_FAILURE
517  */
518 wl_err_t wl_init(void* ctx, wl_init_complete_cb_t init_complete_cb,
519                  enum wl_host_attention_mode mode);
520 
521 
522 /*! \brief Shutdown the wl_api library and free resources.
523  *
524  * \a wl_init() must be invoked to startup the library
525  * again.
526  *
527  * @return
528  * - WL_SUCCESS on success
529  * - WL_FAILURE
530  *
531  */
532 wl_err_t wl_shutdown(void);
533 
534 
535 /*! \brief WiFi driver timer tick function
536  *
537  * Periodic timers are triggered from this function so it should be called as
538  * often as possible if precision timing is required (traffic timeouts,
539  * authentication timeouts etc).
540  *
541  * @param tick A tick count in us. This is used to expire timers
542  *  in the driver.
543  */
544 void wl_tick(uint32_t tick);
545 
546 /*!  @} */
547 
548 
549 /** \defgroup wl_wifi Connection Management
550  *
551  * These functions access WiFi-specific functionality such as
552  * scanning, connect/disconnect, authentication and encryption,
553  * and power save modes.
554  *
555 
556 \section scanning Scanning
557 
558 To scan all channels that are available in the current regulatory
559 domain
560 
561 \code
562        if ( wl_scan() != WL_SUCCESS ) {
563               // May be busy scanning already, no fatal error
564               return 0;
565        }
566 \endcode
567 
568 Since wl_scan() only starts the scanning process the application
569 should add code to the event handler to catch the "scan complete" event
570 and retrieve the list of seen networks from the library
571 
572 \code
573 static void event_cb(struct wl_event_t event, void* ctx) {
574        switch(event.id) {
575               case WL_EVENT_SCAN_COMPLETE:
576                      struct wl_network_list_t *netlist;
577                      uint8_t netcnt;
578 
579                      wl_get_network_list(&netlist);
580                      netcnt = netlist->cnt;
581                      while (--netcnt) {
582                              print_network(netlist->net[netcnt]);
583                      }
584                      break;
585        }
586 }
587 \endcode
588 
589 The function print_network() could display the network name, the SSID, in
590 a user interface. It is important to keep in mind is that despite the fact
591 that the SSID is usually presented as a ASCII string, it is
592 in fact just a byte string and can legally contain all kinds of
593 non-printable characters, including a 0-byte. This means that it is
594 easy to end up with buffer overrun bugs if the SSID is ever treated
595 as a normal string without precautions.
596 
597 \code
598 void print_network(struct wl_network_t* wl_network)
599 {
600         char ssid[WL_SSID_MAX_LENGTH + 1];
601         memset(ssid, 0, sizeof(ssid));
602         memcpy(ssid, wl_network->ssid.ssid, wl_network->ssid.len);
603         if (app_is_printable(ssid)) {
604                 app_print("\"%s\" ", ssid);
605         }
606         else {
607                 app_print("<binary SSID> ");
608         }
609         switch (wl_network->enc_type) {
610         case ENC_TYPE_WEP :
611                 app_print("(WEP encryption)");
612                 break;
613         case ENC_TYPE_TKIP :
614                 app_print("(TKIP encryption)");
615                 break;
616         case ENC_TYPE_CCMP :
617                 app_print("(CCMP encryption)");
618                 break;
619         }
620         app_print("\n");
621 }
622 \endcode
623 
624 \section connecting Connecting
625 
626 To connect to an access point (beware binary SSIDs) the connection process
627 must be started
628 
629 \code
630          if ( wl_connect("My AP", strlen("My AP"))
631               != WL_SUCCESS ) {
632               app_error("Connection failed.\n");
633               return 0;
634          }
635 \endcode
636 
637 and the \a WL_EVENT_MEDIA_CONNECTED and \a WL_EVENT_CONN_FAILURE events should be
638 caught. To detect that a connection is terminated after it has been successfully established
639 (such as when the AP goes out of range) the \a WL_EVENT_MEDIA_DISCONNECTED event
640 must be also be caught
641 
642 
643 \code
644 static void event_cb(struct wl_event_t event, void* ctx) {
645        switch(event.id) {
646               case WL_EVENT_SCAN_COMPLETE:
647                      struct wl_network_list_t *netlist;
648                      uint8_t netcnt;
649 
650                      wl_get_network_list(&netlist);
651                      netcnt = netlist->cnt;
652                      while (--netcnt) {
653                              print_network(netlist->net[netcnt]);
654                      }
655                      break;
656               case WL_EVENT_CONN_FAILURE:
657                      app_error("Connection failed\n");
658                      break;
659               case WL_EVENT_MEDIA_CONNECTED:
660                      app_print("Connected to Access Point\n");
661                      app_ip_interface_up();
662                      break;
663               case WL_EVENT_MEDIA_DISCONNECTED:
664                      app_print("Disconnected from Access Point\n");
665                      app_ip_interface_down();
666                      break;
667        }
668 }
669 \endcode
670 
671 \section security Security
672 
673 To use WEP a WEP key must be added before the connection is initiated.
674 To set the 40-bit WEP key 0xDEADBEEF00 as default key for key index 0 do
675 
676 \code
677          char key[5] = { 0xDE, 0xAD, 0xBE, 0xEF, 0x00 };
678          struct wl_mac_addr_t bssid;
679 
680          // This means that the bssid is a broadcast bssid and the WEP key will be a default key instead of a key-mapping key.
681          memset(&bssid.octet, 0xff, sizeof bssid.octet);
682 
683          if ( wl_add_wep_key(0, sizeof key, key, &bssid)
684               != WL_SUCCESS ) {
685               app_error("Failed to add WEP key.");
686               return 0;
687          }
688 \endcode
689 
690 To use WPA/WPA2 with a Pre-shared key a passphrase must be associated
691 with the network before the connection is initiated.
692 
693 \code
694         struct wl_network_t net;
695         char passphrase[] = "MySecretKey";
696 
697         memset(&net, 0, sizeof net);
698         memset(net.bssid.octet, 0xFF, sizeof net.bssid.octet);
699         strncpy(net.ssid.ssid, "My AP", strlen("My AP"));
700         net.ssid.len = strlen("My AP");
701         net.enc_type = ENC_TYPE_AUTO;
702         if (wl_set_passphrase(&net,
703                               passphrase,
704                               strlen(passphrase),
705                               ENC_TYPE_AUTO,
706                               AUTH_MODE_AUTO)
707             != WL_SUCCESS) {
708                 app_error("Failed to add passphrase");
709         }
710 \endcode
711 
712 The library supports several passphrase-network associations to be
713 configured simultaneously. Be aware that the \a wl_connect() call
714 can take up to 15 seconds longer than normal when using a pre-shared
715 WPA/WPA2 key since the platform must calculate a temporal encryption
716 key from the passphrase before the connection attempt can start.
717 
718  *  @{
719  */
720 
721 
722 /*! \brief Scan all channels.
723  *
724  * Starts a scan of all WiFi channels allowed in this regulatory
725  * domain. The list of allowed channels (the domain) is adapted to the
726  * channels announced as allowed by the first AP heard.
727  *
728  * The scan will proceed asynchronously and will raise a
729  * WL_EVENT_SCAN_COMPLETE event when completed.
730  *
731  * Currently, there's a limit on the scan list size that depends on the
732  * architecture (6 networks for the AVR32 UCR1 architecture 16 networks for
733  * other architectures. If more network exist, the strongest networks are
734  * chosen. Note that the limitation on the scan list size does not limit the
735  * networks which the device can connect to. See wl_connect() for more
736  * details.
737  *
738  * @return
739  * - WL_SUCCESS
740  * - WL_FAILURE.
741  */
742 wl_err_t wl_scan(void);
743 
744 /*! \brief Get the list of currently known networks.
745  *
746  * Retrieves the list of currently known networks from
747  * the driver. To ensure that this list is up-to-date
748  * a wl_scan() call should be issued and this function
749  * should be called upon reception of the WL_EVENT_SCAN_COMPLETE
750  * event. This function can be called at other times
751  * but the list of networks retrieved then might not
752  * correspond to the networks actually in range.
753  *
754  * Note that a successful scan does not necessarily
755  * find any networks.
756  *
757  * @param network_list Output buffer. The API call returns
758  *        a pointer to allocated memory containing the network list.
759  * @return
760  * - WL_SUCCESS
761  * - WL_FAILURE.
762  */
763 wl_err_t wl_get_network_list(struct wl_network_list_t **network_list);
764 
765 #ifdef WFE_6_12
766 /*! \brief Start a Ad-hoc network.
767  *
768  * Attempt to start a Ad-hoc (IBSS) network. If a Ad-hoc network
769  * is successfully started then a WL_EVENT_MEDIA_CONNECTED event
770  * will be raised once the first peer station connects to the Ad-hoc
771  * network (and not when the network is announced on the air).
772  *
773  * If a Ad-hoc network should be started with encryption
774  * enabled then \a wl_set_passphrase() should be called before
775  * \a wl_start_adhoc_net() to configure the security parameters.
776  * The Ad-hoc network is started with the security parameters
777  * (if any) that was configured for the specified \a ssid.
778  *
779  * @param ssid The SSID of the new network. If there's a network
780  *             already present with this SSID this call will fail.
781  * @param channel The channel to use. Valid channels are 1-14
782  * @param auth_mode The authentication mode to use. Supported
783  *        authentication modes for Ad-hoc networks are
784  *        AUTH_MODE_OPEN_SYSTEM and AUTH_MODE_SHARED_KEY.
785  *        Passing other modes will cause a WL_INVALID_ARGS return.
786  *        If AUTH_MODE_SHARED_KEY is used then a valid WEP
787  *        key must be set with a call to \a wl_add_wep_key()
788  *        and the default WEP key index must be set with a
789  *        call to \a wl_set_default_wep_key().
790  * @return
791  *        - WL_SUCCESS on success.
792  *        - WL_INVALID_ARGS if the ssid is malformed, if
793  *          the channel not valid or if the authentication mode
794  *          is invalid.
795  *        - WL_RETRY if the driver is busy resolving a conflicting
796  *          operation.  The operation should be retried after a wait
797  *          (at least one call to wl_poll() for polled implementations).
798  *        - WL_BUSY if the driver is already connected or if a network
799  *          with the same SSID is already known.
800  *
801  */
802 wl_err_t wl_start_adhoc_net(struct wl_ssid_t ssid,
803                             uint8_t channel,
804                             enum wl_auth_mode auth_mode);
805 #endif
806 /*! \brief Connect to a SSID.
807  *
808  * Attempt to connect to a given SSID. If the driver is already
809  * connected to an AP with a different SSID then this call will
810  * return WL_BUSY and wl_disconnect() should be called before
811  * trying again.
812  *
813  * The connection process will proceed asynchronously and will raise a
814  * WL_EVENT_MEDIA_CONNECTED event when completed, or a WL_EVENT_CONN_FAILURE
815  * when failed. After a WL_EVENT_MEDIA_CONNECTED event has been raised
816  * a WL_EVENT_MEDIA_DISCONNECT event will be raised if the connection is
817  * terminated. Note that this can be caused by external factors and can
818  * happen at any time.
819  *
820  * If wl_connect() is invoked with a network that is not shown in the
821  * scan list, the device will probe for that specific network and connect
822  * to it, if found. This is also the method to use in order to connect to
823  * "hidden" networks (AP's that doesn't broadcast its SSID).
824  *
825  * @param ssid Pointer to the SSID string.
826  *             Freed by caller.
827  * @param ssid_len Length of the SSID string in octets. Max value is 32.
828  * @return
829  *  - WL_SUCCESS
830  *  - WL_FAILURE if the network could not be found
831  *  - WL_BUSY if the driver is already connected
832  *  - WL_RETRY if the driver is busy resolving a conflicting operation.
833  *    The operation should be retried after a wait (at least one call to wl_poll()
834  *    for polled implementations).
835  */
836 wl_err_t wl_connect(char* ssid, size_t ssid_len);
837 
838 /*! \brief Connect to a BSSID
839  *
840  * Attempt to connect to a given BSSID. If the driver is already
841  * connected to an AP with a different BSSID then this call will
842  * return WL_BUSY and wl_disconnect() should be called before
843  * trying again.
844  *
845  * The connection process will proceed asynchronously and will raise a
846  * WL_EVENT_MEDIA_CONNECTED event when completed, or a WL_EVENT_CONN_FAILURE
847  * when failed. After a WL_EVENT_MEDIA_CONNECTED event has been raised
848  * a WL_EVENT_MEDIA_DISCONNECT event will be raised if the connection is
849  * terminated. Note that this can be caused by external factors and can
850  * happen at any time.
851  *
852  * If wl_connect_bssid() is invoked with a network that is not shown in the
853  * scan list, the device will probe for that specific network and connect
854  * to it, if found.
855  *
856  * @param bssid Pointer to the BSSID. Freed by caller.
857  * @return
858  *  - WL_SUCCESS
859  *  - WL_FAILURE if the network could not be found
860  *  - WL_BUSY if the driver is already connected
861  *  - WL_RETRY if the driver is busy resolving a conflicting operation.
862  *    The operation should be retried after a wait (at least one call to wl_poll()
863  *    for polled implementations).
864  */
865 wl_err_t wl_connect_bssid(struct wl_mac_addr_t bssid);
866 
867 /*! \brief Disconnect from the network
868  *
869  * Disconnect from any currently associated network.
870  *
871  * The disconnection process will proceed asynchronously and will raise a
872  * WL_EVENT_MEDIA_DISCONNECTED event when completed.
873  * @return
874  *  - WL_SUCCESS if the disconnect process was started
875  *  - WL_FAILURE if the driver was not connected
876  *  - WL_RETRY if the driver is in the process of connecting.
877  *     In this case the disconnect must be retried after
878  *     the connection attempt has completed (resulted in a
879  *     WL_EVENT_MEDIA_CONNECTED or a WL_EVENT_CONN_FAILURE event).
880  */
881 wl_err_t wl_disconnect(void);
882 
883 /*!
884  * @brief Add a WEP encryption key to the device.
885  *
886  * Configure a key into the device. The key type (WEP-40, WEP-104)
887  * is determined by the size of the key (5 bytes for WEP-40, 13 bytes for WEP-104).
888  *
889  * @param key_idx The key index to set. Valid values are 0-3.
890  * @param key_len Length of key in bytes. Valid values are 5 and 13.
891  * @param key Key input buffer.
892  * @param bssid BSSID that the key applies to. If this is
893  *        the broadcast BSSID then the key is configured
894  *        as one of the default keys (not _the_ default key,
895  *        this must be set by calling set_default_wep_key()
896  *        after adding it). If the BSSID is a valid unicast
897  *        bssid then the key is configured as a key-mapping
898  *        key ( See 802.11-2007 8.2.1.3 ).
899  * @return
900  * - WL_SUCCESS on success.
901  * - WL_INVALID_LENGTH if the key length is bad.
902  * - WL_FAILURE on failure
903  */
904 wl_err_t wl_add_wep_key(uint8_t key_idx,
905                         size_t key_len,
906                         const void *key,
907                         struct wl_mac_addr_t *bssid);
908 
909 /*! @brief Set the default WEP key index.
910  *
911  * Select which WEP key to use for transmitted packets.
912  * For this to work correctly you must have added a WEP
913  * key with \a wl_add_wep_key() as a default key, using the
914  * same index as the one set in this call.
915  * @param key_idx Index of the key to make the default key.
916  *        Valid values are 0-3.
917  * @return WL_SUCCESS or WL_FAILURE.
918  */
919 wl_err_t wl_set_default_wep_key(uint8_t key_idx);
920 
921 /*! \brief Delete a WEP key.
922  *
923  * Deletes a WEP key from the driver.
924  *
925  * @param key_idx The index of the key to delete. Valid values are 0-3.
926  * @param bssid BSSID that the key applies to. If this is
927  *        the broadcast BSSID then the key deleted is a default key.
928  *        If the BSSID is a valid unicast bssid then the deleted
929  *        key is a key-mapping key.
930  * @return WL_SUCCESS or WL_FAILURE
931  */
932 wl_err_t wl_delete_wep_key(uint8_t key_idx, struct wl_mac_addr_t *bssid);
933 
934 /*! @brief Set a WPA/WPA2 passphase
935  *
936  * Associate a WPA/WPA2/RSN passphrase with a network.
937  * The number of passphrases that can be stored can
938  * vary but is always at least one. Passphrases can
939  * be added until \a wl_add_wpa_passphrase() returns
940  * WL_RESOURCES.
941  *
942  * @param net Network with which to associate the passphrase.
943  * @param passphrase Passphrase. Valid characters in a passphrase
944  *        must lie between ASCII 32-126 (decimal).
945  * @param len Length of passphrase. Valid lengths are 8-63.
946  * @param enc_type Encryption type. If this is set to ENC_TYPE_AUTO
947  *        then the most secure supported mode will be automatically
948  *        selected. Normally you only need to pass something else here
949  *        if you need to enforce picking a certain encryption mode when
950  *        the network supports several modes and you don't want to use
951  *        the best one.
952  * @param auth_mode Authentication mode. If this is set to AUTH_MODE_AUTO
953  *        then the most secure mode will be automatically selected.
954  *        Normally you only need to pass something else here if the network
955  *        announces support for both WPA and WPA2/RSN and the passphrases are
956  *        different.
957  * @return
958  *        - WL_SUCCESS
959  *        - WL_INVALID_ARGS if the passphrase length is invalid.
960  *        - WL_RESOURCES if no more passphrases can be added.
961  */
962 wl_err_t wl_set_passphrase(const struct wl_network_t *net,
963                            const char *passphrase,
964                            const size_t len,
965                            const enum wl_enc_type  enc_type,
966                            const enum wl_auth_mode auth_mode);
967 
968 /*! @brief Remove a WPA/WPA2 passphase
969  *
970  * Remove a WPA/WPA2/RSN passphrase associated with a network.
971  *
972  * @param net Network with which to associate the passphrase.
973  *        If net is NULL then all stored passphrases will be
974  *        cleared.
975  * @return
976  *        - WL_SUCCESS
977  *        - WL_FAILURE if no passphrase was associated with the net.
978  */
979 wl_err_t wl_clear_passphrase(struct wl_network_t *net);
980 
981 
982 /*! \brief Enable legacy power save mode
983  *
984  * Enable legacy power save mode. In legacy power save mode, the device
985  * will power down when idle. When connected, the device will wake up to
986  * receive beacon frames and any buffered data from the AP. The response
987  * time when legacy power save is enabled might therefore be as long as the
988  * AP beacon interval (mostly 100 ms). However, the throughput should not
989  * be affected.
990  *
991  * @return WL_SUCCESS or WL_FAILURE.
992  */
993 wl_err_t wl_enable_ps(void);
994 
995 /*! \brief Disable legacy power save mode
996  *
997  * @return WL_SUCCESS or WL_FAILURE.
998  */
999 wl_err_t wl_disable_ps(void);
1000 
1001 /*! \brief Configure power save parameters.
1002  *
1003  * @param use_ps_poll Use PS-Poll frames to retrieve buffered data. Any changes
1004  *        to this parameter will take effect upon next connect
1005  *        or when power save is enabled through wl_enable_ps().
1006  *        Note: To retrieve one buffered packet, the ps poll scheme
1007  *        needs one ps poll packet to the AP instead of two null
1008  *        packets in the power management bit scheme. Ps poll avoids
1009  *        the overhead of traffic monitoring time in active mode as
1010  *        well. But since each ps poll request can make the AP
1011  *        release only one buffered packet, it is not the optimal
1012  *        scheme for applications with heavy downlink traffic.
1013  * @param ps_traffic_timeout Timeout in [ms] to wait for more buffered data
1014  *        from AP. This setting has no effect if
1015  *        use_ps_poll is 1. Any changes to this parameter
1016  *        will take effect immediately.
1017  * @param ps_delay Power save will de delayed ps_delay [ms] after connecting to
1018  *        an AP.
1019  * @param rx_all_dtim If set to 1, then STA will wake up to listen to every
1020  *        beacon containing DTIM (delivery traffic indication messages) when
1021  *        connected. The actual DTIM interval is configured in the AP.
1022  *        If the DTIM interval, as configured in the AP, is larger than
1023  *        \a listen_interval, the STA will wakeup according to the
1024  *        \a listen_interval parameter.
1025  * @param listen_interval The Listen Interval field is used to indicate to the
1026  *        AP how often a STA in power save mode wakes to listen
1027  *        to beacon frames. The value of this parameter is expressed in units
1028  *        of Beacon Interval. An AP may use the Listen Interval information in
1029  *        determining the lifetime of frames that it buffers for a STA.
1030  *        Any changes to this parameter will take effect upon next association.
1031  *
1032  * @return WL_SUCCESS or WL_FAILURE.
1033  */
1034 wl_err_t wl_conf_ps(uint8_t use_ps_poll,
1035                     uint32_t ps_traffic_timeout,
1036                     uint32_t ps_delay,
1037                     uint8_t rx_all_dtim,
1038                     uint16_t listen_interval);
1039 
1040 /*! \brief Get the interface MAC address.
1041  *
1042  * Return the 802.3 MAC address of the network interface.
1043  *
1044  * @param buf Output buffer. It must be at least WL_MAC_ADDR_LENGTH
1045  *            bytes long and only the first WL_MAC_ADDR_LENGTH bytes
1046  *            will contain valid data.
1047  * @return
1048  *         - WL_FAILURE if the interface is not up.
1049  *         - WL_SUCCESS
1050  */
1051 wl_err_t wl_get_mac_addr(uint8_t* buf);
1052 
1053 /*! \brief Return the associated network.
1054  *
1055  * Return the description of the currently associated
1056  * network, if any.
1057  *
1058  * @return The network description, or NULL of the driver
1059  *  is unconnected.
1060  */
1061 struct wl_network_t* wl_get_current_network(void);
1062 /*!  @} */
1063 
1064 /** \defgroup wl_data Data Transfer
1065  *
1066  * \brief Packet processing interface.
1067  *
1068  * Note that the examples in this group assumes that the transport library
1069  * functions in the \a wl_transport group are being used. For more information,
1070  * See the documentation for those functions in the \a wl_transport group.
1071 
1072 For the IP stack integration you need to intercept received packets so
1073 they can be sent up the stack and to transmit packets coming down the
1074 stack.
1075 
1076 By default the wl_api library discards all data packets.  To receive
1077 them the application must register a rx interrupt service routine (isr)
1078 using the \a wl_register_rx_isr() function.
1079 
1080 \code
1081 static void rx_isr(void* ctx) {
1082        rx_pending = TRUE;
1083 }
1084 \endcode
1085 
1086 Since the rx_isr() function is only called in interrupt context, it is not
1087 safe to perform the actual read directly from rx_isr(). If an OS is used,
1088 the normal case is to signal a receiver thread to invoke the ip stack
1089 read function to read the pending data. In a system that runs without an OS
1090 (as in the example), a flag is set to indicate that wl_rx() can be invoked
1091 from the ip stack read function next time the ip stack is polled.
1092 The beginning of a ip stack read function can look like this
1093 
1094 \code
1095 static void ip_stack_rx_pkt() {
1096        char *pkt = malloc(MAX_PKT_SIZE);
1097        uint16_t len = MAX_PKT_SIZE;
1098 
1099        if (p == NULL) {
1100               app_error("Out of memory.");
1101               return;
1102        }
1103        wl_rx(pkt, &len);
1104        if (0 == len) {
1105               app_error("Packet reception failed.");
1106               free(pkt);
1107               return
1108        }
1109 }
1110 \endcode
1111 
1112 Since the ip_stack_rx_pkt() function should only be called when there is
1113 actually a packet ready to read you do not have to check the return value
1114 from \a wl_rx() since it only returns failure if there is no packet ready to
1115 read.
1116 
1117 A packet arriving from the WiFi interface can be either a data
1118 packet or a message from the WiFi hardware to the WiFi driver
1119 (which is implemented by the wl_api library). This means that
1120 wl_api must process every packet to decide if it is an internal
1121 message or a data frame that
1122 should be passed up to the application. Data packets are
1123 prefixed with an extra header containing some administrative
1124 information, and may be followed by padding bytes and so
1125 wl_api also needs to strip the extra header and any padding
1126 before the packet can be safely ingested by the IP stack.
1127 All this happens in the function \a wl_process_rx() which \b must
1128 be called on every packet received by a call to \a wl_rx().
1129 
1130 Continuing the ip_stack_rx_pkt() example
1131 
1132 \code
1133        {
1134                 char*  stripped_pkt;
1135                 size_t stripped_pkt_len;
1136                 uint16_t vlan;
1137                 int status;
1138 
1139                 status = wl_process_rx(pkt,
1140                                        len,
1141                                        &stripped_pkt,
1142                                        &stripped_pkt_len,
1143                                        &vlan);
1144                 if (WL_ABSORBED == status) {
1145                        // This is normal. The packet was a
1146                        // wl_api-internal message.
1147                        free(pkt);
1148                        return;
1149                 }
1150                 app_ip_stack_input(stripped_pkt,
1151                                    stripped_pkt_len,
1152                                    vlan);
1153                 free(pkt);
1154         }
1155 }
1156 \endcode
1157 
1158 If \a wl_process_rx() decides that the packet was a command it processes
1159 it and returns \a WL_ABSORBED to signal that the packet should
1160 not be used by anyone else. Otherwise stripped_pkt is
1161 pointing to the beginning of a 802.3 Ethernet frame of length
1162 stripped_pkt_len. If the IP stack supports VLAN and QoS
1163 the extra VLAN tag should be passed to the IP stack
1164 together with the packet. For IP stacks without this support the VLAN tag
1165 contents can safely be ignored, but it must still be filled in by \a wl_process_tx().
1166 
1167 To register the receive isr
1168 
1169 \code
1170         wl_register_rx_isr(rx_isr, NULL);
1171 \endcode
1172 
1173 Transmitting data packets happens in a similar way but does not
1174 require a callback/isr since the application/IP stack knows when it has
1175 packets to send.
1176 
1177 \code
1178 int ip_stack_tx_pkt(char *pkt, size_t len, uint16_t vlan_tag) {
1179         int status;
1180         char wlan_hdr[WL_HEADER_SIZE];
1181         // The packet must have an Ethernet header
1182         if (len < ETHERNET_HEADER_SIZE) {
1183                 app_error("Invalid packet length");
1184                 return 0;
1185         }
1186         hdr_len = sizeof wlan_hdr;
1187         status = wl_process_tx(pkt,
1188                                ETHERNET_HEADER_SIZE,
1189                                len,
1190                                wlan_hdr,
1191                                vlan_tag,
1192                                NULL);
1193         if ( WL_SUCCESS != status ) {
1194                 app_error("Packet processing failed");
1195                 return 0;
1196         }
1197         // Transmit the header first
1198         if (wl_tx(wlan_hdr, hdr_len) != WL_SUCCESS) {
1199                 app_error("Header transmission failed");
1200                 return 0;
1201         }
1202         // Then transmit the data packet
1203         if (wl_tx(pkt, len) != WL_SUCCESS) {
1204                 app_error("Packet transmission failed");
1205                 return 0;
1206         }
1207 }
1208 \endcode
1209 
1210 The final piece of the puzzle in the IP stack integration is
1211 the MAC address of the WiFi interface
1212 
1213 \code
1214         char mac_addr[WL_MAC_ADDR_LENGTH];
1215 
1216         wl_get_mac_addr(mac_addr);
1217         ip_stack_set_mac_address(mac_addr);
1218 \endcode
1219 
1220  *  @{
1221  */
1222 
1223 /*! Size of the wl_api packet header */
1224 #ifdef WFE_6_12
1225 #define WL_HEADER_SIZE 16
1226 #else
1227 #define WL_HEADER_SIZE 14
1228 #endif
1229 
1230 /*! Maximum packet size (including wl_api headers and paddings)
1231  *
1232  * Maximum packet size is obtained with the following data:
1233  *
1234  * 1500 bytes of Ethernet payload (MTU) + 14 bytes of Ethernet header +
1235  * WL_HEADER_SIZE of wl header. This data is then size-aligned to 16.
1236  *
1237  */
1238 #define WL_MAX_PKT_LEN 1536
1239 
1240 
1241 /*!
1242  * \brief Process rx packet.
1243  *
1244  * Processes a raw rx packet by unencrypting it (if necessary)
1245  * and stripping headers so as to output a 802.3 frame.
1246  *
1247  * wl_process_rx() will strip bytes both from the head and from the tail.
1248  *
1249  * Upon return from wl_process_rx(), the pointer at stripped_pkt will
1250  * point to the start of the Ethernet header, hence adjusting the offset
1251  * by WL_HEADER_LEN bytes. Any padding (added by the wifi device) will
1252  * be removed from the tail of the packet, hence making len smaller.
1253  *
1254  * The wl_api library of the device will not perform any Ethernet padding
1255  * removal. The padding removal performed by wl_process_rx() is only for
1256  * the padding used in the protocol shared by the host and the device.
1257  * This padding is mainly there to ensure that the host does not have to
1258  * deal with rx of odd-sized data buffers (which some DMA's have problems
1259  * to handle).
1260  *
1261  * @param pkt Input buffer (raw packet)
1262  * @param pkt_len Length of the input buffer (in bytes)
1263  * @param stripped_pkt Pointer to the packet with the
1264  *  transport header stripped.
1265  * @param stripped_pkt_len Length of the stripped packet.
1266  * @param vlanid_prio VLAN ID and 802.1p priority value
1267  * using following format:
1268  * <PRE>
1269  *        1
1270  *  5|432109876543|210
1271  *  -+------------+---
1272  *  0|   VLANID   |PRI
1273  * </PRE>
1274  *
1275  * @returns
1276  *          - WL_FAILURE
1277  *          - WL_ABSORBED if the packet was an internal driver command
1278  *                      and not a proper data packet. The packet should
1279  *                      be freed and the stripped_pkt will not point
1280  *                      to a valid packet.
1281  *          - WL_SUCCESS
1282  */
1283 wl_err_t wl_process_rx(char *pkt, size_t pkt_len, char **stripped_pkt,
1284                        size_t *stripped_pkt_len, uint16_t *vlanid_prio);
1285 
1286 /*! \brief Process tx packet.
1287  *
1288  * Prepare tx packet for transmission.
1289  *
1290  * This function is typically used only by the TCP/IP stack driver.
1291  *
1292  * Takes a Ethernet II frame header and generates a message passing header
1293  * for it.
1294  *
1295  * The caller should ensure that any frames injected into wl_process_tx()
1296  * are proper Ethernet frames. The wl_api library or the device will not
1297  * perform any Ethernet padding if the frames are too short.
1298  *
1299  * The Ethernet header is assumed to have the following layout :
1300  * <dst addr:6><src addr:6><type:2>...
1301  * The rest of the Ethernet header buffer (if any) is ignored.
1302  *
1303  * A note on the TX packet representation :
1304  * If your TX packets are simple contiguous buffers you can ignore
1305  * the rest of this note and pass NULL in parameter \a pkt_handle.
1306  * A TX packet may have a more complex structure than a RX packet
1307  * (which must be a contiguous, flat buffer). The IP stack may
1308  * for example represent a packet as a linked list of buffers where
1309  * the Ethernet header, the IP header and other headers, are represented
1310  * by separate buffers. In some cases, such as when the driver is
1311  * running in SoftAP mode, a TX packet has to be copied and queued
1312  * internally for later processing and to support this when packets
1313  * have a complicated structure a special data access function can
1314  * be registered. See \a wl_register_pkt_read_cb() for details.
1315  * If you use \a wl_process_tx() with non-simple packets you
1316  * should pass a handle to the packet in parameter \a pkt_handle
1317  * and register an access function with \a wl_register_pkt_read_cb().
1318  *
1319  * @param eth_hdr Input buffer (Ethernet header)
1320  * @param eth_hdr_len Input buffer length (must be >= 14)
1321  *  This is usually the same as pkt_len unless e.g linked list or buffers
1322  *  chained in other ways are being used.
1323  * @param pkt_len Length of the complete data packet (in bytes)
1324  * @param hdr Pointer to the header buffer (must be
1325  * allocated by the caller). The length of the buffer
1326  * must be at least WL_HEADER_SIZE bytes.
1327  * @param vlanid_prio VLAN ID and 802.1p priority value
1328  * using following format:
1329  * <PRE>
1330  *        1
1331  *  5|432109876543|210
1332  *  -+------------+---
1333  *  0|   VLANID   |PRI
1334  * </PRE>
1335  * Ignored for legacy association (no WMM)
1336  * @param pkt_handle A handle to the complete packet. If this parameter
1337  *  is NULL then \a eth_hdr is expected to point to the whole packet
1338  *  in a single contiguous buffer (the default). If a different packet
1339  *  representation is used this parameter should be a handle to the
1340  *  complete packet and will be passed unmodified to the data
1341  *  access function that was registered with \a wl_register_pkt_read_cb().
1342  *
1343  * @returns
1344  *          - WL_FAILURE
1345  *          - WL_RESOURCES if packet can not be processed at the moment.
1346  *                       The caller must either drop the packet or try
1347  *                       retransmit it later.
1348  *          - WL_AVAIL     if network not available
1349  *          - WL_SUCCESS   if packet is ready for transmission through wl_tx().
1350  */
1351 wl_err_t wl_process_tx(char *eth_hdr,
1352                        size_t eth_hdr_len,
1353                        size_t pkt_len,
1354                        char *hdr,
1355                        uint16_t vlanid_prio,
1356                        void *pkt_handle);
1357 
1358 
1359 /*! \brief Get current TX and RX rate used for data transfer
1360  *
1361  * During transmission and reception of data, the actual rate used will depend
1362  * on the signal quality. This function can be used to get the actual rate used
1363  * for the last tx and rx data.
1364  *
1365  * @param tx will hold the tx rate upon successful return.
1366  * @param rx will hold the rx rate upon successful return.
1367  *
1368  * @return
1369  * - WL_SUCCESS on success
1370  * - WL_FAILURE on failure.
1371  */
1372 wl_err_t wl_get_rate(wl_rate_t *tx, wl_rate_t *rx);
1373 
1374 
1375 /*! @} */ /* End wl_data group */
1376 
1377 
1378 /** \defgroup wl_transport Transport interface
1379  *
1380  * \brief Low level transport interface.
1381  *
1382  * These functions access the low level transport driver which makes
1383  * the application independent of the actual physical transport
1384  * layer (usually SDIO or SPI).
1385  *
1386 
1387 For applications running on an real time kernel or without an
1388 operating system, the provided transport library will fit right into the
1389 application design. However, when running on a more complex operating system
1390 (such as windows or linux) which has its own transport primitivies and
1391 components (and probably its own IP stack) it might be preferred to design a
1392 custom transport library for that specific environment. Therefore, these
1393 transport interface functions are fully optional.
1394 
1395 
1396  *  @{
1397  */
1398 
1399 #define WL_RX_MIN_PKT_LEN    32
1400 
1401 
1402 /*! \brief WiFi event callback.
1403  *
1404  * This function is invoked in interrupt context when there is new data
1405  * available from the mac. This function is supplied by the user
1406  * of the API.
1407  *
1408  * This function is typically used only by the TCP/IP stack driver.
1409  *
1410  * @param ctx   A context handle. This handle is passed
1411  *              untouched to the callback and has the same value
1412  *              as the context registered with the callback in
1413  *              wl_register_event_cb().
1414  */
1415 typedef void (*wl_rx_isr_t) (void* ctx);
1416 
1417 
1418 /*! \brief Firmware access function.
1419  *
1420  * Reads the WiFi firmware image. This function is supplied by
1421  * the user of this API since storage for the firmware image is
1422  * managed by the application.
1423  *
1424  * This function should read the specified number of bytes of the
1425  * firmware image starting at the specified \a offset. The number of
1426  * bytes to read is given in \a len. Upon return, \a buf should point
1427  * to a buffer which holds the read data and the number of valid bytes
1428  * in \a buf is returned from the call.
1429  *
1430  * This function will be called repeatedly until the complete firmware
1431  * image has been read.
1432  *
1433  * This function may be called again at any time while the driver is
1434  * running to download further pieces of the WiFi firmware image as
1435  * needed by the runtime requirements. This will normally only happen
1436  * when the driver switches between networks of different kinds such
1437  * as from WEP to WPA, or from ESS to IBSS for example.
1438  *
1439  * For convenience, any time a firmware chunk has been completely
1440  * downloaded this function will be called once with the \a buf
1441  * parameter set to NULL to indicate that no more data is needed right
1442  * now and that any dynamically allocated buffers which holds firmware
1443  * data can be freed without much performance impact.
1444  *
1445  * @param ctx Opaque context pointer as provided to \a wl_init() that will be
1446  *            passed back to the callback.
1447  * @param buf Should be assigned the address of the buffer holding the read
1448  *            data upon return. This parameter can be NULL which indicates
1449  *            that there are no further immediately pending accesses.
1450  * @param offset Offset in bytes from the start of the firmware image.
1451  *            Data should be copied into buf starting at \a offset.
1452  * @param len The number of bytes to copy into \a buf.
1453  * @return The number of bytes copied into buf. This may be smaller than
1454  *         \len if the implementation of the function so requires.
1455  */
1456 typedef size_t (wl_fw_read_cb_t)(void *ctx,
1457                                  const uint8_t **buf,
1458                                  size_t offset,
1459                                  size_t len);
1460 
1461 
1462 /*! \brief Initialize the transport interface and download the WiFi firmware
1463  * image to the device.
1464  *
1465  * This operation will proceed synchronously until the firmware is completely
1466  * downloaded. wl_init() should be called after this function has returned to
1467  * perform device initialization.
1468  *
1469  * @param fw_read_cb callback function to invoke during firmware download.
1470  * @param ctx Opaque context pointer that will be passed to the callbacks
1471  *            when they are invoked. This parameter is never
1472  *            accessed by the API.
1473  * @param mode will hold the host attention mode used by the transport layer.
1474  *         This parameter can be passed directly to \a wl_init().
1475  *
1476  * @return
1477  *
1478  * - WL_CARD_FAILURE if the wl hardware device is not available
1479  * - WL_FIRMWARE_INVALID if the firmware obtained through fw_read_cb is
1480  *                       invalid.
1481  * - WL_OOM if the necessary memory could not be allocated.
1482  */
1483 wl_err_t wl_transport_init(wl_fw_read_cb_t *fw_read_cb,
1484                            void *ctx,
1485                            enum wl_host_attention_mode *mode);
1486 
1487 /*! \brief WiFi driver forward progress function
1488  *
1489  * This function must be called in polled environments to
1490  * ensure forward progress. The call can be made as often as possible from
1491  * the main application loop. However, the call will not have any effect unless
1492  * there is an interrupt pending from the hardware.
1493  *
1494  * In interrupt mode, wl_poll() must be called if no interrupt
1495  * handler is registered through wl_register_rx_isr(). When an interrupt
1496  * handler is registered, it is no longer necessary to invoke wl_poll().
1497  *
1498  * Note that this function should not be invoked from interrupt context.
1499  *
1500  */
1501 void wl_poll(void);
1502 
1503 
1504 /*! \brief Register RX callback
1505  *
1506  * Register function to be called by the low level transport driver
1507  * when a new packet is available or when there is a state change in the
1508  * data path. When invoked, any pending data can be fetched by calling wl_rx().
1509  *
1510  * This function is typically used only by the TCP/IP stack driver.
1511  * Note, the registered function is called in interrupt context.
1512  *
1513  * @param isr rx interrup handler.
1514  * @param ctx Opaque context pointer that is passed unmodified to the
1515  * rx_cb callback when it is invoked.
1516  *
1517  * @return WL_SUCCESS
1518  */
1519 wl_err_t wl_register_rx_isr(wl_rx_isr_t isr, void* ctx);
1520 
1521 
1522 /*! \brief Read pending packet
1523  *
1524  * Read a pending packet from the low level transport driver.
1525  * The read packet must be passed to the wl_process_rx() function
1526  * for proper driver operation.
1527  *
1528  * @param buf Buffer to read the packet into. This buffer must be
1529  *            at least WL_MAX_PKT_LEN bytes long.
1530  * @param len Length of buf in bytes. Contains the length of the
1531  *            read packet in bytes on output.
1532  * @return
1533  *         - WL_FAILURE if no RX packet is pending.
1534  *         - WL_SUCCESS
1535  */
1536 wl_err_t wl_rx(uint8_t* buf, uint16_t* len);
1537 
1538 /*! \brief Send processed tx packet
1539  *
1540  * Send a packet to the low level transport driver.
1541  * This packet has to have been successfully processed by the
1542  * wl_process_tx() function.
1543  *
1544  * @param buf Buffer to send.
1545  * @param len Length of buf in bytes.
1546  *
1547  * @return
1548  *         - WL_FAILURE if the interface is not ready to send.
1549  *         - WL_SUCCESS if the packet was successfully transmitted.
1550  */
1551 wl_err_t wl_tx(const uint8_t* buf, uint16_t len);
1552 
1553 
1554 /*! \brief Configure data alignment
1555  *
1556  * This function can be used if the host SDIO/SPI controller has certain
1557  * requirements on the data transfer sizes that can be used on the SDIO/SPI bus.
1558  *
1559  * If the txsize parameter is non-zero, additional padding data should be added
1560  * when performing the low level transfer of data buffer of sizes that are not
1561  * a multiple of the size_align parameter. See \ref wl_sdio and \ref wl_spi for
1562  * more information.
1563  *
1564  * @param txsize will configure the size alignment for tx data.
1565  *
1566  */
1567 void wl_conf_alignment(uint8_t txsize);
1568 
1569 
1570 /*! @} */ /* End wl_transport group */
1571 
1572 
1573 /** \defgroup wl_custom Custom environment support
1574  *
1575  * \brief Support for custom environments
1576  *
1577  * These functions should only be used in cases where the transport library is
1578  * not used at all. This usually applies to operating systems and environments
1579  * where there already exists a transport layer framework, e.g. linux or
1580  * windows.
1581  *
1582  *
1583 
1584 Note that the \a wl_poll() function is part of the transport library. Therefore,
1585 it should not be used in custom environments. Therefore, it is necessary to
1586 implement a custom polling or interrupt based scheme to ensure that any
1587 incoming packets are processed by the core.
1588 
1589  *  @{
1590  */
1591 
1592  /*! \brief Wakeup callback function.
1593  *
1594  * Invoked when the WiFi device should wake up from power save mode.
1595  * This function should send the proper commands to the device.
1596  *
1597  * Note that this type should only be used in custom environments, where
1598  * the transport library is not used.
1599  *
1600  * @param ctx Opaque context pointer as provided to \a wl_register_wakeup_cb()
1601  *            that will be passed back to the callback.
1602  * @param wakeup indicates whether wakeup should be set or cleared in the
1603  *               device.
1604  */
1605 typedef void (wl_wakeup_cb_t)(void* ctx, uint8_t wakeup);
1606 
1607 /*! \brief Register wakeup callback function.
1608  *
1609  * Register a function that will be invoked when the WiFi device should wake
1610  * up from power save mode.
1611  *
1612  * Note that this function should only be used in custom environments, where
1613  * the transport library is not used.
1614  *
1615  * @param wakeup_cb Will be invoked when the device should wakeup from sleep
1616  *                 mode.
1617  * @param ctx Opaque context pointer that will be passed back to the callback.
1618  */
1619 void wl_register_wakeup_cb(wl_wakeup_cb_t *wakeup_cb, void *ctx);
1620 
1621 
1622 /*! \brief Management tx callback function.
1623  *
1624  * Invoked when the a management message should be transmitted to the
1625  * WiFi device. This function should ensure that the message is passed through
1626  * to the device and should never fail.
1627  *
1628  * Note that this type should only be used in custom environments, where
1629  * the transport library is not used.
1630  *
1631  * @param ctx Opaque context pointer as provided to \a wl_register_mgmt_tx_cb()
1632  *            that will be passed back to the callback.
1633  * @param buf Points to the buffer which holds the management data,
1634  * @param len Size of the buffer.
1635  */
1636 typedef void (wl_mgmt_tx_cb_t)(void *ctx, const uint8_t *buf, uint16_t len);
1637 
1638 
1639 /*! \brief Register management tx callback function
1640  *
1641  * Register a function that will be invoked when a management message should
1642  * be transmitted to the device.
1643  *
1644  * Note that this function should only be used in custom environments, where
1645  * the transport library is not used.
1646  *
1647  * IMPORTANT : In a custom environment without a transport library \a
1648  *             wl_register_mgmt_tx_cb() \b must have been called
1649  *             before \a wl_fw_download() is called since \a
1650  *             wl_fw_download() depends on the \a mgmt_tx_cb() to send
1651  *             the firmware data to the WiFi chip.
1652  *
1653  * @param mgmt_tx_cb The callback function to invoke.
1654  * @param ctx Opaque context pointer that  will be passed back to the callback.
1655  */
1656 void wl_register_mgmt_tx_cb(wl_mgmt_tx_cb_t *mgmt_tx_cb, void *ctx);
1657 
1658 
1659 
1660 /*! \brief Download the WiFi firmware image to the device.
1661  *
1662  * This operation will proceed synchronously until the firmware is completely
1663  * downloaded. wl_init() should be called after this function has returned to
1664  * perform device initialization. This function depends on \a
1665  * wl_register_mgmt_tx_cb(). See that function for details.
1666  *
1667  * @param ctx Opaque context pointer that will be passed to the callbacks
1668  *            when they are invoked. This parameter is never
1669  *            accessed by the API.
1670  * @param fw_read_cb callback function to invoke during firmware download.
1671  *
1672  * @return
1673  *
1674  * - WL_CARD_FAILURE if the wl hardware device is not available
1675  * - WL_FIRMWARE_INVALID if the firmware obtained through fw_read_cb is
1676  *                       invalid.
1677  * - WL_OOM if the necessary memory could not be allocated.
1678  */
1679  wl_err_t wl_fw_download(wl_fw_read_cb_t *fw_read_cb, void *ctx);
1680 
1681 
1682 
1683 /*! @} */ /* End wl_custom group */
1684 
1685 
1686 
1687 #endif
1688