EMAC driver for the ENC28J60 Ethernet controller. This is a simplified fork of https://github.com/tobiasjaster/ENC28J60-EMAC-Driver published by Tobias Jaster.

Dependents:   MQTT_Hello MQTT_HelloENC28J60

EMAC driver for the ENC28J60 Ethernet controller

https://os.mbed.com/media/uploads/hudakz/enc28j60_module01.jpg

This is a fork (the INT and RST pins are not used) of the ENC28J60-EMAC driver published by Tobias Jaster at

https://github.com/tobiasjaster/ENC28J60-EMAC-Driver

Usage:

  • Connect the ENC28J60 module to the Mbed board as follows:

https://os.mbed.com/media/uploads/hudakz/enc28j60-emac.png

  • Import (add) this ENC28J60-EMAC library to your program.
  • Add a "mbed_app.json" file with the following content to the root directory of your program:

    {
        "target_overrides": {
            "*": {
                "platform.callback-nontrivial": true,
                "enc28j60-emac.mosi":  "D11",
                "enc28j60-emac.miso":  "D12",
                "enc28j60-emac.sck" :  "D13",
                "enc28j60-emac.cs"  :  "D10"
            }
        }
    }
  • Replace "D11", ..., "D10" with the actual pin names you selected on the Mbed board to be used for the SPI communication.
  • To set the MAC address define an array with the desired address bytes and call the "set_hwaddr(mac)" function before calling the network interface "connect" function.

For example:

    const uint8_t       MAC[6] = { 0, 1, 2, 3, 4, 5 };
    EthernetInterface   net;
 
    int main()
    {
        net.get_emac().set_hwaddr(MAC);             // set MAC address
        if (net.connect() != 0) {
            printf("Error: Unable to connect to the network.\n");
            return -1;
        }
     ...
Committer:
hudakz
Date:
Mon Mar 29 08:37:01 2021 +0000
Revision:
3:aa88808326b9
Parent:
2:19d290369c66
Mbed OS Ethernet MAC (EMAC) driver for the ENC28J60 Ethernet controller. This a simplified fork of https://github.com/tobiasjaster/ENC28J60-EMAC-Driver published by Tobias Jaster.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
hudakz 0:b599e748252c 1 /*
hudakz 0:b599e748252c 2 * Copyright (c) 2019 Tobias Jaster
hudakz 0:b599e748252c 3 *
hudakz 0:b599e748252c 4 * Modified by Zoltan Hudak
hudakz 0:b599e748252c 5 *
hudakz 0:b599e748252c 6 * Licensed under the Apache License, Version 2.0 (the "License");
hudakz 0:b599e748252c 7 * you may not use this file except in compliance with the License.
hudakz 0:b599e748252c 8 * You may obtain a copy of the License at
hudakz 0:b599e748252c 9 *
hudakz 0:b599e748252c 10 * http://www.apache.org/licenses/LICENSE-2.0
hudakz 0:b599e748252c 11 *
hudakz 0:b599e748252c 12 * Unless required by applicable law or agreed to in writing, software
hudakz 0:b599e748252c 13 * distributed under the License is distributed on an "AS IS" BASIS,
hudakz 0:b599e748252c 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
hudakz 0:b599e748252c 15 * See the License for the specific language governing permissions and
hudakz 0:b599e748252c 16 * limitations under the License.
hudakz 0:b599e748252c 17 */
hudakz 2:19d290369c66 18 #ifndef ENC28J60_EMAC_H_
hudakz 2:19d290369c66 19 #define ENC28J60_EMAC_H_
hudakz 0:b599e748252c 20
hudakz 2:19d290369c66 21 #include <ctype.h>
hudakz 2:19d290369c66 22 #include <stdio.h>
hudakz 2:19d290369c66 23 #include <string.h>
hudakz 2:19d290369c66 24 #include <stdlib.h>
hudakz 2:19d290369c66 25 #include <stdint.h>
hudakz 0:b599e748252c 26 #include "mbed.h"
hudakz 2:19d290369c66 27 #include "EMAC.h"
hudakz 2:19d290369c66 28 #include "rtos.h"
hudakz 0:b599e748252c 29 #include "enc28j60_reg.h"
hudakz 2:19d290369c66 30 #include "enc28j60.h"
hudakz 0:b599e748252c 31 #include "enc28j60_emac_config.h"
hudakz 0:b599e748252c 32
hudakz 2:19d290369c66 33 class ENC28J60_EMAC :
hudakz 2:19d290369c66 34 public EMAC
hudakz 0:b599e748252c 35 {
hudakz 0:b599e748252c 36 public:
hudakz 2:19d290369c66 37 ENC28J60_EMAC();
hudakz 2:19d290369c66 38
hudakz 2:19d290369c66 39 /** Return the ENC28J60 EMAC
hudakz 2:19d290369c66 40 *
hudakz 2:19d290369c66 41 * Returns the default on-board EMAC - this will be target-specific, and
hudakz 2:19d290369c66 42 * may not be available on all targets.
hudakz 2:19d290369c66 43 */
hudakz 2:19d290369c66 44 static ENC28J60_EMAC& get_instance(void);
hudakz 0:b599e748252c 45
hudakz 2:19d290369c66 46 /**
hudakz 2:19d290369c66 47 * Return maximum transmission unit
hudakz 2:19d290369c66 48 *
hudakz 2:19d290369c66 49 * @return MTU in bytes
hudakz 2:19d290369c66 50 */
hudakz 2:19d290369c66 51 virtual uint32_t get_mtu_size(void) const;
hudakz 2:19d290369c66 52
hudakz 2:19d290369c66 53 /**
hudakz 2:19d290369c66 54 * Gets memory buffer alignment preference
hudakz 2:19d290369c66 55 *
hudakz 2:19d290369c66 56 * Gets preferred memory buffer alignment of the Emac device. IP stack may
hudakz 2:19d290369c66 57 * or may not align link out memory buffer chains using the alignment.
hudakz 2:19d290369c66 58 *
hudakz 2:19d290369c66 59 * @return Memory alignment requirement in bytes
hudakz 2:19d290369c66 60 */
hudakz 2:19d290369c66 61 virtual uint32_t get_align_preference(void) const;
hudakz 0:b599e748252c 62
hudakz 0:b599e748252c 63 /**
hudakz 2:19d290369c66 64 * Return interface name
hudakz 0:b599e748252c 65 *
hudakz 2:19d290369c66 66 * @param name Pointer to where the name should be written
hudakz 2:19d290369c66 67 * @param size Maximum number of character to copy
hudakz 0:b599e748252c 68 */
hudakz 2:19d290369c66 69 virtual void get_ifname(char* name, uint8_t size) const;
hudakz 0:b599e748252c 70
hudakz 0:b599e748252c 71 /**
hudakz 2:19d290369c66 72 * Returns size of the underlying interface HW address size.
hudakz 0:b599e748252c 73 *
hudakz 2:19d290369c66 74 * @return HW address size in bytes
hudakz 0:b599e748252c 75 */
hudakz 2:19d290369c66 76 virtual uint8_t get_hwaddr_size(void) const;
hudakz 0:b599e748252c 77
hudakz 0:b599e748252c 78 /**
hudakz 2:19d290369c66 79 * Return interface-supplied HW address
hudakz 2:19d290369c66 80 *
hudakz 2:19d290369c66 81 * Copies HW address to provided memory, @param addr has to be of correct
hudakz 2:19d290369c66 82 * size see @a get_hwaddr_size
hudakz 0:b599e748252c 83 *
hudakz 2:19d290369c66 84 * HW address need not be provided if this interface does not have its own
hudakz 2:19d290369c66 85 * HW address configuration; stack will choose address from central system
hudakz 2:19d290369c66 86 * configuration if the function returns false and does not write to addr.
hudakz 2:19d290369c66 87 *
hudakz 2:19d290369c66 88 * @param addr HW address for underlying interface
hudakz 2:19d290369c66 89 * @return true if HW address is available
hudakz 0:b599e748252c 90 */
hudakz 2:19d290369c66 91 virtual bool get_hwaddr(uint8_t* addr) const;
hudakz 0:b599e748252c 92
hudakz 0:b599e748252c 93 /**
hudakz 2:19d290369c66 94 * Set HW address for interface
hudakz 2:19d290369c66 95 *
hudakz 2:19d290369c66 96 * Provided address has to be of correct size, see @a get_hwaddr_size
hudakz 0:b599e748252c 97 *
hudakz 2:19d290369c66 98 * Called to set the MAC address to actually use - if @a get_hwaddr is
hudakz 2:19d290369c66 99 * provided the stack would normally use that, but it could be overridden,
hudakz 2:19d290369c66 100 * eg for test purposes.
hudakz 2:19d290369c66 101 *
hudakz 2:19d290369c66 102 * @param addr Address to be set
hudakz 1:bce04bfc41fe 103 */
hudakz 2:19d290369c66 104 virtual void set_hwaddr(const uint8_t* addr);
hudakz 0:b599e748252c 105
hudakz 0:b599e748252c 106 /**
hudakz 2:19d290369c66 107 * Sends the packet over the link
hudakz 2:19d290369c66 108 *
hudakz 2:19d290369c66 109 * That can not be called from an interrupt context.
hudakz 0:b599e748252c 110 *
hudakz 2:19d290369c66 111 * @param buf Packet to be send
hudakz 2:19d290369c66 112 * @return True if the packet was send successfully, False otherwise
hudakz 0:b599e748252c 113 */
hudakz 2:19d290369c66 114 virtual bool link_out(emac_mem_buf_t* buf);
hudakz 0:b599e748252c 115
hudakz 0:b599e748252c 116 /**
hudakz 2:19d290369c66 117 * Initializes the HW
hudakz 0:b599e748252c 118 *
hudakz 2:19d290369c66 119 * @return True on success, False in case of an error.
hudakz 0:b599e748252c 120 */
hudakz 2:19d290369c66 121 virtual bool power_up(void);
hudakz 0:b599e748252c 122
hudakz 0:b599e748252c 123 /**
hudakz 2:19d290369c66 124 * Deinitializes the HW
hudakz 0:b599e748252c 125 *
hudakz 0:b599e748252c 126 */
hudakz 2:19d290369c66 127 virtual void power_down(void);
hudakz 2:19d290369c66 128
hudakz 2:19d290369c66 129 /**
hudakz 2:19d290369c66 130 * Sets a callback that needs to be called for packets received for that
hudakz 2:19d290369c66 131 * interface
hudakz 2:19d290369c66 132 *
hudakz 2:19d290369c66 133 * @param input_cb Function to be register as a callback
hudakz 2:19d290369c66 134 */
hudakz 2:19d290369c66 135 virtual void set_link_input_cb(emac_link_input_cb_t input_cb);
hudakz 0:b599e748252c 136
hudakz 0:b599e748252c 137 /**
hudakz 2:19d290369c66 138 * Sets a callback that needs to be called on link status changes for given
hudakz 2:19d290369c66 139 * interface
hudakz 0:b599e748252c 140 *
hudakz 2:19d290369c66 141 * @param state_cb Function to be register as a callback
hudakz 0:b599e748252c 142 */
hudakz 2:19d290369c66 143 virtual void set_link_state_cb(emac_link_state_change_cb_t state_cb);
hudakz 0:b599e748252c 144
hudakz 2:19d290369c66 145 /** Add device to a multicast group
hudakz 1:bce04bfc41fe 146 *
hudakz 2:19d290369c66 147 * @param address A multicast group hardware address
hudakz 0:b599e748252c 148 */
hudakz 2:19d290369c66 149 virtual void add_multicast_group(const uint8_t* address);
hudakz 0:b599e748252c 150
hudakz 2:19d290369c66 151 /** Remove device from a multicast group
hudakz 0:b599e748252c 152 *
hudakz 2:19d290369c66 153 * @param address A multicast group hardware address
hudakz 2:19d290369c66 154 */
hudakz 2:19d290369c66 155 virtual void remove_multicast_group(const uint8_t* address);
hudakz 2:19d290369c66 156
hudakz 2:19d290369c66 157 /** Request reception of all multicast packets
hudakz 1:bce04bfc41fe 158 *
hudakz 2:19d290369c66 159 * @param all True to receive all multicasts
hudakz 2:19d290369c66 160 * False to receive only multicasts addressed to specified groups
hudakz 0:b599e748252c 161 */
hudakz 2:19d290369c66 162 virtual void set_all_multicast(bool all);
hudakz 2:19d290369c66 163
hudakz 2:19d290369c66 164 /** Sets memory manager that is used to handle memory buffers
hudakz 2:19d290369c66 165 *
hudakz 2:19d290369c66 166 * @param mem_mngr Pointer to memory manager
hudakz 2:19d290369c66 167 */
hudakz 2:19d290369c66 168 virtual void set_memory_manager(EMACMemoryManager& mem_mngr);
hudakz 0:b599e748252c 169 private:
hudakz 2:19d290369c66 170 void link_status_task();
hudakz 2:19d290369c66 171 void receive_task();
hudakz 2:19d290369c66 172 bool low_level_init_successful();
hudakz 2:19d290369c66 173 emac_mem_buf_t* low_level_input();
hudakz 2:19d290369c66 174
hudakz 2:19d290369c66 175 ENC28J60* _enc28j60;
hudakz 2:19d290369c66 176 bool _prev_link_status_up;
hudakz 2:19d290369c66 177 int _link_status_task_handle;
hudakz 2:19d290369c66 178 int _receive_task_handle;
hudakz 2:19d290369c66 179 EMACMemoryManager* _memory_manager;
hudakz 2:19d290369c66 180 Mutex _ethLockMutex;
hudakz 2:19d290369c66 181 uint8_t _hwaddr[ENC28J60_HWADDR_SIZE];
hudakz 2:19d290369c66 182
hudakz 2:19d290369c66 183 emac_link_input_cb_t _emac_link_input_cb;
hudakz 2:19d290369c66 184 emac_link_state_change_cb_t _emac_link_state_cb;
hudakz 0:b599e748252c 185 };
hudakz 2:19d290369c66 186 #endif /* ENC28J60_EMAC_H_ */