From 990090a4cc9070837d31e66b58d40f0c3d038741 Mon Sep 17 00:00:00 2001 From: Yuval Adam Date: Sun, 16 Mar 2014 14:41:11 +0200 Subject: Add usblib and utils --- utils/locator.c | 342 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 342 insertions(+) create mode 100644 utils/locator.c (limited to 'utils/locator.c') diff --git a/utils/locator.c b/utils/locator.c new file mode 100644 index 0000000..fb240b2 --- /dev/null +++ b/utils/locator.c @@ -0,0 +1,342 @@ +//***************************************************************************** +// +// locator.c - A device locator server using UDP in lwIP. +// +// Copyright (c) 2009-2014 Texas Instruments Incorporated. All rights reserved. +// Software License Agreement +// +// Texas Instruments (TI) is supplying this software for use solely and +// exclusively on TI's microcontroller products. The software is owned by +// TI and/or its suppliers, and is protected under applicable copyright +// laws. You may not combine this software with "viral" open-source +// software in order to form a larger program. +// +// THIS SOFTWARE IS PROVIDED "AS IS" AND WITH ALL FAULTS. +// NO WARRANTIES, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT +// NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. TI SHALL NOT, UNDER ANY +// CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR CONSEQUENTIAL +// DAMAGES, FOR ANY REASON WHATSOEVER. +// +// This is part of revision 2.1.0.12573 of the Tiva Utility Library. +// +//***************************************************************************** + +#include +#include "utils/locator.h" +#include "utils/lwiplib.h" + +//***************************************************************************** +// +//! \addtogroup locator_api +//! @{ +// +//***************************************************************************** + +//***************************************************************************** +// +// These defines are used to describe the device locator protocol. +// +//***************************************************************************** +#define TAG_CMD 0xff +#define TAG_STATUS 0xfe +#define CMD_DISCOVER_TARGET 0x02 + +//***************************************************************************** +// +// An array that contains the device locator response data. The format of the +// data is as follows: +// +// Byte Description +// -------- ------------------------ +// 0 TAG_STATUS +// 1 packet length +// 2 CMD_DISCOVER_TARGET +// 3 board type +// 4 board ID +// 5..8 client IP address +// 9..14 MAC address +// 15..18 firmware version +// 19..82 application title +// 83 checksum +// +//***************************************************************************** +static uint8_t g_pui8LocatorData[84]; + +//***************************************************************************** +// +// This function is called by the lwIP TCP/IP stack when it receives a UDP +// packet from the discovery port. It produces the response packet, which is +// sent back to the querying client. +// +//***************************************************************************** +static void +LocatorReceive(void *arg, struct udp_pcb *pcb, struct pbuf *p, + struct ip_addr *addr, u16_t port) +{ + uint8_t *pui8Data; + uint32_t ui32Idx; + + // + // Validate the contents of the datagram. + // + pui8Data = p->payload; + if((p->len != 4) || (pui8Data[0] != TAG_CMD) || (pui8Data[1] != 4) || + (pui8Data[2] != CMD_DISCOVER_TARGET) || + (pui8Data[3] != ((0 - TAG_CMD - 4 - CMD_DISCOVER_TARGET) & 0xff))) + { + pbuf_free(p); + return; + } + + // + // The incoming pbuf is no longer needed, so free it. + // + pbuf_free(p); + + // + // Allocate a new pbuf for sending the response. + // + p = pbuf_alloc(PBUF_TRANSPORT, sizeof(g_pui8LocatorData), PBUF_RAM); + if(p == NULL) + { + return; + } + + // + // Calculate and fill in the checksum on the response packet. + // + for(ui32Idx = 0, g_pui8LocatorData[sizeof(g_pui8LocatorData) - 1] = 0; + ui32Idx < (sizeof(g_pui8LocatorData) - 1); ui32Idx++) + { + g_pui8LocatorData[sizeof(g_pui8LocatorData) - 1] -= + g_pui8LocatorData[ui32Idx]; + } + + // + // Copy the response packet data into the pbuf. + // + pui8Data = p->payload; + for(ui32Idx = 0; ui32Idx < sizeof(g_pui8LocatorData); ui32Idx++) + { + pui8Data[ui32Idx] = g_pui8LocatorData[ui32Idx]; + } + + // + // Send the response. + // + udp_sendto(pcb, p, addr, port); + + // + // Free the pbuf. + // + pbuf_free(p); +} + +//***************************************************************************** +// +//! Initializes the locator service. +//! +//! This function prepares the locator service to handle device discovery +//! requests. A UDP server is created and the locator response data is +//! initialized to all empty. +//! +//! \return None. +// +//***************************************************************************** +void +LocatorInit(void) +{ + uint32_t ui32Idx; + void *pcb; + + // + // Clear out the response data. + // + for(ui32Idx = 0; ui32Idx < 84; ui32Idx++) + { + g_pui8LocatorData[ui32Idx] = 0; + } + + // + // Fill in the header for the response data. + // + g_pui8LocatorData[0] = TAG_STATUS; + g_pui8LocatorData[1] = sizeof(g_pui8LocatorData); + g_pui8LocatorData[2] = CMD_DISCOVER_TARGET; + + // + // Fill in the MAC address for the response data. + // + g_pui8LocatorData[9] = 0; + g_pui8LocatorData[10] = 0; + g_pui8LocatorData[11] = 0; + g_pui8LocatorData[12] = 0; + g_pui8LocatorData[13] = 0; + g_pui8LocatorData[14] = 0; + + // + // Create a new UDP port for listening to device locator requests. + // + pcb = udp_new(); + udp_recv(pcb, LocatorReceive, NULL); + udp_bind(pcb, IP_ADDR_ANY, 23); +} + +//***************************************************************************** +// +//! Sets the board type in the locator response packet. +//! +//! \param ui32Type is the type of the board. +//! +//! This function sets the board type field in the locator response packet. +//! +//! \return None. +// +//***************************************************************************** +void +LocatorBoardTypeSet(uint32_t ui32Type) +{ + // + // Save the board type in the response data. + // + g_pui8LocatorData[3] = ui32Type & 0xff; +} + +//***************************************************************************** +// +//! Sets the board ID in the locator response packet. +//! +//! \param ui32ID is the ID of the board. +//! +//! This function sets the board ID field in the locator response packet. +//! +//! \return None. +// +//***************************************************************************** +void +LocatorBoardIDSet(uint32_t ui32ID) +{ + // + // Save the board ID in the response data. + // + g_pui8LocatorData[4] = ui32ID & 0xff; +} + +//***************************************************************************** +// +//! Sets the client IP address in the locator response packet. +//! +//! \param ui32IP is the IP address of the currently connected client. +//! +//! This function sets the IP address of the currently connected client in the +//! locator response packet. The IP should be set to 0.0.0.0 if there is no +//! client connected. It should never be set for devices that do not have a +//! strict one-to-one mapping of client to server (for example, a web server). +//! +//! \return None. +// +//***************************************************************************** +void +LocatorClientIPSet(uint32_t ui32IP) +{ + // + // Save the client IP address in the response data. + // + g_pui8LocatorData[5] = ui32IP & 0xff; + g_pui8LocatorData[6] = (ui32IP >> 8) & 0xff; + g_pui8LocatorData[7] = (ui32IP >> 16) & 0xff; + g_pui8LocatorData[8] = (ui32IP >> 24) & 0xff; +} + +//***************************************************************************** +// +//! Sets the MAC address in the locator response packet. +//! +//! \param pui8MACArray is the MAC address of the network interface. +//! +//! This function sets the MAC address of the network interface in the locator +//! response packet. +//! +//! \return None. +// +//***************************************************************************** +void +LocatorMACAddrSet(uint8_t *pui8MACArray) +{ + // + // Save the MAC address. + // + g_pui8LocatorData[9] = pui8MACArray[0]; + g_pui8LocatorData[10] = pui8MACArray[1]; + g_pui8LocatorData[11] = pui8MACArray[2]; + g_pui8LocatorData[12] = pui8MACArray[3]; + g_pui8LocatorData[13] = pui8MACArray[4]; + g_pui8LocatorData[14] = pui8MACArray[5]; +} + +//***************************************************************************** +// +//! Sets the firmware version in the locator response packet. +//! +//! \param ui32Version is the version number of the device firmware. +//! +//! This function sets the version number of the device firmware in the locator +//! response packet. +//! +//! \return None. +// +//***************************************************************************** +void +LocatorVersionSet(uint32_t ui32Version) +{ + // + // Save the firmware version number in the response data. + // + g_pui8LocatorData[15] = ui32Version & 0xff; + g_pui8LocatorData[16] = (ui32Version >> 8) & 0xff; + g_pui8LocatorData[17] = (ui32Version >> 16) & 0xff; + g_pui8LocatorData[18] = (ui32Version >> 24) & 0xff; +} + +//***************************************************************************** +// +//! Sets the application title in the locator response packet. +//! +//! \param pcAppTitle is a pointer to the application title string. +//! +//! This function sets the application title in the locator response packet. +//! The string is truncated at 64 characters if it is longer (without a +//! terminating 0), and is zero-filled to 64 characters if it is shorter. +//! +//! \return None. +// +//***************************************************************************** +void +LocatorAppTitleSet(const char *pcAppTitle) +{ + uint32_t ui32Count; + + // + // Copy the application title string into the response data. + // + for(ui32Count = 0; (ui32Count < 64) && *pcAppTitle; ui32Count++) + { + g_pui8LocatorData[ui32Count + 19] = *pcAppTitle++; + } + + // + // Zero-fill the remainder of the space in the response data (if any). + // + for(; ui32Count < 64; ui32Count++) + { + g_pui8LocatorData[ui32Count + 19] = 0; + } +} + +//***************************************************************************** +// +// Close the Doxygen group. +//! @} +// +//***************************************************************************** -- cgit v1.3.1