source: arduino-1-6-7/trunk/fuentes/arduino-ide-amd64/hardware/arduino/avr/firmwares/wifishield/wifiHD/src/main.c @ 4837

Last change on this file since 4837 was 4837, checked in by daduve, 3 years ago

Adding new version

File size: 10.8 KB
Line 
1/*
2 * main.c
3 *
4 *  Created on: May 27, 2010
5 *      Author: mlf by Metodo2 srl
6 */
7
8//#define _TEST_SPI_
9
10#include <compiler.h>
11#include "board.h"
12#include "gpio.h"
13
14#include <stdint.h>
15#include "wl_api.h"
16#include "wl_cm.h"
17
18#include "lwip/init.h"
19#include "lwip/dhcp.h"
20#include "lwip/dns.h"
21#include "lwip/tcp.h"
22#include "netif/etharp.h"
23#include "netif/wlif.h"
24
25#include "board_init.h"
26#include "trace.h"
27
28#include "timer.h"
29#include "util.h"
30#include "cmd_wl.h"
31#include "ping.h"
32#include "ard_tcp.h"
33#include "spi.h"
34#include "ard_spi.h"
35#include "delay.h"
36#include "tc.h"
37#include "debug.h"
38#include "ard_utils.h"
39#include <lwip_setup.h>
40
41/* FIRMWARE version */
42const char* fwVersion = "1.1.0";
43
44#if BOARD == ARDUINO
45#if !defined(DATAFLASH)
46#include "wl_fw.h"
47
48int fw_download_init(void) { return 0;}
49void fw_download_cb(void* ctx, uint8_t** buf, uint32_t* len)
50{
51        //printk("Fw download not available!\n");
52        /* remember accross different calls */
53        static uint8_t* _fw_buf = (uint8_t*)&fw_buf[0];
54        static uint32_t offset = 0;
55
56        /* when firmware download is completed, this function will be invoked
57         * on additional time with the input value of len set to 0. we can free
58         * the firmware buffer at this time since it's no longer needed.
59         */
60        if (*len == 0) {
61                return;
62        }
63
64        /* decide how much to read. we know *len bytes remains, but we only have
65         * room for SECTOR_SIEZ bytes in our buffer (fw_buf)
66         */
67        uint32_t fw_len = *len;
68
69        *buf = (_fw_buf+offset);
70        *len = fw_len;
71
72        /* we need to know where to start reading upon next call */
73        offset += fw_len;
74
75}
76#else
77#include "fw_download.h"
78#endif
79#endif
80
81bool ifStatus = false;
82bool scanNetCompleted = false;
83
84static bool initSpiComplete = false;
85
86// variable used as enable flag for debug prints
87DEFINE_DEBUG_VARIABLES();
88
89/**
90 *
91 */
92static void
93wl_cm_scan_cb(void* ctx)
94{
95        INFO_INIT("Scan Completed!\n");
96    scanNetCompleted=true;
97}
98
99/**
100 *
101 */
102static void
103wl_cm_conn_cb(struct wl_network_t* net, void* ctx)
104{
105        struct ctx_server* hs = ctx;
106
107        LINK_LED_ON();
108
109        INFO_INIT("Connection cb...\n");
110
111        printk("link up, connected to \"%s\"\n", ssid2str(&net->ssid));
112    if ( hs->net_cfg.dhcp_enabled == DYNAMIC_IP_CONFIG ) {
113                        INFO_INIT("Start DHCP...\n");
114                    printk("requesting dhcp ... ");
115            int8_t result = dhcp_start(hs->net_cfg.netif);
116            printk((result==ERR_OK)?"OK\n":"FAILED\n");
117            hs->net_cfg.dhcp_running = 1;
118    }
119    else {
120        netif_set_up(hs->net_cfg.netif);
121    }
122
123    INFO_INIT("Start DNS...\n");
124    dns_init();
125}
126
127
128/**
129 *
130 */
131static void
132wl_cm_disconn_cb(void* ctx)
133{
134        struct ctx_server* hs = ctx;
135
136        LINK_LED_OFF();
137        INFO_INIT("Disconnection cb...\n");
138
139    if (hs->net_cfg.dhcp_running) {
140        printk("link down, release dhcp\n");
141        dhcp_release(hs->net_cfg.netif);
142        dhcp_stop(hs->net_cfg.netif);
143        hs->net_cfg.dhcp_running = 0;
144     } else {
145         printk("link down\n");
146         netif_set_down(hs->net_cfg.netif);
147     }
148
149     set_result_cmd(WL_FAILURE);
150}
151
152#if 0
153static void wl_cm_err_cb(void* ctx)
154{
155    int err = *(int*)ctx;
156    WARN("Error: %d\n", err);
157    set_result_cmd(err);
158}
159#endif
160
161/**
162 *
163 */
164static void
165ip_status_cb(struct netif* netif)
166{
167        INFO_INIT("IP status cb...\n");
168        if (netif_is_up(netif)) {
169            set_result_cmd(WL_SUCCESS);
170            printk("bound to %s\n", ip2str(netif->ip_addr));
171            ifStatus = true;
172        }else{
173                ifStatus = false;
174                closeConnections();
175                WARN("Interface not up!\n");
176        }
177}
178
179
180/**
181 *
182 */
183void
184led_init(void)
185{
186        gpio_enable_gpio_pin(LED0_GPIO);
187        gpio_enable_gpio_pin(LED1_GPIO);
188        gpio_enable_gpio_pin(LED2_GPIO);
189        LINK_LED_OFF();
190        ERROR_LED_OFF();
191        DATA_LED_OFF();
192}
193
194
195void tc_init(void)
196{
197          // The timer/counter instance and channel number are used in several functions.
198          // It's defined as local variable for ease-of-use causes and readability.
199          volatile avr32_tc_t *tc = WIFI_TC;
200
201          // Options for waveform genration.
202          tc_waveform_opt_t waveform_opt =
203          {
204            .channel  = WIFI_TC_CHANNEL_ID,        // Channel selection.
205
206            .bswtrg   = TC_EVT_EFFECT_NOOP,           // Software trigger effect on TIOB.
207            .beevt    = TC_EVT_EFFECT_NOOP,           // External event effect on TIOB.
208            .bcpc     = TC_EVT_EFFECT_NOOP,           // RC compare effect on TIOB.
209            .bcpb     = TC_EVT_EFFECT_NOOP,           // RB compare effect on TIOB.
210
211            .aswtrg   = TC_EVT_EFFECT_NOOP,           // Software trigger effect on TIOA.
212            .aeevt    = TC_EVT_EFFECT_NOOP,           // External event effect on TIOA.
213            .acpc     = TC_EVT_EFFECT_TOGGLE,         // RC compare effect on TIOA: toggle.
214            .acpa     = TC_EVT_EFFECT_TOGGLE,         // RA compare effect on TIOA: toggle (other possibilities are none, set and clear).
215
216            .wavsel   = TC_WAVEFORM_SEL_UP_MODE_RC_TRIGGER,// Waveform selection: Up mode with automatic trigger(reset) on RC compare.
217            .enetrg   = FALSE,                        // External event trigger enable.
218            .eevt     = TC_EXT_EVENT_SEL_TIOB_INPUT,  // External event selection.
219            .eevtedg  = TC_SEL_NO_EDGE,               // External event edge selection.
220            .cpcdis   = FALSE,                        // Counter disable when RC compare.
221            .cpcstop  = FALSE,                        // Counter clock stopped with RC compare.
222
223            .burst    = TC_BURST_NOT_GATED,           // Burst signal selection.
224            .clki     = TC_CLOCK_RISING_EDGE,         // Clock inversion.
225            .tcclks   = TC_CLOCK_SOURCE_TC2           // Internal source clock 3, connected to fPBA / 2.
226          };
227
228          // Assign I/O to timer/counter channel pin & function.
229          gpio_enable_module_pin(WIFI_TC_CHANNEL_PIN, WIFI_TC_CHANNEL_FUNCTION);
230
231          // Initialize the timer/counter.
232          tc_init_waveform(tc, &waveform_opt);  // Initialize the timer/counter waveform.
233
234          // Set the compare triggers.
235          tc_write_ra(tc, WIFI_TC_CHANNEL_ID, 0x01A4);     // Set RA value.
236          tc_write_rc(tc, WIFI_TC_CHANNEL_ID, 0x0348);     // Set RC value.
237
238          // Start the timer/counter.
239          tc_start(tc, WIFI_TC_CHANNEL_ID);
240
241}
242
243/**
244 *
245 */
246void 
247poll(struct ctx_server* hs)
248{
249        /* this will trigger any scheduled timer callbacks */
250        timer_poll();
251
252        /* handle console input */
253        console_poll();
254
255        /* wl api 'tick' */
256        wl_tick(timer_get_ms());
257
258        /* lwip driver poll */
259        wlif_poll(hs->net_cfg.netif);
260
261        if (initSpiComplete) spi_poll(hs->net_cfg.netif);
262
263#ifdef WITH_GUI
264        gui_exec(timer_get_ms());
265#endif
266}
267
268void initShell(void* ctx)
269{
270        /* initialize shell */
271        INFO_INIT("Shell init...\n");
272        console_init();
273        console_add_cmd("scan", cmd_scan, NULL);
274        console_add_cmd("connect", cmd_connect, NULL);
275        console_add_cmd("setkey", cmd_setkey, NULL);
276        console_add_cmd("status", cmd_status, ctx);
277        console_add_cmd("debug", cmd_debug, NULL);
278        console_add_cmd("dumpBuf", cmd_dumpBuf, NULL);
279                console_add_cmd("ipconfig", cmd_set_ip, ctx);
280#ifdef ADD_CMDS
281        console_add_cmd("powersave", cmd_power, NULL);
282        console_add_cmd("psconf", cmd_psconf, NULL);
283#endif
284#ifdef PING_CMD
285        console_add_cmd("ping", cmd_ping, NULL);
286#endif
287        console_add_cmd("ttcp", cmd_ttcp, NULL);
288#ifdef WITH_WPA
289        console_add_cmd("wpass", cmd_setpass, NULL);
290        console_add_cmd("dpass", cmd_delpass, NULL);
291#endif
292#ifdef _SPI_STATS_
293        console_add_cmd("spiStat", cmd_statSpi, NULL);
294        console_add_cmd("resetSpiStat", cmd_resetStatSpi, NULL);
295#endif
296#ifdef _DNS_CMD_
297        console_add_cmd("getHost", cmd_gethostbyname, NULL);
298        console_add_cmd("setDNS", cmd_setDnsServer, NULL);
299#endif
300        console_add_cmd("startSrv", cmd_startSrv, NULL);
301        console_add_cmd("startCli", cmd_startCli, NULL);
302        console_add_cmd("sendUdp", cmd_sendUdpData, NULL);
303
304}
305
306/**
307 *
308 */
309void 
310wl_init_complete_cb(void* ctx) 
311{
312        struct ctx_server *hs = ctx;
313    struct ip_addr ipaddr, netmask, gw;
314        wl_err_t wl_status;
315       
316        if (hs->net_cfg.dhcp_enabled == INIT_IP_CONFIG)
317        {
318                IP4_ADDR(&gw, 0,0,0,0);
319                IP4_ADDR(&ipaddr, 0,0,0,0);
320                IP4_ADDR(&netmask, 0,0,0,0);
321                       
322                /* default is dhcp enabled */
323                hs->net_cfg.dhcp_enabled = DYNAMIC_IP_CONFIG;
324        }
325
326    start_ip_stack(&hs->net_cfg,
327                   ipaddr,
328                   netmask,
329                   gw);
330    netif_set_status_callback(hs->net_cfg.netif, ip_status_cb);
331
332    INFO_INIT("Starting CM...\n");
333    /* start connection manager */
334    wl_status = wl_cm_init(wl_cm_scan_cb, wl_cm_conn_cb, wl_cm_disconn_cb, hs);
335    ASSERT(wl_status == WL_SUCCESS, "failed to init wl conn mgr");
336    wl_cm_start();
337
338    wl_scan();
339
340    if (initSpi(hs)){
341        WARN("Spi not initialized\n");
342    }else
343    {
344        initSpiComplete = true;
345        AVAIL_FOR_SPI();
346    }
347
348    hs->wl_init_complete = 1;
349}
350
351void startup_init(void)
352{
353        INIT_SIGNAL_FOR_SPI();
354        BUSY_FOR_SPI();
355
356        // if DEBUG enabled use DEB_PIN_GPIO for debug purposes
357    DEB_PIN_ENA();
358        DEB_PIN_ENA(2);
359    DEB_PIN_UP();
360        DEB_PIN_UP(2);
361}
362
363const char timestamp[] = __TIMESTAMP__;
364
365/**
366 *
367 */
368int
369main(void)
370{
371        wl_err_t wl_status;
372        int status;
373        struct ctx_server *hs;
374    enum wl_host_attention_mode mode;
375
376    startup_init();
377
378    board_init();
379
380    led_init();
381
382    tc_init();
383
384    delay_init(FOSC0);
385
386#ifdef _TEST_SPI_
387    for (;;)
388    {
389         /* handle console input */
390
391        console_poll();
392
393        spi_poll(NULL);
394
395     }
396#else
397    printk("Arduino Wifi Startup... [%s]\n", timestamp);
398
399    size_t size_ctx_server = sizeof(struct ctx_server);
400        hs = calloc(1, size_ctx_server);
401        ASSERT(hs, "out of memory");
402
403        size_t size_netif = sizeof(struct netif);
404        hs->net_cfg.netif = calloc(1, size_netif);
405        ASSERT(hs->net_cfg.netif, "out of memory");
406        hs->net_cfg.dhcp_enabled = INIT_IP_CONFIG;
407
408        INFO_INIT("hs:%p size:0x%x netif:%p size:0x%x\n", hs, size_ctx_server,
409                        hs->net_cfg.netif, size_netif);
410    initShell(hs);
411        timer_init(NULL, NULL);
412    lwip_init();
413       
414        status = fw_download_init();
415        ASSERT(status == 0, "failed to prepare for firmware download\n");
416
417    wl_status = wl_transport_init(fw_read_cb, hs, &mode);
418    if (wl_status != WL_SUCCESS)
419            goto err;
420    INFO_INIT("Mode: 0x%x\n", mode);
421    wl_status = wl_init(hs, wl_init_complete_cb, mode);
422    if (wl_status != WL_SUCCESS)
423            goto err;
424
425    /* start main loop */
426    for (;;)
427            poll(hs);
428
429
430err:
431    /* show error message on console and display if wlan initialization fails */
432
433#define WL_CARD_FAILURE_STR     "Could not detect wl device, aborting\n"
434#define WL_FIRMWARE_INVALID_STR "Invalid firmware data, aborting\n"
435#define WL_OTHER_FAILURE_STR    "Failed to start wl initialization\n"
436
437    switch (wl_status) {
438    case WL_CARD_FAILURE:
439            printk(WL_CARD_FAILURE_STR);
440            break;
441
442    case WL_FIRMWARE_INVALID:
443            printk(WL_FIRMWARE_INVALID_STR);
444            break;
445
446    default:
447            printk(WL_OTHER_FAILURE_STR);
448            break;
449    }
450    for (;;) {
451            timer_poll();
452    }
453#endif
454}
Note: See TracBrowser for help on using the repository browser.