CDC/ECM driver for mbed, based on USBDevice by mbed-official. Uses PicoTCP to access Ethernet USB device. License: GPLv2

Dependents:   USBEthernet_TEST

Fork of USB_Ethernet by Daniele Lacamera

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers pico_dev_mbed_usb.cpp Source File

pico_dev_mbed_usb.cpp

00001 /*********************************************************************
00002 PicoTCP. Copyright (c) 2012 TASS Belgium NV. Some rights reserved.
00003 See LICENSE and COPYING for usage.
00004 Do not redistribute without a written permission by the Copyright
00005 holders.
00006 
00007 Authors: Daniele Lacamera, Julien Duraj
00008 *********************************************************************/
00009 #include "mbed.h"
00010 #include "USBCDC_ECM.h"
00011 #include "ethernet_api.h"
00012 #include "pico_dev_mbed_usb.h"
00013 
00014 extern "C" {
00015 #include "pico_device.h"
00016 #include "pico_stack.h"
00017 }
00018 
00019 struct pico_device_mbed_usb {
00020   struct pico_device dev;
00021   int bytes_left_in_frame;
00022   USBCDC_ECM *ecm;
00023 };
00024 
00025 #define ETH_MTU 1514
00026 static uint8_t buf[ETH_MTU];
00027 static int rx_i = 0;
00028 
00029 Serial __pc(p9, p10, "Serial port"); // tx, rx
00030 
00031 extern "C" {
00032 
00033 static int pico_mbed_usb_send(struct pico_device *dev, void *buffer, int len)
00034 {
00035   int ret, sent = 0;
00036   struct pico_device_mbed_usb *mb = (struct pico_device_mbed_usb *) dev;
00037 
00038   //printf("USBETH> sending %d bytes\n", len);
00039   if (len > ETH_MTU)
00040     return -1;
00041   while (sent < len) {
00042     int to_send = 64;
00043     if ((len - sent) < to_send) 
00044         to_send = len -sent;
00045     ret = mb->ecm->send(((uint8_t *)buffer) + sent, to_send);
00046     if (!ret)
00047         return -1;
00048     sent += to_send;
00049   }
00050   if ((len % 64) == 0) {
00051     mb->ecm->send(((uint8_t *)buffer), 0);
00052   }
00053   //printf("USBETH> Sent %d bytes.\n", sent);
00054   return sent;
00055 }
00056 
00057 static int pico_mbed_usb_poll(struct pico_device *dev, int loop_score)
00058 {
00059   int size;
00060   struct pico_device_mbed_usb *mb = (struct pico_device_mbed_usb *) dev;
00061   
00062   while(loop_score > 0)
00063   {
00064     bool ret;
00065     /* check for new frame(s) */
00066     ret = mb->ecm->readEP_NB(buf + rx_i, (uint32_t *)&size);
00067     
00068     /* return if no frame has arrived */
00069     if (!ret)
00070       return loop_score;
00071       
00072     rx_i += size;
00073     if (size < 64) {
00074         /* read and process frame */
00075         pico_stack_recv(dev, buf, rx_i);
00076         loop_score--;
00077         rx_i = 0;
00078     }
00079   }
00080   return loop_score;
00081 }
00082 
00083 /* Public interface: create/destroy. */
00084 void pico_mbed_usb_destroy(struct pico_device *dev)
00085 {
00086   pico_device_destroy(dev);
00087 }
00088 
00089 struct pico_device *pico_mbed_usb_create(char *name, USBCDC_ECM *ecm)
00090 {
00091   std::uint8_t mac[PICO_SIZE_ETH] = {0x00, 0x01, 0xaa, 0x00, 0x02, 0xbb};
00092   struct pico_device_mbed_usb *mb = (struct pico_device_mbed_usb*) pico_zalloc(sizeof(struct pico_device_mbed_usb));
00093 
00094   if (!mb)
00095     return NULL;
00096 
00097   if(0 != pico_device_init((struct pico_device *)mb, name, mac)) {
00098     __pc.printf ("ETH> Loop init failed.\n");
00099     //pico_loop_destroy(mb);
00100     return NULL;
00101   }
00102   mb->ecm = ecm;
00103   mb->dev.send = pico_mbed_usb_send;
00104   mb->dev.poll = pico_mbed_usb_poll;
00105   mb->dev.destroy = pico_mbed_usb_destroy;
00106   mb->bytes_left_in_frame = 0;
00107 
00108   if(0 != ethernet_init()) {
00109     __pc.printf("ETH> Failed to initialize hardware.\r\n");
00110     pico_device_destroy((struct pico_device *)mb);
00111     return NULL;
00112   }
00113 
00114   __pc.printf("ETH> Device %s created.\r\n", mb->dev.name);
00115 
00116   return (struct pico_device *)mb;
00117 }
00118 
00119 void pico_mbed_usb_get_address(char *mac)
00120 {
00121   /* TODO */
00122 }
00123 
00124 }