mbed client lightswitch demo

Dependencies:   mbed Socket lwip-eth lwip-sys lwip

Fork of mbed-client-classic-example-lwip by Austin Blackstone

Committer:
mbedAustin
Date:
Thu Jun 09 17:08:36 2016 +0000
Revision:
11:cada08fc8a70
Commit for public Consumption

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mbedAustin 11:cada08fc8a70 1 /*
mbedAustin 11:cada08fc8a70 2 * Copyright (c) 2014-2015 ARM Limited. All rights reserved.
mbedAustin 11:cada08fc8a70 3 * SPDX-License-Identifier: Apache-2.0
mbedAustin 11:cada08fc8a70 4 * Licensed under the Apache License, Version 2.0 (the License); you may
mbedAustin 11:cada08fc8a70 5 * not use this file except in compliance with the License.
mbedAustin 11:cada08fc8a70 6 * You may obtain a copy of the License at
mbedAustin 11:cada08fc8a70 7 *
mbedAustin 11:cada08fc8a70 8 * http://www.apache.org/licenses/LICENSE-2.0
mbedAustin 11:cada08fc8a70 9 *
mbedAustin 11:cada08fc8a70 10 * Unless required by applicable law or agreed to in writing, software
mbedAustin 11:cada08fc8a70 11 * distributed under the License is distributed on an AS IS BASIS, WITHOUT
mbedAustin 11:cada08fc8a70 12 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
mbedAustin 11:cada08fc8a70 13 * See the License for the specific language governing permissions and
mbedAustin 11:cada08fc8a70 14 * limitations under the License.
mbedAustin 11:cada08fc8a70 15 */
mbedAustin 11:cada08fc8a70 16 #include "stdint.h"
mbedAustin 11:cada08fc8a70 17 #include "ip_fsc.h"
mbedAustin 11:cada08fc8a70 18
mbedAustin 11:cada08fc8a70 19 /** \brief Compute IP checksum for arbitary data
mbedAustin 11:cada08fc8a70 20 *
mbedAustin 11:cada08fc8a70 21 * Compute an IP checksum, given a arbitrary gather list.
mbedAustin 11:cada08fc8a70 22 *
mbedAustin 11:cada08fc8a70 23 * See ipv6_fcf for discussion of use.
mbedAustin 11:cada08fc8a70 24 *
mbedAustin 11:cada08fc8a70 25 * This will work for any arbitrary gather list - it can handle odd
mbedAustin 11:cada08fc8a70 26 * alignments. The one limitation is that the 32-bit accumulator limits
mbedAustin 11:cada08fc8a70 27 * it to basically 64K of total data.
mbedAustin 11:cada08fc8a70 28 */
mbedAustin 11:cada08fc8a70 29 uint16_t ip_fcf_v(uint_fast8_t count, const ns_iovec_t vec[static count])
mbedAustin 11:cada08fc8a70 30 {
mbedAustin 11:cada08fc8a70 31 uint_fast32_t acc32 = 0;
mbedAustin 11:cada08fc8a70 32 bool odd = false;
mbedAustin 11:cada08fc8a70 33 while (count) {
mbedAustin 11:cada08fc8a70 34 const uint8_t *data_ptr = vec->iov_base;
mbedAustin 11:cada08fc8a70 35 uint_fast16_t data_length = vec->iov_len;
mbedAustin 11:cada08fc8a70 36 if (odd && data_length > 0) {
mbedAustin 11:cada08fc8a70 37 acc32 += *data_ptr++;
mbedAustin 11:cada08fc8a70 38 data_length--;
mbedAustin 11:cada08fc8a70 39 odd = false;
mbedAustin 11:cada08fc8a70 40 }
mbedAustin 11:cada08fc8a70 41 while (data_length >= 2) {
mbedAustin 11:cada08fc8a70 42 acc32 += (uint_fast16_t) data_ptr[0] << 8 | data_ptr[1];
mbedAustin 11:cada08fc8a70 43 data_ptr += 2;
mbedAustin 11:cada08fc8a70 44 data_length -= 2;
mbedAustin 11:cada08fc8a70 45 }
mbedAustin 11:cada08fc8a70 46 if (data_length) {
mbedAustin 11:cada08fc8a70 47 acc32 += (uint_fast16_t) data_ptr[0] << 8;
mbedAustin 11:cada08fc8a70 48 odd = true;
mbedAustin 11:cada08fc8a70 49 }
mbedAustin 11:cada08fc8a70 50 vec++;
mbedAustin 11:cada08fc8a70 51 count--;
mbedAustin 11:cada08fc8a70 52 }
mbedAustin 11:cada08fc8a70 53
mbedAustin 11:cada08fc8a70 54 // Fold down up to 0xffff carries in the 32-bit accumulator
mbedAustin 11:cada08fc8a70 55 acc32 = (acc32 >> 16) + (acc32 & 0xffff);
mbedAustin 11:cada08fc8a70 56
mbedAustin 11:cada08fc8a70 57 // Could be one more carry from the previous addition (result <= 0x1fffe)
mbedAustin 11:cada08fc8a70 58 uint16_t sum16 = (uint16_t)((acc32 >> 16) + (acc32 & 0xffff));
mbedAustin 11:cada08fc8a70 59 return ~sum16;
mbedAustin 11:cada08fc8a70 60 }
mbedAustin 11:cada08fc8a70 61
mbedAustin 11:cada08fc8a70 62 /** \brief Compute IPv6 checksum
mbedAustin 11:cada08fc8a70 63 *
mbedAustin 11:cada08fc8a70 64 * Compute an IPv6 checksum, given fields of an IPv6 pseudoheader and payload.
mbedAustin 11:cada08fc8a70 65 *
mbedAustin 11:cada08fc8a70 66 * This returns the 1's-complement of the checksum, as required when
mbedAustin 11:cada08fc8a70 67 * generating the checksum for transmission. The result can be 0x0000;
mbedAustin 11:cada08fc8a70 68 * for UDP (only) this must be transformed to 0xFFFF to distinguish from
mbedAustin 11:cada08fc8a70 69 * a packet with no checksum.
mbedAustin 11:cada08fc8a70 70 *
mbedAustin 11:cada08fc8a70 71 * To check a packet, this function will return 0 when run on a
mbedAustin 11:cada08fc8a70 72 * packet with a valid checksum. Checksums should be checked like this rather
mbedAustin 11:cada08fc8a70 73 * than setting the checksum field to zero and comparing generated checksum with
mbedAustin 11:cada08fc8a70 74 * the original value - this would fail in the case the received packet had
mbedAustin 11:cada08fc8a70 75 * checksum 0xFFFF.
mbedAustin 11:cada08fc8a70 76 */
mbedAustin 11:cada08fc8a70 77 uint16_t ipv6_fcf(const uint8_t src_address[static 16], const uint8_t dest_address[static 16],
mbedAustin 11:cada08fc8a70 78 uint16_t data_length, const uint8_t data_ptr[static data_length], uint8_t next_protocol)
mbedAustin 11:cada08fc8a70 79 {
mbedAustin 11:cada08fc8a70 80 // Use gather vector to lay out IPv6 pseudo-header (RFC 2460) and data
mbedAustin 11:cada08fc8a70 81 uint8_t hdr_data[] = { data_length >> 8, data_length, 0, next_protocol };
mbedAustin 11:cada08fc8a70 82 ns_iovec_t vec[4] = {
mbedAustin 11:cada08fc8a70 83 { (void *) src_address, 16 },
mbedAustin 11:cada08fc8a70 84 { (void *) dest_address, 16 },
mbedAustin 11:cada08fc8a70 85 { hdr_data, 4 },
mbedAustin 11:cada08fc8a70 86 { (void *) data_ptr, data_length }
mbedAustin 11:cada08fc8a70 87 };
mbedAustin 11:cada08fc8a70 88
mbedAustin 11:cada08fc8a70 89 return ip_fcf_v(4, vec);
mbedAustin 11:cada08fc8a70 90 }