diff options
author | nbd <nbd@3c298f89-4303-0410-b956-a3cf2f4a3e73> | 2012-10-10 12:32:29 +0000 |
---|---|---|
committer | nbd <nbd@3c298f89-4303-0410-b956-a3cf2f4a3e73> | 2012-10-10 12:32:29 +0000 |
commit | 9c8997d54dc9df184bfcedeabf0b3c85cf5e6753 (patch) | |
tree | 46b83031a0da1b4458317413c00d13c252c72afa /package/network/services/ead | |
parent | eecf5b17520f6b3b6ffb45ac7dca298d93b27501 (diff) |
packages: sort network related packages into package/network/
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@33688 3c298f89-4303-0410-b956-a3cf2f4a3e73
Diffstat (limited to 'package/network/services/ead')
69 files changed, 17693 insertions, 0 deletions
diff --git a/package/network/services/ead/Makefile b/package/network/services/ead/Makefile new file mode 100644 index 0000000000..5633a315a1 --- /dev/null +++ b/package/network/services/ead/Makefile @@ -0,0 +1,57 @@ +# +# Copyright (C) 2006-2008 OpenWrt.org +# +# This is free software, licensed under the GNU General Public License v2. +# See /LICENSE for more information. +# + +include $(TOPDIR)/rules.mk + +PKG_NAME:=ead +PKG_RELEASE:=1 + +PKG_BUILD_DEPENDS:=libpcap +PKG_BUILD_DIR:=$(BUILD_DIR)/ead + +PKG_MAINTAINER:=Felix Fietkau <nbd@openwrt.org> + +include $(INCLUDE_DIR)/package.mk +include $(INCLUDE_DIR)/kernel.mk + +define Package/ead + SECTION:=net + CATEGORY:=Base system + TITLE:=Emergency Access Daemon + URL:=http://bridge.sourceforge.net/ +endef + +define Package/ead/description + Provides remote access to your device even if IP and firewall + configuration settings are defunct +endef + +CONFIGURE_PATH = tinysrp + +TARGET_CFLAGS += \ + -I$(LINUX_DIR)/include \ + -I$(PKG_BUILD_DIR) \ + -I$(PKG_BUILD_DIR)/tinysrp \ + $(TARGET_CPPFLAGS) + +MAKE_FLAGS += \ + CONFIGURE_ARGS="$(CONFIGURE_ARGS)" \ + LIBS_EADCLIENT="$(PKG_BUILD_DIR)/tinysrp/libtinysrp.a" \ + LIBS_EAD="$(PKG_BUILD_DIR)/tinysrp/libtinysrp.a $(STAGING_DIR)/usr/lib/libpcap.a" \ + CFLAGS="$(TARGET_CFLAGS)" + +define Build/Prepare + mkdir -p $(PKG_BUILD_DIR) + $(CP) ./src/* $(PKG_BUILD_DIR)/ +endef + +define Package/ead/install + $(INSTALL_DIR) $(1)/sbin + $(INSTALL_BIN) $(PKG_BUILD_DIR)/ead $(1)/sbin/ +endef + +$(eval $(call BuildPackage,ead)) diff --git a/package/network/services/ead/src/Makefile b/package/network/services/ead/src/Makefile new file mode 100644 index 0000000000..faef3b7997 --- /dev/null +++ b/package/network/services/ead/src/Makefile @@ -0,0 +1,33 @@ +CC = gcc +CPPFLAGS = -I. -Itinysrp +CFLAGS = -Os -Wall +LDFLAGS = +LIBS_EADCLIENT = tinysrp/libtinysrp.a +LIBS_EAD = tinysrp/libtinysrp.a -lpcap +CONFIGURE_ARGS = + +all: ead ead-client + +obj = ead-crypt.o + +tinysrp/Makefile: + cd tinysrp; ./configure $(CONFIGURE_ARGS) + +tinysrp/libtinysrp.a: tinysrp/Makefile + -$(MAKE) -C tinysrp CFLAGS="$(CFLAGS)" + +%.o: %.c $(wildcard *.h) tinysrp/libtinysrp.a + $(CC) $(CPPFLAGS) $(CFLAGS) -c $< -o $@ + +ead.o: filter.c +ead-crypt.o: aes.c sha1.c + +ead: ead.o $(obj) tinysrp/libtinysrp.a + $(CC) -o $@ $< $(obj) $(LDFLAGS) $(LIBS_EAD) + +ead-client: ead-client.o $(obj) + $(CC) -o $@ $< $(obj) $(LDFLAGS) $(LIBS_EADCLIENT) + +clean: + rm -f *.o ead ead-client + if [ -f tinysrp/Makefile ]; then $(MAKE) -C tinysrp distclean; fi diff --git a/package/network/services/ead/src/aes.c b/package/network/services/ead/src/aes.c new file mode 100644 index 0000000000..6f9db345fb --- /dev/null +++ b/package/network/services/ead/src/aes.c @@ -0,0 +1,1061 @@ +/* + * AES (Rijndael) cipher + * + * Modifications to public domain implementation: + * - support only 128-bit keys + * - cleanup + * - use C pre-processor to make it easier to change S table access + * - added option (AES_SMALL_TABLES) for reducing code size by about 8 kB at + * cost of reduced throughput (quite small difference on Pentium 4, + * 10-25% when using -O1 or -O2 optimization) + * + * Copyright (c) 2003-2005, Jouni Malinen <j@w1.fi> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * Alternatively, this software may be distributed under the terms of BSD + * license. + * + * See README and COPYING for more details. + */ + +/* + * rijndael-alg-fst.c + * + * @version 3.0 (December 2000) + * + * Optimised ANSI C code for the Rijndael cipher (now AES) + * + * @author Vincent Rijmen <vincent.rijmen@esat.kuleuven.ac.be> + * @author Antoon Bosselaers <antoon.bosselaers@esat.kuleuven.ac.be> + * @author Paulo Barreto <paulo.barreto@terra.com.br> + * + * This code is hereby placed in the public domain. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ''AS IS'' AND ANY EXPRESS + * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR + * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, + * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/* #define FULL_UNROLL */ +#define AES_SMALL_TABLES + +typedef uint8_t u8; +typedef uint16_t u16; +typedef uint32_t u32; + +/* +Te0[x] = S [x].[02, 01, 01, 03]; +Te1[x] = S [x].[03, 02, 01, 01]; +Te2[x] = S [x].[01, 03, 02, 01]; +Te3[x] = S [x].[01, 01, 03, 02]; +Te4[x] = S [x].[01, 01, 01, 01]; + +Td0[x] = Si[x].[0e, 09, 0d, 0b]; +Td1[x] = Si[x].[0b, 0e, 09, 0d]; +Td2[x] = Si[x].[0d, 0b, 0e, 09]; +Td3[x] = Si[x].[09, 0d, 0b, 0e]; +Td4[x] = Si[x].[01, 01, 01, 01]; +*/ + +static const u32 Te0[256] = { + 0xc66363a5U, 0xf87c7c84U, 0xee777799U, 0xf67b7b8dU, + 0xfff2f20dU, 0xd66b6bbdU, 0xde6f6fb1U, 0x91c5c554U, + 0x60303050U, 0x02010103U, 0xce6767a9U, 0x562b2b7dU, + 0xe7fefe19U, 0xb5d7d762U, 0x4dababe6U, 0xec76769aU, + 0x8fcaca45U, 0x1f82829dU, 0x89c9c940U, 0xfa7d7d87U, + 0xeffafa15U, 0xb25959ebU, 0x8e4747c9U, 0xfbf0f00bU, + 0x41adadecU, 0xb3d4d467U, 0x5fa2a2fdU, 0x45afafeaU, + 0x239c9cbfU, 0x53a4a4f7U, 0xe4727296U, 0x9bc0c05bU, + 0x75b7b7c2U, 0xe1fdfd1cU, 0x3d9393aeU, 0x4c26266aU, + 0x6c36365aU, 0x7e3f3f41U, 0xf5f7f702U, 0x83cccc4fU, + 0x6834345cU, 0x51a5a5f4U, 0xd1e5e534U, 0xf9f1f108U, + 0xe2717193U, 0xabd8d873U, 0x62313153U, 0x2a15153fU, + 0x0804040cU, 0x95c7c752U, 0x46232365U, 0x9dc3c35eU, + 0x30181828U, 0x379696a1U, 0x0a05050fU, 0x2f9a9ab5U, + 0x0e070709U, 0x24121236U, 0x1b80809bU, 0xdfe2e23dU, + 0xcdebeb26U, 0x4e272769U, 0x7fb2b2cdU, 0xea75759fU, + 0x1209091bU, 0x1d83839eU, 0x582c2c74U, 0x341a1a2eU, + 0x361b1b2dU, 0xdc6e6eb2U, 0xb45a5aeeU, 0x5ba0a0fbU, + 0xa45252f6U, 0x763b3b4dU, 0xb7d6d661U, 0x7db3b3ceU, + 0x5229297bU, 0xdde3e33eU, 0x5e2f2f71U, 0x13848497U, + 0xa65353f5U, 0xb9d1d168U, 0x00000000U, 0xc1eded2cU, + 0x40202060U, 0xe3fcfc1fU, 0x79b1b1c8U, 0xb65b5bedU, + 0xd46a6abeU, 0x8dcbcb46U, 0x67bebed9U, 0x7239394bU, + 0x944a4adeU, 0x984c4cd4U, 0xb05858e8U, 0x85cfcf4aU, + 0xbbd0d06bU, 0xc5efef2aU, 0x4faaaae5U, 0xedfbfb16U, + 0x864343c5U, 0x9a4d4dd7U, 0x66333355U, 0x11858594U, + 0x8a4545cfU, 0xe9f9f910U, 0x04020206U, 0xfe7f7f81U, + 0xa05050f0U, 0x783c3c44U, 0x259f9fbaU, 0x4ba8a8e3U, + 0xa25151f3U, 0x5da3a3feU, 0x804040c0U, 0x058f8f8aU, + 0x3f9292adU, 0x219d9dbcU, 0x70383848U, 0xf1f5f504U, + 0x63bcbcdfU, 0x77b6b6c1U, 0xafdada75U, 0x42212163U, + 0x20101030U, 0xe5ffff1aU, 0xfdf3f30eU, 0xbfd2d26dU, + 0x81cdcd4cU, 0x180c0c14U, 0x26131335U, 0xc3ecec2fU, + 0xbe5f5fe1U, 0x359797a2U, 0x884444ccU, 0x2e171739U, + 0x93c4c457U, 0x55a7a7f2U, 0xfc7e7e82U, 0x7a3d3d47U, + 0xc86464acU, 0xba5d5de7U, 0x3219192bU, 0xe6737395U, + 0xc06060a0U, 0x19818198U, 0x9e4f4fd1U, 0xa3dcdc7fU, + 0x44222266U, 0x542a2a7eU, 0x3b9090abU, 0x0b888883U, + 0x8c4646caU, 0xc7eeee29U, 0x6bb8b8d3U, 0x2814143cU, + 0xa7dede79U, 0xbc5e5ee2U, 0x160b0b1dU, 0xaddbdb76U, + 0xdbe0e03bU, 0x64323256U, 0x743a3a4eU, 0x140a0a1eU, + 0x924949dbU, 0x0c06060aU, 0x4824246cU, 0xb85c5ce4U, + 0x9fc2c25dU, 0xbdd3d36eU, 0x43acacefU, 0xc46262a6U, + 0x399191a8U, 0x319595a4U, 0xd3e4e437U, 0xf279798bU, + 0xd5e7e732U, 0x8bc8c843U, 0x6e373759U, 0xda6d6db7U, + 0x018d8d8cU, 0xb1d5d564U, 0x9c4e4ed2U, 0x49a9a9e0U, + 0xd86c6cb4U, 0xac5656faU, 0xf3f4f407U, 0xcfeaea25U, + 0xca6565afU, 0xf47a7a8eU, 0x47aeaee9U, 0x10080818U, + 0x6fbabad5U, 0xf0787888U, 0x4a25256fU, 0x5c2e2e72U, + 0x381c1c24U, 0x57a6a6f1U, 0x73b4b4c7U, 0x97c6c651U, + 0xcbe8e823U, 0xa1dddd7cU, 0xe874749cU, 0x3e1f1f21U, + 0x964b4bddU, 0x61bdbddcU, 0x0d8b8b86U, 0x0f8a8a85U, + 0xe0707090U, 0x7c3e3e42U, 0x71b5b5c4U, 0xcc6666aaU, + 0x904848d8U, 0x06030305U, 0xf7f6f601U, 0x1c0e0e12U, + 0xc26161a3U, 0x6a35355fU, 0xae5757f9U, 0x69b9b9d0U, + 0x17868691U, 0x99c1c158U, 0x3a1d1d27U, 0x279e9eb9U, + 0xd9e1e138U, 0xebf8f813U, 0x2b9898b3U, 0x22111133U, + 0xd26969bbU, 0xa9d9d970U, 0x078e8e89U, 0x339494a7U, + 0x2d9b9bb6U, 0x3c1e1e22U, 0x15878792U, 0xc9e9e920U, + 0x87cece49U, 0xaa5555ffU, 0x50282878U, 0xa5dfdf7aU, + 0x038c8c8fU, 0x59a1a1f8U, 0x09898980U, 0x1a0d0d17U, + 0x65bfbfdaU, 0xd7e6e631U, 0x844242c6U, 0xd06868b8U, + 0x824141c3U, 0x299999b0U, 0x5a2d2d77U, 0x1e0f0f11U, + 0x7bb0b0cbU, 0xa85454fcU, 0x6dbbbbd6U, 0x2c16163aU, +}; +#ifndef AES_SMALL_TABLES +static const u32 Te1[256] = { + 0xa5c66363U, 0x84f87c7cU, 0x99ee7777U, 0x8df67b7bU, + 0x0dfff2f2U, 0xbdd66b6bU, 0xb1de6f6fU, 0x5491c5c5U, + 0x50603030U, 0x03020101U, 0xa9ce6767U, 0x7d562b2bU, + 0x19e7fefeU, 0x62b5d7d7U, 0xe64dababU, 0x9aec7676U, + 0x458fcacaU, 0x9d1f8282U, 0x4089c9c9U, 0x87fa7d7dU, + 0x15effafaU, 0xebb25959U, 0xc98e4747U, 0x0bfbf0f0U, + 0xec41adadU, 0x67b3d4d4U, 0xfd5fa2a2U, 0xea45afafU, + 0xbf239c9cU, 0xf753a4a4U, 0x96e47272U, 0x5b9bc0c0U, + 0xc275b7b7U, 0x1ce1fdfdU, 0xae3d9393U, 0x6a4c2626U, + 0x5a6c3636U, 0x417e3f3fU, 0x02f5f7f7U, 0x4f83ccccU, + 0x5c683434U, 0xf451a5a5U, 0x34d1e5e5U, 0x08f9f1f1U, + 0x93e27171U, 0x73abd8d8U, 0x53623131U, 0x3f2a1515U, + 0x0c080404U, 0x5295c7c7U, 0x65462323U, 0x5e9dc3c3U, + 0x28301818U, 0xa1379696U, 0x0f0a0505U, 0xb52f9a9aU, + 0x090e0707U, 0x36241212U, 0x9b1b8080U, 0x3ddfe2e2U, + 0x26cdebebU, 0x694e2727U, 0xcd7fb2b2U, 0x9fea7575U, + 0x1b120909U, 0x9e1d8383U, 0x74582c2cU, 0x2e341a1aU, + 0x2d361b1bU, 0xb2dc6e6eU, 0xeeb45a5aU, 0xfb5ba0a0U, + 0xf6a45252U, 0x4d763b3bU, 0x61b7d6d6U, 0xce7db3b3U, + 0x7b522929U, 0x3edde3e3U, 0x715e2f2fU, 0x97138484U, + 0xf5a65353U, 0x68b9d1d1U, 0x00000000U, 0x2cc1ededU, + 0x60402020U, 0x1fe3fcfcU, 0xc879b1b1U, 0xedb65b5bU, + 0xbed46a6aU, 0x468dcbcbU, 0xd967bebeU, 0x4b723939U, + 0xde944a4aU, 0xd4984c4cU, 0xe8b05858U, 0x4a85cfcfU, + 0x6bbbd0d0U, 0x2ac5efefU, 0xe54faaaaU, 0x16edfbfbU, + 0xc5864343U, 0xd79a4d4dU, 0x55663333U, 0x94118585U, + 0xcf8a4545U, 0x10e9f9f9U, 0x06040202U, 0x81fe7f7fU, + 0xf0a05050U, 0x44783c3cU, 0xba259f9fU, 0xe34ba8a8U, + 0xf3a25151U, 0xfe5da3a3U, 0xc0804040U, 0x8a058f8fU, + 0xad3f9292U, 0xbc219d9dU, 0x48703838U, 0x04f1f5f5U, + 0xdf63bcbcU, 0xc177b6b6U, 0x75afdadaU, 0x63422121U, + 0x30201010U, 0x1ae5ffffU, 0x0efdf3f3U, 0x6dbfd2d2U, + 0x4c81cdcdU, 0x14180c0cU, 0x35261313U, 0x2fc3ececU, + 0xe1be5f5fU, 0xa2359797U, 0xcc884444U, 0x392e1717U, + 0x5793c4c4U, 0xf255a7a7U, 0x82fc7e7eU, 0x477a3d3dU, + 0xacc86464U, 0xe7ba5d5dU, 0x2b321919U, 0x95e67373U, + 0xa0c06060U, 0x98198181U, 0xd19e4f4fU, 0x7fa3dcdcU, + 0x66442222U, 0x7e542a2aU, 0xab3b9090U, 0x830b8888U, + 0xca8c4646U, 0x29c7eeeeU, 0xd36bb8b8U, 0x3c281414U, + 0x79a7dedeU, 0xe2bc5e5eU, 0x1d160b0bU, 0x76addbdbU, + 0x3bdbe0e0U, 0x56643232U, 0x4e743a3aU, 0x1e140a0aU, + 0xdb924949U, 0x0a0c0606U, 0x6c482424U, 0xe4b85c5cU, + 0x5d9fc2c2U, 0x6ebdd3d3U, 0xef43acacU, 0xa6c46262U, + 0xa8399191U, 0xa4319595U, 0x37d3e4e4U, 0x8bf27979U, + 0x32d5e7e7U, 0x438bc8c8U, 0x596e3737U, 0xb7da6d6dU, + 0x8c018d8dU, 0x64b1d5d5U, 0xd29c4e4eU, 0xe049a9a9U, + 0xb4d86c6cU, 0xfaac5656U, 0x07f3f4f4U, 0x25cfeaeaU, + 0xafca6565U, 0x8ef47a7aU, 0xe947aeaeU, 0x18100808U, + 0xd56fbabaU, 0x88f07878U, 0x6f4a2525U, 0x725c2e2eU, + 0x24381c1cU, 0xf157a6a6U, 0xc773b4b4U, 0x5197c6c6U, + 0x23cbe8e8U, 0x7ca1ddddU, 0x9ce87474U, 0x213e1f1fU, + 0xdd964b4bU, 0xdc61bdbdU, 0x860d8b8bU, 0x850f8a8aU, + 0x90e07070U, 0x427c3e3eU, 0xc471b5b5U, 0xaacc6666U, + 0xd8904848U, 0x05060303U, 0x01f7f6f6U, 0x121c0e0eU, + 0xa3c26161U, 0x5f6a3535U, 0xf9ae5757U, 0xd069b9b9U, + 0x91178686U, 0x5899c1c1U, 0x273a1d1dU, 0xb9279e9eU, + 0x38d9e1e1U, 0x13ebf8f8U, 0xb32b9898U, 0x33221111U, + 0xbbd26969U, 0x70a9d9d9U, 0x89078e8eU, 0xa7339494U, + 0xb62d9b9bU, 0x223c1e1eU, 0x92158787U, 0x20c9e9e9U, + 0x4987ceceU, 0xffaa5555U, 0x78502828U, 0x7aa5dfdfU, + 0x8f038c8cU, 0xf859a1a1U, 0x80098989U, 0x171a0d0dU, + 0xda65bfbfU, 0x31d7e6e6U, 0xc6844242U, 0xb8d06868U, + 0xc3824141U, 0xb0299999U, 0x775a2d2dU, 0x111e0f0fU, + 0xcb7bb0b0U, 0xfca85454U, 0xd66dbbbbU, 0x3a2c1616U, +}; +static const u32 Te2[256] = { + 0x63a5c663U, 0x7c84f87cU, 0x7799ee77U, 0x7b8df67bU, + 0xf20dfff2U, 0x6bbdd66bU, 0x6fb1de6fU, 0xc55491c5U, + 0x30506030U, 0x01030201U, 0x67a9ce67U, 0x2b7d562bU, + 0xfe19e7feU, 0xd762b5d7U, 0xabe64dabU, 0x769aec76U, + 0xca458fcaU, 0x829d1f82U, 0xc94089c9U, 0x7d87fa7dU, + 0xfa15effaU, 0x59ebb259U, 0x47c98e47U, 0xf00bfbf0U, + 0xadec41adU, 0xd467b3d4U, 0xa2fd5fa2U, 0xafea45afU, + 0x9cbf239cU, 0xa4f753a4U, 0x7296e472U, 0xc05b9bc0U, + 0xb7c275b7U, 0xfd1ce1fdU, 0x93ae3d93U, 0x266a4c26U, + 0x365a6c36U, 0x3f417e3fU, 0xf702f5f7U, 0xcc4f83ccU, + 0x345c6834U, 0xa5f451a5U, 0xe534d1e5U, 0xf108f9f1U, + 0x7193e271U, 0xd873abd8U, 0x31536231U, 0x153f2a15U, + 0x040c0804U, 0xc75295c7U, 0x23654623U, 0xc35e9dc3U, + 0x18283018U, 0x96a13796U, 0x050f0a05U, 0x9ab52f9aU, + 0x07090e07U, 0x12362412U, 0x809b1b80U, 0xe23ddfe2U, + 0xeb26cdebU, 0x27694e27U, 0xb2cd7fb2U, 0x759fea75U, + 0x091b1209U, 0x839e1d83U, 0x2c74582cU, 0x1a2e341aU, + 0x1b2d361bU, 0x6eb2dc6eU, 0x5aeeb45aU, 0xa0fb5ba0U, + 0x52f6a452U, 0x3b4d763bU, 0xd661b7d6U, 0xb3ce7db3U, + 0x297b5229U, 0xe33edde3U, 0x2f715e2fU, 0x84971384U, + 0x53f5a653U, 0xd168b9d1U, 0x00000000U, 0xed2cc1edU, + 0x20604020U, 0xfc1fe3fcU, 0xb1c879b1U, 0x5bedb65bU, + 0x6abed46aU, 0xcb468dcbU, 0xbed967beU, 0x394b7239U, + 0x4ade944aU, 0x4cd4984cU, 0x58e8b058U, 0xcf4a85cfU, + 0xd06bbbd0U, 0xef2ac5efU, 0xaae54faaU, 0xfb16edfbU, + 0x43c58643U, 0x4dd79a4dU, 0x33556633U, 0x85941185U, + 0x45cf8a45U, 0xf910e9f9U, 0x02060402U, 0x7f81fe7fU, + 0x50f0a050U, 0x3c44783cU, 0x9fba259fU, 0xa8e34ba8U, + 0x51f3a251U, 0xa3fe5da3U, 0x40c08040U, 0x8f8a058fU, + 0x92ad3f92U, 0x9dbc219dU, 0x38487038U, 0xf504f1f5U, + 0xbcdf63bcU, 0xb6c177b6U, 0xda75afdaU, 0x21634221U, + 0x10302010U, 0xff1ae5ffU, 0xf30efdf3U, 0xd26dbfd2U, + 0xcd4c81cdU, 0x0c14180cU, 0x13352613U, 0xec2fc3ecU, + 0x5fe1be5fU, 0x97a23597U, 0x44cc8844U, 0x17392e17U, + 0xc45793c4U, 0xa7f255a7U, 0x7e82fc7eU, 0x3d477a3dU, + 0x64acc864U, 0x5de7ba5dU, 0x192b3219U, 0x7395e673U, + 0x60a0c060U, 0x81981981U, 0x4fd19e4fU, 0xdc7fa3dcU, + 0x22664422U, 0x2a7e542aU, 0x90ab3b90U, 0x88830b88U, + 0x46ca8c46U, 0xee29c7eeU, 0xb8d36bb8U, 0x143c2814U, + 0xde79a7deU, 0x5ee2bc5eU, 0x0b1d160bU, 0xdb76addbU, + 0xe03bdbe0U, 0x32566432U, 0x3a4e743aU, 0x0a1e140aU, + 0x49db9249U, 0x060a0c06U, 0x246c4824U, 0x5ce4b85cU, + 0xc25d9fc2U, 0xd36ebdd3U, 0xacef43acU, 0x62a6c462U, + 0x91a83991U, 0x95a43195U, 0xe437d3e4U, 0x798bf279U, + 0xe732d5e7U, 0xc8438bc8U, 0x37596e37U, 0x6db7da6dU, + 0x8d8c018dU, 0xd564b1d5U, 0x4ed29c4eU, 0xa9e049a9U, + 0x6cb4d86cU, 0x56faac56U, 0xf407f3f4U, 0xea25cfeaU, + 0x65afca65U, 0x7a8ef47aU, 0xaee947aeU, 0x08181008U, + 0xbad56fbaU, 0x7888f078U, 0x256f4a25U, 0x2e725c2eU, + 0x1c24381cU, 0xa6f157a6U, 0xb4c773b4U, 0xc65197c6U, + 0xe823cbe8U, 0xdd7ca1ddU, 0x749ce874U, 0x1f213e1fU, + 0x4bdd964bU, 0xbddc61bdU, 0x8b860d8bU, 0x8a850f8aU, + 0x7090e070U, 0x3e427c3eU, 0xb5c471b5U, 0x66aacc66U, + 0x48d89048U, 0x03050603U, 0xf601f7f6U, 0x0e121c0eU, + 0x61a3c261U, 0x355f6a35U, 0x57f9ae57U, 0xb9d069b9U, + 0x86911786U, 0xc15899c1U, 0x1d273a1dU, 0x9eb9279eU, + 0xe138d9e1U, 0xf813ebf8U, 0x98b32b98U, 0x11332211U, + 0x69bbd269U, 0xd970a9d9U, 0x8e89078eU, 0x94a73394U, + 0x9bb62d9bU, 0x1e223c1eU, 0x87921587U, 0xe920c9e9U, + 0xce4987ceU, 0x55ffaa55U, 0x28785028U, 0xdf7aa5dfU, + 0x8c8f038cU, 0xa1f859a1U, 0x89800989U, 0x0d171a0dU, + 0xbfda65bfU, 0xe631d7e6U, 0x42c68442U, 0x68b8d068U, + 0x41c38241U, 0x99b02999U, 0x2d775a2dU, 0x0f111e0fU, + 0xb0cb7bb0U, 0x54fca854U, 0xbbd66dbbU, 0x163a2c16U, +}; +static const u32 Te3[256] = { + + 0x6363a5c6U, 0x7c7c84f8U, 0x777799eeU, 0x7b7b8df6U, + 0xf2f20dffU, 0x6b6bbdd6U, 0x6f6fb1deU, 0xc5c55491U, + 0x30305060U, 0x01010302U, 0x6767a9ceU, 0x2b2b7d56U, + 0xfefe19e7U, 0xd7d762b5U, 0xababe64dU, 0x76769aecU, + 0xcaca458fU, 0x82829d1fU, 0xc9c94089U, 0x7d7d87faU, + 0xfafa15efU, 0x5959ebb2U, 0x4747c98eU, 0xf0f00bfbU, + 0xadadec41U, 0xd4d467b3U, 0xa2a2fd5fU, 0xafafea45U, + 0x9c9cbf23U, 0xa4a4f753U, 0x727296e4U, 0xc0c05b9bU, + 0xb7b7c275U, 0xfdfd1ce1U, 0x9393ae3dU, 0x26266a4cU, + 0x36365a6cU, 0x3f3f417eU, 0xf7f702f5U, 0xcccc4f83U, + 0x34345c68U, 0xa5a5f451U, 0xe5e534d1U, 0xf1f108f9U, + 0x717193e2U, 0xd8d873abU, 0x31315362U, 0x15153f2aU, + 0x04040c08U, 0xc7c75295U, 0x23236546U, 0xc3c35e9dU, + 0x18182830U, 0x9696a137U, 0x05050f0aU, 0x9a9ab52fU, + 0x0707090eU, 0x12123624U, 0x80809b1bU, 0xe2e23ddfU, + 0xebeb26cdU, 0x2727694eU, 0xb2b2cd7fU, 0x75759feaU, + 0x09091b12U, 0x83839e1dU, 0x2c2c7458U, 0x1a1a2e34U, + 0x1b1b2d36U, 0x6e6eb2dcU, 0x5a5aeeb4U, 0xa0a0fb5bU, + 0x5252f6a4U, 0x3b3b4d76U, 0xd6d661b7U, 0xb3b3ce7dU, + 0x29297b52U, 0xe3e33eddU, 0x2f2f715eU, 0x84849713U, + 0x5353f5a6U, 0xd1d168b9U, 0x00000000U, 0xeded2cc1U, + 0x20206040U, 0xfcfc1fe3U, 0xb1b1c879U, 0x5b5bedb6U, + 0x6a6abed4U, 0xcbcb468dU, 0xbebed967U, 0x39394b72U, + 0x4a4ade94U, 0x4c4cd498U, 0x5858e8b0U, 0xcfcf4a85U, + 0xd0d06bbbU, 0xefef2ac5U, 0xaaaae54fU, 0xfbfb16edU, + 0x4343c586U, 0x4d4dd79aU, 0x33335566U, 0x85859411U, + 0x4545cf8aU, 0xf9f910e9U, 0x02020604U, 0x7f7f81feU, + 0x5050f0a0U, 0x3c3c4478U, 0x9f9fba25U, 0xa8a8e34bU, + 0x5151f3a2U, 0xa3a3fe5dU, 0x4040c080U, 0x8f8f8a05U, + 0x9292ad3fU, 0x9d9dbc21U, 0x38384870U, 0xf5f504f1U, + 0xbcbcdf63U, 0xb6b6c177U, 0xdada75afU, 0x21216342U, + 0x10103020U, 0xffff1ae5U, 0xf3f30efdU, 0xd2d26dbfU, + 0xcdcd4c81U, 0x0c0c1418U, 0x13133526U, 0xecec2fc3U, + 0x5f5fe1beU, 0x9797a235U, 0x4444cc88U, 0x1717392eU, + 0xc4c45793U, 0xa7a7f255U, 0x7e7e82fcU, 0x3d3d477aU, + 0x6464acc8U, 0x5d5de7baU, 0x19192b32U, 0x737395e6U, + 0x6060a0c0U, 0x81819819U, 0x4f4fd19eU, 0xdcdc7fa3U, + 0x22226644U, 0x2a2a7e54U, 0x9090ab3bU, 0x8888830bU, + 0x4646ca8cU, 0xeeee29c7U, 0xb8b8d36bU, 0x14143c28U, + 0xdede79a7U, 0x5e5ee2bcU, 0x0b0b1d16U, 0xdbdb76adU, + 0xe0e03bdbU, 0x32325664U, 0x3a3a4e74U, 0x0a0a1e14U, + 0x4949db92U, 0x06060a0cU, 0x24246c48U, 0x5c5ce4b8U, + 0xc2c25d9fU, 0xd3d36ebdU, 0xacacef43U, 0x6262a6c4U, + 0x9191a839U, 0x9595a431U, 0xe4e437d3U, 0x79798bf2U, + 0xe7e732d5U, 0xc8c8438bU, 0x3737596eU, 0x6d6db7daU, + 0x8d8d8c01U, 0xd5d564b1U, 0x4e4ed29cU, 0xa9a9e049U, + 0x6c6cb4d8U, 0x5656faacU, 0xf4f407f3U, 0xeaea25cfU, + 0x6565afcaU, 0x7a7a8ef4U, 0xaeaee947U, 0x08081810U, + 0xbabad56fU, 0x787888f0U, 0x25256f4aU, 0x2e2e725cU, + 0x1c1c2438U, 0xa6a6f157U, 0xb4b4c773U, 0xc6c65197U, + 0xe8e823cbU, 0xdddd7ca1U, 0x74749ce8U, 0x1f1f213eU, + 0x4b4bdd96U, 0xbdbddc61U, 0x8b8b860dU, 0x8a8a850fU, + 0x707090e0U, 0x3e3e427cU, 0xb5b5c471U, 0x6666aaccU, + 0x4848d890U, 0x03030506U, 0xf6f601f7U, 0x0e0e121cU, + 0x6161a3c2U, 0x35355f6aU, 0x5757f9aeU, 0xb9b9d069U, + 0x86869117U, 0xc1c15899U, 0x1d1d273aU, 0x9e9eb927U, + 0xe1e138d9U, 0xf8f813ebU, 0x9898b32bU, 0x11113322U, + 0x6969bbd2U, 0xd9d970a9U, 0x8e8e8907U, 0x9494a733U, + 0x9b9bb62dU, 0x1e1e223cU, 0x87879215U, 0xe9e920c9U, + 0xcece4987U, 0x5555ffaaU, 0x28287850U, 0xdfdf7aa5U, + 0x8c8c8f03U, 0xa1a1f859U, 0x89898009U, 0x0d0d171aU, + 0xbfbfda65U, 0xe6e631d7U, 0x4242c684U, 0x6868b8d0U, + 0x4141c382U, 0x9999b029U, 0x2d2d775aU, 0x0f0f111eU, + 0xb0b0cb7bU, 0x5454fca8U, 0xbbbbd66dU, 0x16163a2cU, +}; +static const u32 Te4[256] = { + 0x63636363U, 0x7c7c7c7cU, 0x77777777U, 0x7b7b7b7bU, + 0xf2f2f2f2U, 0x6b6b6b6bU, 0x6f6f6f6fU, 0xc5c5c5c5U, + 0x30303030U, 0x01010101U, 0x67676767U, 0x2b2b2b2bU, + 0xfefefefeU, 0xd7d7d7d7U, 0xababababU, 0x76767676U, + 0xcacacacaU, 0x82828282U, 0xc9c9c9c9U, 0x7d7d7d7dU, + 0xfafafafaU, 0x59595959U, 0x47474747U, 0xf0f0f0f0U, + 0xadadadadU, 0xd4d4d4d4U, 0xa2a2a2a2U, 0xafafafafU, + 0x9c9c9c9cU, 0xa4a4a4a4U, 0x72727272U, 0xc0c0c0c0U, + 0xb7b7b7b7U, 0xfdfdfdfdU, 0x93939393U, 0x26262626U, + 0x36363636U, 0x3f3f3f3fU, 0xf7f7f7f7U, 0xccccccccU, + 0x34343434U, 0xa5a5a5a5U, 0xe5e5e5e5U, 0xf1f1f1f1U, + 0x71717171U, 0xd8d8d8d8U, 0x31313131U, 0x15151515U, + 0x04040404U, 0xc7c7c7c7U, 0x23232323U, 0xc3c3c3c3U, + 0x18181818U, 0x96969696U, 0x05050505U, 0x9a9a9a9aU, + 0x07070707U, 0x12121212U, 0x80808080U, 0xe2e2e2e2U, + 0xebebebebU, 0x27272727U, 0xb2b2b2b2U, 0x75757575U, + 0x09090909U, 0x83838383U, 0x2c2c2c2cU, 0x1a1a1a1aU, + 0x1b1b1b1bU, 0x6e6e6e6eU, 0x5a5a5a5aU, 0xa0a0a0a0U, + 0x52525252U, 0x3b3b3b3bU, 0xd6d6d6d6U, 0xb3b3b3b3U, + 0x29292929U, 0xe3e3e3e3U, 0x2f2f2f2fU, 0x84848484U, + 0x53535353U, 0xd1d1d1d1U, 0x00000000U, 0xededededU, + 0x20202020U, 0xfcfcfcfcU, 0xb1b1b1b1U, 0x5b5b5b5bU, + 0x6a6a6a6aU, 0xcbcbcbcbU, 0xbebebebeU, 0x39393939U, + 0x4a4a4a4aU, 0x4c4c4c4cU, 0x58585858U, 0xcfcfcfcfU, + 0xd0d0d0d0U, 0xefefefefU, 0xaaaaaaaaU, 0xfbfbfbfbU, + 0x43434343U, 0x4d4d4d4dU, 0x33333333U, 0x85858585U, + 0x45454545U, 0xf9f9f9f9U, 0x02020202U, 0x7f7f7f7fU, + 0x50505050U, 0x3c3c3c3cU, 0x9f9f9f9fU, 0xa8a8a8a8U, + 0x51515151U, 0xa3a3a3a3U, 0x40404040U, 0x8f8f8f8fU, + 0x92929292U, 0x9d9d9d9dU, 0x38383838U, 0xf5f5f5f5U, + 0xbcbcbcbcU, 0xb6b6b6b6U, 0xdadadadaU, 0x21212121U, + 0x10101010U, 0xffffffffU, 0xf3f3f3f3U, 0xd2d2d2d2U, + 0xcdcdcdcdU, 0x0c0c0c0cU, 0x13131313U, 0xececececU, + 0x5f5f5f5fU, 0x97979797U, 0x44444444U, 0x17171717U, + 0xc4c4c4c4U, 0xa7a7a7a7U, 0x7e7e7e7eU, 0x3d3d3d3dU, + 0x64646464U, 0x5d5d5d5dU, 0x19191919U, 0x73737373U, + 0x60606060U, 0x81818181U, 0x4f4f4f4fU, 0xdcdcdcdcU, + 0x22222222U, 0x2a2a2a2aU, 0x90909090U, 0x88888888U, + 0x46464646U, 0xeeeeeeeeU, 0xb8b8b8b8U, 0x14141414U, + 0xdedededeU, 0x5e5e5e5eU, 0x0b0b0b0bU, 0xdbdbdbdbU, + 0xe0e0e0e0U, 0x32323232U, 0x3a3a3a3aU, 0x0a0a0a0aU, + 0x49494949U, 0x06060606U, 0x24242424U, 0x5c5c5c5cU, + 0xc2c2c2c2U, 0xd3d3d3d3U, 0xacacacacU, 0x62626262U, + 0x91919191U, 0x95959595U, 0xe4e4e4e4U, 0x79797979U, + 0xe7e7e7e7U, 0xc8c8c8c8U, 0x37373737U, 0x6d6d6d6dU, + 0x8d8d8d8dU, 0xd5d5d5d5U, 0x4e4e4e4eU, 0xa9a9a9a9U, + 0x6c6c6c6cU, 0x56565656U, 0xf4f4f4f4U, 0xeaeaeaeaU, + 0x65656565U, 0x7a7a7a7aU, 0xaeaeaeaeU, 0x08080808U, + 0xbabababaU, 0x78787878U, 0x25252525U, 0x2e2e2e2eU, + 0x1c1c1c1cU, 0xa6a6a6a6U, 0xb4b4b4b4U, 0xc6c6c6c6U, + 0xe8e8e8e8U, 0xddddddddU, 0x74747474U, 0x1f1f1f1fU, + 0x4b4b4b4bU, 0xbdbdbdbdU, 0x8b8b8b8bU, 0x8a8a8a8aU, + 0x70707070U, 0x3e3e3e3eU, 0xb5b5b5b5U, 0x66666666U, + 0x48484848U, 0x03030303U, 0xf6f6f6f6U, 0x0e0e0e0eU, + 0x61616161U, 0x35353535U, 0x57575757U, 0xb9b9b9b9U, + 0x86868686U, 0xc1c1c1c1U, 0x1d1d1d1dU, 0x9e9e9e9eU, + 0xe1e1e1e1U, 0xf8f8f8f8U, 0x98989898U, 0x11111111U, + 0x69696969U, 0xd9d9d9d9U, 0x8e8e8e8eU, 0x94949494U, + 0x9b9b9b9bU, 0x1e1e1e1eU, 0x87878787U, 0xe9e9e9e9U, + 0xcecececeU, 0x55555555U, 0x28282828U, 0xdfdfdfdfU, + 0x8c8c8c8cU, 0xa1a1a1a1U, 0x89898989U, 0x0d0d0d0dU, + 0xbfbfbfbfU, 0xe6e6e6e6U, 0x42424242U, 0x68686868U, + 0x41414141U, 0x99999999U, 0x2d2d2d2dU, 0x0f0f0f0fU, + 0xb0b0b0b0U, 0x54545454U, 0xbbbbbbbbU, 0x16161616U, +}; +#endif /* AES_SMALL_TABLES */ +static const u32 Td0[256] = { + 0x51f4a750U, 0x7e416553U, 0x1a17a4c3U, 0x3a275e96U, + 0x3bab6bcbU, 0x1f9d45f1U, 0xacfa58abU, 0x4be30393U, + 0x2030fa55U, 0xad766df6U, 0x88cc7691U, 0xf5024c25U, + 0x4fe5d7fcU, 0xc52acbd7U, 0x26354480U, 0xb562a38fU, + 0xdeb15a49U, 0x25ba1b67U, 0x45ea0e98U, 0x5dfec0e1U, + 0xc32f7502U, 0x814cf012U, 0x8d4697a3U, 0x6bd3f9c6U, + 0x038f5fe7U, 0x15929c95U, 0xbf6d7aebU, 0x955259daU, + 0xd4be832dU, 0x587421d3U, 0x49e06929U, 0x8ec9c844U, + 0x75c2896aU, 0xf48e7978U, 0x99583e6bU, 0x27b971ddU, + 0xbee14fb6U, 0xf088ad17U, 0xc920ac66U, 0x7dce3ab4U, + 0x63df4a18U, 0xe51a3182U, 0x97513360U, 0x62537f45U, + 0xb16477e0U, 0xbb6bae84U, 0xfe81a01cU, 0xf9082b94U, + 0x70486858U, 0x8f45fd19U, 0x94de6c87U, 0x527bf8b7U, + 0xab73d323U, 0x724b02e2U, 0xe31f8f57U, 0x6655ab2aU, + 0xb2eb2807U, 0x2fb5c203U, 0x86c57b9aU, 0xd33708a5U, + 0x302887f2U, 0x23bfa5b2U, 0x02036abaU, 0xed16825cU, + 0x8acf1c2bU, 0xa779b492U, 0xf307f2f0U, 0x4e69e2a1U, + 0x65daf4cdU, 0x0605bed5U, 0xd134621fU, 0xc4a6fe8aU, + 0x342e539dU, 0xa2f355a0U, 0x058ae132U, 0xa4f6eb75U, + 0x0b83ec39U, 0x4060efaaU, 0x5e719f06U, 0xbd6e1051U, + 0x3e218af9U, 0x96dd063dU, 0xdd3e05aeU, 0x4de6bd46U, + 0x91548db5U, 0x71c45d05U, 0x0406d46fU, 0x605015ffU, + 0x1998fb24U, 0xd6bde997U, 0x894043ccU, 0x67d99e77U, + 0xb0e842bdU, 0x07898b88U, 0xe7195b38U, 0x79c8eedbU, + 0xa17c0a47U, 0x7c420fe9U, 0xf8841ec9U, 0x00000000U, + 0x09808683U, 0x322bed48U, 0x1e1170acU, 0x6c5a724eU, + 0xfd0efffbU, 0x0f853856U, 0x3daed51eU, 0x362d3927U, + 0x0a0fd964U, 0x685ca621U, 0x9b5b54d1U, 0x24362e3aU, + 0x0c0a67b1U, 0x9357e70fU, 0xb4ee96d2U, 0x1b9b919eU, + 0x80c0c54fU, 0x61dc20a2U, 0x5a774b69U, 0x1c121a16U, + 0xe293ba0aU, 0xc0a02ae5U, 0x3c22e043U, 0x121b171dU, + 0x0e090d0bU, 0xf28bc7adU, 0x2db6a8b9U, 0x141ea9c8U, + 0x57f11985U, 0xaf75074cU, 0xee99ddbbU, 0xa37f60fdU, + 0xf701269fU, 0x5c72f5bcU, 0x44663bc5U, 0x5bfb7e34U, + 0x8b432976U, 0xcb23c6dcU, 0xb6edfc68U, 0xb8e4f163U, + 0xd731dccaU, 0x42638510U, 0x13972240U, 0x84c61120U, + 0x854a247dU, 0xd2bb3df8U, 0xaef93211U, 0xc729a16dU, + 0x1d9e2f4bU, 0xdcb230f3U, 0x0d8652ecU, 0x77c1e3d0U, + 0x2bb3166cU, 0xa970b999U, 0x119448faU, 0x47e96422U, + 0xa8fc8cc4U, 0xa0f03f1aU, 0x567d2cd8U, 0x223390efU, + 0x87494ec7U, 0xd938d1c1U, 0x8ccaa2feU, 0x98d40b36U, + 0xa6f581cfU, 0xa57ade28U, 0xdab78e26U, 0x3fadbfa4U, + 0x2c3a9de4U, 0x5078920dU, 0x6a5fcc9bU, 0x547e4662U, + 0xf68d13c2U, 0x90d8b8e8U, 0x2e39f75eU, 0x82c3aff5U, + 0x9f5d80beU, 0x69d0937cU, 0x6fd52da9U, 0xcf2512b3U, + 0xc8ac993bU, 0x10187da7U, 0xe89c636eU, 0xdb3bbb7bU, + 0xcd267809U, 0x6e5918f4U, 0xec9ab701U, 0x834f9aa8U, + 0xe6956e65U, 0xaaffe67eU, 0x21bccf08U, 0xef15e8e6U, + 0xbae79bd9U, 0x4a6f36ceU, 0xea9f09d4U, 0x29b07cd6U, + 0x31a4b2afU, 0x2a3f2331U, 0xc6a59430U, 0x35a266c0U, + 0x744ebc37U, 0xfc82caa6U, 0xe090d0b0U, 0x33a7d815U, + 0xf104984aU, 0x41ecdaf7U, 0x7fcd500eU, 0x1791f62fU, + 0x764dd68dU, 0x43efb04dU, 0xccaa4d54U, 0xe49604dfU, + 0x9ed1b5e3U, 0x4c6a881bU, 0xc12c1fb8U, 0x4665517fU, + 0x9d5eea04U, 0x018c355dU, 0xfa877473U, 0xfb0b412eU, + 0xb3671d5aU, 0x92dbd252U, 0xe9105633U, 0x6dd64713U, + 0x9ad7618cU, 0x37a10c7aU, 0x59f8148eU, 0xeb133c89U, + 0xcea927eeU, 0xb761c935U, 0xe11ce5edU, 0x7a47b13cU, + 0x9cd2df59U, 0x55f2733fU, 0x1814ce79U, 0x73c737bfU, + 0x53f7cdeaU, 0x5ffdaa5bU, 0xdf3d6f14U, 0x7844db86U, + 0xcaaff381U, 0xb968c43eU, 0x3824342cU, 0xc2a3405fU, + 0x161dc372U, 0xbce2250cU, 0x283c498bU, 0xff0d9541U, + 0x39a80171U, 0x080cb3deU, 0xd8b4e49cU, 0x6456c190U, + 0x7bcb8461U, 0xd532b670U, 0x486c5c74U, 0xd0b85742U, +}; +#ifndef AES_SMALL_TABLES +static const u32 Td1[256] = { + 0x5051f4a7U, 0x537e4165U, 0xc31a17a4U, 0x963a275eU, + 0xcb3bab6bU, 0xf11f9d45U, 0xabacfa58U, 0x934be303U, + 0x552030faU, 0xf6ad766dU, 0x9188cc76U, 0x25f5024cU, + 0xfc4fe5d7U, 0xd7c52acbU, 0x80263544U, 0x8fb562a3U, + 0x49deb15aU, 0x6725ba1bU, 0x9845ea0eU, 0xe15dfec0U, + 0x02c32f75U, 0x12814cf0U, 0xa38d4697U, 0xc66bd3f9U, + 0xe7038f5fU, 0x9515929cU, 0xebbf6d7aU, 0xda955259U, + 0x2dd4be83U, 0xd3587421U, 0x2949e069U, 0x448ec9c8U, + 0x6a75c289U, 0x78f48e79U, 0x6b99583eU, 0xdd27b971U, + 0xb6bee14fU, 0x17f088adU, 0x66c920acU, 0xb47dce3aU, + 0x1863df4aU, 0x82e51a31U, 0x60975133U, 0x4562537fU, + 0xe0b16477U, 0x84bb6baeU, 0x1cfe81a0U, 0x94f9082bU, + 0x58704868U, 0x198f45fdU, 0x8794de6cU, 0xb7527bf8U, + 0x23ab73d3U, 0xe2724b02U, 0x57e31f8fU, 0x2a6655abU, + 0x07b2eb28U, 0x032fb5c2U, 0x9a86c57bU, 0xa5d33708U, + 0xf2302887U, 0xb223bfa5U, 0xba02036aU, 0x5ced1682U, + 0x2b8acf1cU, 0x92a779b4U, 0xf0f307f2U, 0xa14e69e2U, + 0xcd65daf4U, 0xd50605beU, 0x1fd13462U, 0x8ac4a6feU, + 0x9d342e53U, 0xa0a2f355U, 0x32058ae1U, 0x75a4f6ebU, + 0x390b83ecU, 0xaa4060efU, 0x065e719fU, 0x51bd6e10U, + 0xf93e218aU, 0x3d96dd06U, 0xaedd3e05U, 0x464de6bdU, + 0xb591548dU, 0x0571c45dU, 0x6f0406d4U, 0xff605015U, + 0x241998fbU, 0x97d6bde9U, 0xcc894043U, 0x7767d99eU, + 0xbdb0e842U, 0x8807898bU, 0x38e7195bU, 0xdb79c8eeU, + 0x47a17c0aU, 0xe97c420fU, 0xc9f8841eU, 0x00000000U, + 0x83098086U, 0x48322bedU, 0xac1e1170U, 0x4e6c5a72U, + 0xfbfd0effU, 0x560f8538U, 0x1e3daed5U, 0x27362d39U, + 0x640a0fd9U, 0x21685ca6U, 0xd19b5b54U, 0x3a24362eU, + 0xb10c0a67U, 0x0f9357e7U, 0xd2b4ee96U, 0x9e1b9b91U, + 0x4f80c0c5U, 0xa261dc20U, 0x695a774bU, 0x161c121aU, + 0x0ae293baU, 0xe5c0a02aU, 0x433c22e0U, 0x1d121b17U, + 0x0b0e090dU, 0xadf28bc7U, 0xb92db6a8U, 0xc8141ea9U, + 0x8557f119U, 0x4caf7507U, 0xbbee99ddU, 0xfda37f60U, + 0x9ff70126U, 0xbc5c72f5U, 0xc544663bU, 0x345bfb7eU, + 0x768b4329U, 0xdccb23c6U, 0x68b6edfcU, 0x63b8e4f1U, + 0xcad731dcU, 0x10426385U, 0x40139722U, 0x2084c611U, + 0x7d854a24U, 0xf8d2bb3dU, 0x11aef932U, 0x6dc729a1U, + 0x4b1d9e2fU, 0xf3dcb230U, 0xec0d8652U, 0xd077c1e3U, + 0x6c2bb316U, 0x99a970b9U, 0xfa119448U, 0x2247e964U, + 0xc4a8fc8cU, 0x1aa0f03fU, 0xd8567d2cU, 0xef223390U, + 0xc787494eU, 0xc1d938d1U, 0xfe8ccaa2U, 0x3698d40bU, + 0xcfa6f581U, 0x28a57adeU, 0x26dab78eU, 0xa43fadbfU, + 0xe42c3a9dU, 0x0d507892U, 0x9b6a5fccU, 0x62547e46U, + 0xc2f68d13U, 0xe890d8b8U, 0x5e2e39f7U, 0xf582c3afU, + 0xbe9f5d80U, 0x7c69d093U, 0xa96fd52dU, 0xb3cf2512U, + 0x3bc8ac99U, 0xa710187dU, 0x6ee89c63U, 0x7bdb3bbbU, + 0x09cd2678U, 0xf46e5918U, 0x01ec9ab7U, 0xa8834f9aU, + 0x65e6956eU, 0x7eaaffe6U, 0x0821bccfU, 0xe6ef15e8U, + 0xd9bae79bU, 0xce4a6f36U, 0xd4ea9f09U, 0xd629b07cU, + 0xaf31a4b2U, 0x312a3f23U, 0x30c6a594U, 0xc035a266U, + 0x37744ebcU, 0xa6fc82caU, 0xb0e090d0U, 0x1533a7d8U, + 0x4af10498U, 0xf741ecdaU, 0x0e7fcd50U, 0x2f1791f6U, + 0x8d764dd6U, 0x4d43efb0U, 0x54ccaa4dU, 0xdfe49604U, + 0xe39ed1b5U, 0x1b4c6a88U, 0xb8c12c1fU, 0x7f466551U, + 0x049d5eeaU, 0x5d018c35U, 0x73fa8774U, 0x2efb0b41U, + 0x5ab3671dU, 0x5292dbd2U, 0x33e91056U, 0x136dd647U, + 0x8c9ad761U, 0x7a37a10cU, 0x8e59f814U, 0x89eb133cU, + 0xeecea927U, 0x35b761c9U, 0xede11ce5U, 0x3c7a47b1U, + 0x599cd2dfU, 0x3f55f273U, 0x791814ceU, 0xbf73c737U, + 0xea53f7cdU, 0x5b5ffdaaU, 0x14df3d6fU, 0x867844dbU, + 0x81caaff3U, 0x3eb968c4U, 0x2c382434U, 0x5fc2a340U, + 0x72161dc3U, 0x0cbce225U, 0x8b283c49U, 0x41ff0d95U, + 0x7139a801U, 0xde080cb3U, 0x9cd8b4e4U, 0x906456c1U, + 0x617bcb84U, 0x70d532b6U, 0x74486c5cU, 0x42d0b857U, +}; +static const u32 Td2[256] = { + 0xa75051f4U, 0x65537e41U, 0xa4c31a17U, 0x5e963a27U, + 0x6bcb3babU, 0x45f11f9dU, 0x58abacfaU, 0x03934be3U, + 0xfa552030U, 0x6df6ad76U, 0x769188ccU, 0x4c25f502U, + 0xd7fc4fe5U, 0xcbd7c52aU, 0x44802635U, 0xa38fb562U, + 0x5a49deb1U, 0x1b6725baU, 0x0e9845eaU, 0xc0e15dfeU, + 0x7502c32fU, 0xf012814cU, 0x97a38d46U, 0xf9c66bd3U, + 0x5fe7038fU, 0x9c951592U, 0x7aebbf6dU, 0x59da9552U, + 0x832dd4beU, 0x21d35874U, 0x692949e0U, 0xc8448ec9U, + 0x896a75c2U, 0x7978f48eU, 0x3e6b9958U, 0x71dd27b9U, + 0x4fb6bee1U, 0xad17f088U, 0xac66c920U, 0x3ab47dceU, + 0x4a1863dfU, 0x3182e51aU, 0x33609751U, 0x7f456253U, + 0x77e0b164U, 0xae84bb6bU, 0xa01cfe81U, 0x2b94f908U, + 0x68587048U, 0xfd198f45U, 0x6c8794deU, 0xf8b7527bU, + 0xd323ab73U, 0x02e2724bU, 0x8f57e31fU, 0xab2a6655U, + 0x2807b2ebU, 0xc2032fb5U, 0x7b9a86c5U, 0x08a5d337U, + 0x87f23028U, 0xa5b223bfU, 0x6aba0203U, 0x825ced16U, + 0x1c2b8acfU, 0xb492a779U, 0xf2f0f307U, 0xe2a14e69U, + 0xf4cd65daU, 0xbed50605U, 0x621fd134U, 0xfe8ac4a6U, + 0x539d342eU, 0x55a0a2f3U, 0xe132058aU, 0xeb75a4f6U, + 0xec390b83U, 0xefaa4060U, 0x9f065e71U, 0x1051bd6eU, + + 0x8af93e21U, 0x063d96ddU, 0x05aedd3eU, 0xbd464de6U, + 0x8db59154U, 0x5d0571c4U, 0xd46f0406U, 0x15ff6050U, + 0xfb241998U, 0xe997d6bdU, 0x43cc8940U, 0x9e7767d9U, + 0x42bdb0e8U, 0x8b880789U, 0x5b38e719U, 0xeedb79c8U, + 0x0a47a17cU, 0x0fe97c42U, 0x1ec9f884U, 0x00000000U, + 0x86830980U, 0xed48322bU, 0x70ac1e11U, 0x724e6c5aU, + 0xfffbfd0eU, 0x38560f85U, 0xd51e3daeU, 0x3927362dU, + 0xd9640a0fU, 0xa621685cU, 0x54d19b5bU, 0x2e3a2436U, + 0x67b10c0aU, 0xe70f9357U, 0x96d2b4eeU, 0x919e1b9bU, + 0xc54f80c0U, 0x20a261dcU, 0x4b695a77U, 0x1a161c12U, + 0xba0ae293U, 0x2ae5c0a0U, 0xe0433c22U, 0x171d121bU, + 0x0d0b0e09U, 0xc7adf28bU, 0xa8b92db6U, 0xa9c8141eU, + 0x198557f1U, 0x074caf75U, 0xddbbee99U, 0x60fda37fU, + 0x269ff701U, 0xf5bc5c72U, 0x3bc54466U, 0x7e345bfbU, + 0x29768b43U, 0xc6dccb23U, 0xfc68b6edU, 0xf163b8e4U, + 0xdccad731U, 0x85104263U, 0x22401397U, 0x112084c6U, + 0x247d854aU, 0x3df8d2bbU, 0x3211aef9U, 0xa16dc729U, + 0x2f4b1d9eU, 0x30f3dcb2U, 0x52ec0d86U, 0xe3d077c1U, + 0x166c2bb3U, 0xb999a970U, 0x48fa1194U, 0x642247e9U, + 0x8cc4a8fcU, 0x3f1aa0f0U, 0x2cd8567dU, 0x90ef2233U, + 0x4ec78749U, 0xd1c1d938U, 0xa2fe8ccaU, 0x0b3698d4U, + 0x81cfa6f5U, 0xde28a57aU, 0x8e26dab7U, 0xbfa43fadU, + 0x9de42c3aU, 0x920d5078U, 0xcc9b6a5fU, 0x4662547eU, + 0x13c2f68dU, 0xb8e890d8U, 0xf75e2e39U, 0xaff582c3U, + 0x80be9f5dU, 0x937c69d0U, 0x2da96fd5U, 0x12b3cf25U, + 0x993bc8acU, 0x7da71018U, 0x636ee89cU, 0xbb7bdb3bU, + 0x7809cd26U, 0x18f46e59U, 0xb701ec9aU, 0x9aa8834fU, + 0x6e65e695U, 0xe67eaaffU, 0xcf0821bcU, 0xe8e6ef15U, + 0x9bd9bae7U, 0x36ce4a6fU, 0x09d4ea9fU, 0x7cd629b0U, + 0xb2af31a4U, 0x23312a3fU, 0x9430c6a5U, 0x66c035a2U, + 0xbc37744eU, 0xcaa6fc82U, 0xd0b0e090U, 0xd81533a7U, + 0x984af104U, 0xdaf741ecU, 0x500e7fcdU, 0xf62f1791U, + 0xd68d764dU, 0xb04d43efU, 0x4d54ccaaU, 0x04dfe496U, + 0xb5e39ed1U, 0x881b4c6aU, 0x1fb8c12cU, 0x517f4665U, + 0xea049d5eU, 0x355d018cU, 0x7473fa87U, 0x412efb0bU, + 0x1d5ab367U, 0xd25292dbU, 0x5633e910U, 0x47136dd6U, + 0x618c9ad7U, 0x0c7a37a1U, 0x148e59f8U, 0x3c89eb13U, + 0x27eecea9U, 0xc935b761U, 0xe5ede11cU, 0xb13c7a47U, + 0xdf599cd2U, 0x733f55f2U, 0xce791814U, 0x37bf73c7U, + 0xcdea53f7U, 0xaa5b5ffdU, 0x6f14df3dU, 0xdb867844U, + 0xf381caafU, 0xc43eb968U, 0x342c3824U, 0x405fc2a3U, + 0xc372161dU, 0x250cbce2U, 0x498b283cU, 0x9541ff0dU, + 0x017139a8U, 0xb3de080cU, 0xe49cd8b4U, 0xc1906456U, + 0x84617bcbU, 0xb670d532U, 0x5c74486cU, 0x5742d0b8U, +}; +static const u32 Td3[256] = { + 0xf4a75051U, 0x4165537eU, 0x17a4c31aU, 0x275e963aU, + 0xab6bcb3bU, 0x9d45f11fU, 0xfa58abacU, 0xe303934bU, + 0x30fa5520U, 0x766df6adU, 0xcc769188U, 0x024c25f5U, + 0xe5d7fc4fU, 0x2acbd7c5U, 0x35448026U, 0x62a38fb5U, + 0xb15a49deU, 0xba1b6725U, 0xea0e9845U, 0xfec0e15dU, + 0x2f7502c3U, 0x4cf01281U, 0x4697a38dU, 0xd3f9c66bU, + 0x8f5fe703U, 0x929c9515U, 0x6d7aebbfU, 0x5259da95U, + 0xbe832dd4U, 0x7421d358U, 0xe0692949U, 0xc9c8448eU, + 0xc2896a75U, 0x8e7978f4U, 0x583e6b99U, 0xb971dd27U, + 0xe14fb6beU, 0x88ad17f0U, 0x20ac66c9U, 0xce3ab47dU, + 0xdf4a1863U, 0x1a3182e5U, 0x51336097U, 0x537f4562U, + 0x6477e0b1U, 0x6bae84bbU, 0x81a01cfeU, 0x082b94f9U, + 0x48685870U, 0x45fd198fU, 0xde6c8794U, 0x7bf8b752U, + 0x73d323abU, 0x4b02e272U, 0x1f8f57e3U, 0x55ab2a66U, + 0xeb2807b2U, 0xb5c2032fU, 0xc57b9a86U, 0x3708a5d3U, + 0x2887f230U, 0xbfa5b223U, 0x036aba02U, 0x16825cedU, + 0xcf1c2b8aU, 0x79b492a7U, 0x07f2f0f3U, 0x69e2a14eU, + 0xdaf4cd65U, 0x05bed506U, 0x34621fd1U, 0xa6fe8ac4U, + 0x2e539d34U, 0xf355a0a2U, 0x8ae13205U, 0xf6eb75a4U, + 0x83ec390bU, 0x60efaa40U, 0x719f065eU, 0x6e1051bdU, + 0x218af93eU, 0xdd063d96U, 0x3e05aeddU, 0xe6bd464dU, + 0x548db591U, 0xc45d0571U, 0x06d46f04U, 0x5015ff60U, + 0x98fb2419U, 0xbde997d6U, 0x4043cc89U, 0xd99e7767U, + 0xe842bdb0U, 0x898b8807U, 0x195b38e7U, 0xc8eedb79U, + 0x7c0a47a1U, 0x420fe97cU, 0x841ec9f8U, 0x00000000U, + 0x80868309U, 0x2bed4832U, 0x1170ac1eU, 0x5a724e6cU, + 0x0efffbfdU, 0x8538560fU, 0xaed51e3dU, 0x2d392736U, + 0x0fd9640aU, 0x5ca62168U, 0x5b54d19bU, 0x362e3a24U, + 0x0a67b10cU, 0x57e70f93U, 0xee96d2b4U, 0x9b919e1bU, + 0xc0c54f80U, 0xdc20a261U, 0x774b695aU, 0x121a161cU, + 0x93ba0ae2U, 0xa02ae5c0U, 0x22e0433cU, 0x1b171d12U, + 0x090d0b0eU, 0x8bc7adf2U, 0xb6a8b92dU, 0x1ea9c814U, + 0xf1198557U, 0x75074cafU, 0x99ddbbeeU, 0x7f60fda3U, + 0x01269ff7U, 0x72f5bc5cU, 0x663bc544U, 0xfb7e345bU, + 0x4329768bU, 0x23c6dccbU, 0xedfc68b6U, 0xe4f163b8U, + 0x31dccad7U, 0x63851042U, 0x97224013U, 0xc6112084U, + 0x4a247d85U, 0xbb3df8d2U, 0xf93211aeU, 0x29a16dc7U, + 0x9e2f4b1dU, 0xb230f3dcU, 0x8652ec0dU, 0xc1e3d077U, + 0xb3166c2bU, 0x70b999a9U, 0x9448fa11U, 0xe9642247U, + 0xfc8cc4a8U, 0xf03f1aa0U, 0x7d2cd856U, 0x3390ef22U, + 0x494ec787U, 0x38d1c1d9U, 0xcaa2fe8cU, 0xd40b3698U, + 0xf581cfa6U, 0x7ade28a5U, 0xb78e26daU, 0xadbfa43fU, + 0x3a9de42cU, 0x78920d50U, 0x5fcc9b6aU, 0x7e466254U, + 0x8d13c2f6U, 0xd8b8e890U, 0x39f75e2eU, 0xc3aff582U, + 0x5d80be9fU, 0xd0937c69U, 0xd52da96fU, 0x2512b3cfU, + 0xac993bc8U, 0x187da710U, 0x9c636ee8U, 0x3bbb7bdbU, + 0x267809cdU, 0x5918f46eU, 0x9ab701ecU, 0x4f9aa883U, + 0x956e65e6U, 0xffe67eaaU, 0xbccf0821U, 0x15e8e6efU, + 0xe79bd9baU, 0x6f36ce4aU, 0x9f09d4eaU, 0xb07cd629U, + 0xa4b2af31U, 0x3f23312aU, 0xa59430c6U, 0xa266c035U, + 0x4ebc3774U, 0x82caa6fcU, 0x90d0b0e0U, 0xa7d81533U, + 0x04984af1U, 0xecdaf741U, 0xcd500e7fU, 0x91f62f17U, + 0x4dd68d76U, 0xefb04d43U, 0xaa4d54ccU, 0x9604dfe4U, + 0xd1b5e39eU, 0x6a881b4cU, 0x2c1fb8c1U, 0x65517f46U, + 0x5eea049dU, 0x8c355d01U, 0x877473faU, 0x0b412efbU, + 0x671d5ab3U, 0xdbd25292U, 0x105633e9U, 0xd647136dU, + 0xd7618c9aU, 0xa10c7a37U, 0xf8148e59U, 0x133c89ebU, + 0xa927eeceU, 0x61c935b7U, 0x1ce5ede1U, 0x47b13c7aU, + 0xd2df599cU, 0xf2733f55U, 0x14ce7918U, 0xc737bf73U, + 0xf7cdea53U, 0xfdaa5b5fU, 0x3d6f14dfU, 0x44db8678U, + 0xaff381caU, 0x68c43eb9U, 0x24342c38U, 0xa3405fc2U, + 0x1dc37216U, 0xe2250cbcU, 0x3c498b28U, 0x0d9541ffU, + 0xa8017139U, 0x0cb3de08U, 0xb4e49cd8U, 0x56c19064U, + 0xcb84617bU, 0x32b670d5U, 0x6c5c7448U, 0xb85742d0U, +}; +static const u32 Td4[256] = { + 0x52525252U, 0x09090909U, 0x6a6a6a6aU, 0xd5d5d5d5U, + 0x30303030U, 0x36363636U, 0xa5a5a5a5U, 0x38383838U, + 0xbfbfbfbfU, 0x40404040U, 0xa3a3a3a3U, 0x9e9e9e9eU, + 0x81818181U, 0xf3f3f3f3U, 0xd7d7d7d7U, 0xfbfbfbfbU, + 0x7c7c7c7cU, 0xe3e3e3e3U, 0x39393939U, 0x82828282U, + 0x9b9b9b9bU, 0x2f2f2f2fU, 0xffffffffU, 0x87878787U, + 0x34343434U, 0x8e8e8e8eU, 0x43434343U, 0x44444444U, + 0xc4c4c4c4U, 0xdedededeU, 0xe9e9e9e9U, 0xcbcbcbcbU, + 0x54545454U, 0x7b7b7b7bU, 0x94949494U, 0x32323232U, + 0xa6a6a6a6U, 0xc2c2c2c2U, 0x23232323U, 0x3d3d3d3dU, + 0xeeeeeeeeU, 0x4c4c4c4cU, 0x95959595U, 0x0b0b0b0bU, + 0x42424242U, 0xfafafafaU, 0xc3c3c3c3U, 0x4e4e4e4eU, + 0x08080808U, 0x2e2e2e2eU, 0xa1a1a1a1U, 0x66666666U, + 0x28282828U, 0xd9d9d9d9U, 0x24242424U, 0xb2b2b2b2U, + 0x76767676U, 0x5b5b5b5bU, 0xa2a2a2a2U, 0x49494949U, + 0x6d6d6d6dU, 0x8b8b8b8bU, 0xd1d1d1d1U, 0x25252525U, + 0x72727272U, 0xf8f8f8f8U, 0xf6f6f6f6U, 0x64646464U, + 0x86868686U, 0x68686868U, 0x98989898U, 0x16161616U, + 0xd4d4d4d4U, 0xa4a4a4a4U, 0x5c5c5c5cU, 0xccccccccU, + 0x5d5d5d5dU, 0x65656565U, 0xb6b6b6b6U, 0x92929292U, + 0x6c6c6c6cU, 0x70707070U, 0x48484848U, 0x50505050U, + 0xfdfdfdfdU, 0xededededU, 0xb9b9b9b9U, 0xdadadadaU, + 0x5e5e5e5eU, 0x15151515U, 0x46464646U, 0x57575757U, + 0xa7a7a7a7U, 0x8d8d8d8dU, 0x9d9d9d9dU, 0x84848484U, + 0x90909090U, 0xd8d8d8d8U, 0xababababU, 0x00000000U, + 0x8c8c8c8cU, 0xbcbcbcbcU, 0xd3d3d3d3U, 0x0a0a0a0aU, + 0xf7f7f7f7U, 0xe4e4e4e4U, 0x58585858U, 0x05050505U, + 0xb8b8b8b8U, 0xb3b3b3b3U, 0x45454545U, 0x06060606U, + 0xd0d0d0d0U, 0x2c2c2c2cU, 0x1e1e1e1eU, 0x8f8f8f8fU, + 0xcacacacaU, 0x3f3f3f3fU, 0x0f0f0f0fU, 0x02020202U, + 0xc1c1c1c1U, 0xafafafafU, 0xbdbdbdbdU, 0x03030303U, + 0x01010101U, 0x13131313U, 0x8a8a8a8aU, 0x6b6b6b6bU, + 0x3a3a3a3aU, 0x91919191U, 0x11111111U, 0x41414141U, + 0x4f4f4f4fU, 0x67676767U, 0xdcdcdcdcU, 0xeaeaeaeaU, + 0x97979797U, 0xf2f2f2f2U, 0xcfcfcfcfU, 0xcecececeU, + 0xf0f0f0f0U, 0xb4b4b4b4U, 0xe6e6e6e6U, 0x73737373U, + 0x96969696U, 0xacacacacU, 0x74747474U, 0x22222222U, + 0xe7e7e7e7U, 0xadadadadU, 0x35353535U, 0x85858585U, + 0xe2e2e2e2U, 0xf9f9f9f9U, 0x37373737U, 0xe8e8e8e8U, + 0x1c1c1c1cU, 0x75757575U, 0xdfdfdfdfU, 0x6e6e6e6eU, + 0x47474747U, 0xf1f1f1f1U, 0x1a1a1a1aU, 0x71717171U, + 0x1d1d1d1dU, 0x29292929U, 0xc5c5c5c5U, 0x89898989U, + 0x6f6f6f6fU, 0xb7b7b7b7U, 0x62626262U, 0x0e0e0e0eU, + 0xaaaaaaaaU, 0x18181818U, 0xbebebebeU, 0x1b1b1b1bU, + 0xfcfcfcfcU, 0x56565656U, 0x3e3e3e3eU, 0x4b4b4b4bU, + 0xc6c6c6c6U, 0xd2d2d2d2U, 0x79797979U, 0x20202020U, + 0x9a9a9a9aU, 0xdbdbdbdbU, 0xc0c0c0c0U, 0xfefefefeU, + 0x78787878U, 0xcdcdcdcdU, 0x5a5a5a5aU, 0xf4f4f4f4U, + 0x1f1f1f1fU, 0xddddddddU, 0xa8a8a8a8U, 0x33333333U, + 0x88888888U, 0x07070707U, 0xc7c7c7c7U, 0x31313131U, + 0xb1b1b1b1U, 0x12121212U, 0x10101010U, 0x59595959U, + 0x27272727U, 0x80808080U, 0xececececU, 0x5f5f5f5fU, + 0x60606060U, 0x51515151U, 0x7f7f7f7fU, 0xa9a9a9a9U, + 0x19191919U, 0xb5b5b5b5U, 0x4a4a4a4aU, 0x0d0d0d0dU, + 0x2d2d2d2dU, 0xe5e5e5e5U, 0x7a7a7a7aU, 0x9f9f9f9fU, + 0x93939393U, 0xc9c9c9c9U, 0x9c9c9c9cU, 0xefefefefU, + 0xa0a0a0a0U, 0xe0e0e0e0U, 0x3b3b3b3bU, 0x4d4d4d4dU, + 0xaeaeaeaeU, 0x2a2a2a2aU, 0xf5f5f5f5U, 0xb0b0b0b0U, + 0xc8c8c8c8U, 0xebebebebU, 0xbbbbbbbbU, 0x3c3c3c3cU, + 0x83838383U, 0x53535353U, 0x99999999U, 0x61616161U, + 0x17171717U, 0x2b2b2b2bU, 0x04040404U, 0x7e7e7e7eU, + 0xbabababaU, 0x77777777U, 0xd6d6d6d6U, 0x26262626U, + 0xe1e1e1e1U, 0x69696969U, 0x14141414U, 0x63636363U, + 0x55555555U, 0x21212121U, 0x0c0c0c0cU, 0x7d7d7d7dU, +}; +static const u32 rcon[] = { + 0x01000000, 0x02000000, 0x04000000, 0x08000000, + 0x10000000, 0x20000000, 0x40000000, 0x80000000, + 0x1B000000, 0x36000000, /* for 128-bit blocks, Rijndael never uses more than 10 rcon values */ +}; +#else /* AES_SMALL_TABLES */ +static const u8 Td4s[256] = { + 0x52U, 0x09U, 0x6aU, 0xd5U, 0x30U, 0x36U, 0xa5U, 0x38U, + 0xbfU, 0x40U, 0xa3U, 0x9eU, 0x81U, 0xf3U, 0xd7U, 0xfbU, + 0x7cU, 0xe3U, 0x39U, 0x82U, 0x9bU, 0x2fU, 0xffU, 0x87U, + 0x34U, 0x8eU, 0x43U, 0x44U, 0xc4U, 0xdeU, 0xe9U, 0xcbU, + 0x54U, 0x7bU, 0x94U, 0x32U, 0xa6U, 0xc2U, 0x23U, 0x3dU, + 0xeeU, 0x4cU, 0x95U, 0x0bU, 0x42U, 0xfaU, 0xc3U, 0x4eU, + 0x08U, 0x2eU, 0xa1U, 0x66U, 0x28U, 0xd9U, 0x24U, 0xb2U, + 0x76U, 0x5bU, 0xa2U, 0x49U, 0x6dU, 0x8bU, 0xd1U, 0x25U, + 0x72U, 0xf8U, 0xf6U, 0x64U, 0x86U, 0x68U, 0x98U, 0x16U, + 0xd4U, 0xa4U, 0x5cU, 0xccU, 0x5dU, 0x65U, 0xb6U, 0x92U, + 0x6cU, 0x70U, 0x48U, 0x50U, 0xfdU, 0xedU, 0xb9U, 0xdaU, + 0x5eU, 0x15U, 0x46U, 0x57U, 0xa7U, 0x8dU, 0x9dU, 0x84U, + 0x90U, 0xd8U, 0xabU, 0x00U, 0x8cU, 0xbcU, 0xd3U, 0x0aU, + 0xf7U, 0xe4U, 0x58U, 0x05U, 0xb8U, 0xb3U, 0x45U, 0x06U, + 0xd0U, 0x2cU, 0x1eU, 0x8fU, 0xcaU, 0x3fU, 0x0fU, 0x02U, + 0xc1U, 0xafU, 0xbdU, 0x03U, 0x01U, 0x13U, 0x8aU, 0x6bU, + 0x3aU, 0x91U, 0x11U, 0x41U, 0x4fU, 0x67U, 0xdcU, 0xeaU, + 0x97U, 0xf2U, 0xcfU, 0xceU, 0xf0U, 0xb4U, 0xe6U, 0x73U, + 0x96U, 0xacU, 0x74U, 0x22U, 0xe7U, 0xadU, 0x35U, 0x85U, + 0xe2U, 0xf9U, 0x37U, 0xe8U, 0x1cU, 0x75U, 0xdfU, 0x6eU, + 0x47U, 0xf1U, 0x1aU, 0x71U, 0x1dU, 0x29U, 0xc5U, 0x89U, + 0x6fU, 0xb7U, 0x62U, 0x0eU, 0xaaU, 0x18U, 0xbeU, 0x1bU, + 0xfcU, 0x56U, 0x3eU, 0x4bU, 0xc6U, 0xd2U, 0x79U, 0x20U, + 0x9aU, 0xdbU, 0xc0U, 0xfeU, 0x78U, 0xcdU, 0x5aU, 0xf4U, + 0x1fU, 0xddU, 0xa8U, 0x33U, 0x88U, 0x07U, 0xc7U, 0x31U, + 0xb1U, 0x12U, 0x10U, 0x59U, 0x27U, 0x80U, 0xecU, 0x5fU, + 0x60U, 0x51U, 0x7fU, 0xa9U, 0x19U, 0xb5U, 0x4aU, 0x0dU, + 0x2dU, 0xe5U, 0x7aU, 0x9fU, 0x93U, 0xc9U, 0x9cU, 0xefU, + 0xa0U, 0xe0U, 0x3bU, 0x4dU, 0xaeU, 0x2aU, 0xf5U, 0xb0U, + 0xc8U, 0xebU, 0xbbU, 0x3cU, 0x83U, 0x53U, 0x99U, 0x61U, + 0x17U, 0x2bU, 0x04U, 0x7eU, 0xbaU, 0x77U, 0xd6U, 0x26U, + 0xe1U, 0x69U, 0x14U, 0x63U, 0x55U, 0x21U, 0x0cU, 0x7dU, +}; +static const u8 rcons[] = { + 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80, 0x1B, 0x36 + /* for 128-bit blocks, Rijndael never uses more than 10 rcon values */ +}; +#endif /* AES_SMALL_TABLES */ + + +#ifndef AES_SMALL_TABLES + +#define RCON(i) rcon[(i)] + +#define TE0(i) Te0[((i) >> 24) & 0xff] +#define TE1(i) Te1[((i) >> 16) & 0xff] +#define TE2(i) Te2[((i) >> 8) & 0xff] +#define TE3(i) Te3[(i) & 0xff] +#define TE41(i) (Te4[((i) >> 24) & 0xff] & 0xff000000) +#define TE42(i) (Te4[((i) >> 16) & 0xff] & 0x00ff0000) +#define TE43(i) (Te4[((i) >> 8) & 0xff] & 0x0000ff00) +#define TE44(i) (Te4[(i) & 0xff] & 0x000000ff) +#define TE421(i) (Te4[((i) >> 16) & 0xff] & 0xff000000) +#define TE432(i) (Te4[((i) >> 8) & 0xff] & 0x00ff0000) +#define TE443(i) (Te4[(i) & 0xff] & 0x0000ff00) +#define TE414(i) (Te4[((i) >> 24) & 0xff] & 0x000000ff) +#define TE4(i) (Te4[(i)] & 0x000000ff) + +#define TD0(i) Td0[((i) >> 24) & 0xff] +#define TD1(i) Td1[((i) >> 16) & 0xff] +#define TD2(i) Td2[((i) >> 8) & 0xff] +#define TD3(i) Td3[(i) & 0xff] +#define TD41(i) (Td4[((i) >> 24) & 0xff] & 0xff000000) +#define TD42(i) (Td4[((i) >> 16) & 0xff] & 0x00ff0000) +#define TD43(i) (Td4[((i) >> 8) & 0xff] & 0x0000ff00) +#define TD44(i) (Td4[(i) & 0xff] & 0x000000ff) +#define TD0_(i) Td0[(i) & 0xff] +#define TD1_(i) Td1[(i) & 0xff] +#define TD2_(i) Td2[(i) & 0xff] +#define TD3_(i) Td3[(i) & 0xff] + +#else /* AES_SMALL_TABLES */ + +#define RCON(i) (rcons[(i)] << 24) + +static inline u32 rotr(u32 val, int bits) +{ + return (val >> bits) | (val << (32 - bits)); +} + +#define TE0(i) Te0[((i) >> 24) & 0xff] +#define TE1(i) rotr(Te0[((i) >> 16) & 0xff], 8) +#define TE2(i) rotr(Te0[((i) >> 8) & 0xff], 16) +#define TE3(i) rotr(Te0[(i) & 0xff], 24) +#define TE41(i) ((Te0[((i) >> 24) & 0xff] << 8) & 0xff000000) +#define TE42(i) (Te0[((i) >> 16) & 0xff] & 0x00ff0000) +#define TE43(i) (Te0[((i) >> 8) & 0xff] & 0x0000ff00) +#define TE44(i) ((Te0[(i) & 0xff] >> 8) & 0x000000ff) +#define TE421(i) ((Te0[((i) >> 16) & 0xff] << 8) & 0xff000000) +#define TE432(i) (Te0[((i) >> 8) & 0xff] & 0x00ff0000) +#define TE443(i) (Te0[(i) & 0xff] & 0x0000ff00) +#define TE414(i) ((Te0[((i) >> 24) & 0xff] >> 8) & 0x000000ff) +#define TE4(i) ((Te0[(i)] >> 8) & 0x000000ff) + +#define TD0(i) Td0[((i) >> 24) & 0xff] +#define TD1(i) rotr(Td0[((i) >> 16) & 0xff], 8) +#define TD2(i) rotr(Td0[((i) >> 8) & 0xff], 16) +#define TD3(i) rotr(Td0[(i) & 0xff], 24) +#define TD41(i) (Td4s[((i) >> 24) & 0xff] << 24) +#define TD42(i) (Td4s[((i) >> 16) & 0xff] << 16) +#define TD43(i) (Td4s[((i) >> 8) & 0xff] << 8) +#define TD44(i) (Td4s[(i) & 0xff]) +#define TD0_(i) Td0[(i) & 0xff] +#define TD1_(i) rotr(Td0[(i) & 0xff], 8) +#define TD2_(i) rotr(Td0[(i) & 0xff], 16) +#define TD3_(i) rotr(Td0[(i) & 0xff], 24) + +#endif /* AES_SMALL_TABLES */ + +#define SWAP(x) (_lrotl(x, 8) & 0x00ff00ff | _lrotr(x, 8) & 0xff00ff00) + +#ifdef _MSC_VER +#define GETU32(p) SWAP(*((u32 *)(p))) +#define PUTU32(ct, st) { *((u32 *)(ct)) = SWAP((st)); } +#else +#define GETU32(pt) (((u32)(pt)[0] << 24) ^ ((u32)(pt)[1] << 16) ^ \ +((u32)(pt)[2] << 8) ^ ((u32)(pt)[3])) +#define PUTU32(ct, st) { \ +(ct)[0] = (u8)((st) >> 24); (ct)[1] = (u8)((st) >> 16); \ +(ct)[2] = (u8)((st) >> 8); (ct)[3] = (u8)(st); } +#endif + +/** + * Expand the cipher key into the encryption key schedule. + * + * @return the number of rounds for the given cipher key size. + */ +static void rijndaelKeySetupEnc(u32 rk[/*44*/], const u8 cipherKey[]) +{ + int i; + u32 temp; + + rk[0] = GETU32(cipherKey ); + rk[1] = GETU32(cipherKey + 4); + rk[2] = GETU32(cipherKey + 8); + rk[3] = GETU32(cipherKey + 12); + for (i = 0; i < 10; i++) { + temp = rk[3]; + rk[4] = rk[0] ^ + TE421(temp) ^ TE432(temp) ^ TE443(temp) ^ TE414(temp) ^ + RCON(i); + rk[5] = rk[1] ^ rk[4]; + rk[6] = rk[2] ^ rk[5]; + rk[7] = rk[3] ^ rk[6]; + rk += 4; + } +} + +#ifndef CONFIG_NO_AES_DECRYPT +/** + * Expand the cipher key into the decryption key schedule. + * + * @return the number of rounds for the given cipher key size. + */ +static void rijndaelKeySetupDec(u32 rk[/*44*/], const u8 cipherKey[]) +{ + int Nr = 10, i, j; + u32 temp; + + /* expand the cipher key: */ + rijndaelKeySetupEnc(rk, cipherKey); + /* invert the order of the round keys: */ + for (i = 0, j = 4*Nr; i < j; i += 4, j -= 4) { + temp = rk[i ]; rk[i ] = rk[j ]; rk[j ] = temp; + temp = rk[i + 1]; rk[i + 1] = rk[j + 1]; rk[j + 1] = temp; + temp = rk[i + 2]; rk[i + 2] = rk[j + 2]; rk[j + 2] = temp; + temp = rk[i + 3]; rk[i + 3] = rk[j + 3]; rk[j + 3] = temp; + } + /* apply the inverse MixColumn transform to all round keys but the + * first and the last: */ + for (i = 1; i < Nr; i++) { + rk += 4; + for (j = 0; j < 4; j++) { + rk[j] = TD0_(TE4((rk[j] >> 24) )) ^ + TD1_(TE4((rk[j] >> 16) & 0xff)) ^ + TD2_(TE4((rk[j] >> 8) & 0xff)) ^ + TD3_(TE4((rk[j] ) & 0xff)); + } + } +} +#endif /* CONFIG_NO_AES_DECRYPT */ + +#ifndef CONFIG_NO_AES_ENCRYPT +static void rijndaelEncrypt(const u32 rk[/*44*/], const u8 pt[16], u8 ct[16]) +{ + u32 s0, s1, s2, s3, t0, t1, t2, t3; + const int Nr = 10; +#ifndef FULL_UNROLL + int r; +#endif /* ?FULL_UNROLL */ + + /* + * map byte array block to cipher state + * and add initial round key: + */ + s0 = GETU32(pt ) ^ rk[0]; + s1 = GETU32(pt + 4) ^ rk[1]; + s2 = GETU32(pt + 8) ^ rk[2]; + s3 = GETU32(pt + 12) ^ rk[3]; + +#define ROUND(i,d,s) \ +d##0 = TE0(s##0) ^ TE1(s##1) ^ TE2(s##2) ^ TE3(s##3) ^ rk[4 * i]; \ +d##1 = TE0(s##1) ^ TE1(s##2) ^ TE2(s##3) ^ TE3(s##0) ^ rk[4 * i + 1]; \ +d##2 = TE0(s##2) ^ TE1(s##3) ^ TE2(s##0) ^ TE3(s##1) ^ rk[4 * i + 2]; \ +d##3 = TE0(s##3) ^ TE1(s##0) ^ TE2(s##1) ^ TE3(s##2) ^ rk[4 * i + 3] + +#ifdef FULL_UNROLL + + ROUND(1,t,s); + ROUND(2,s,t); + ROUND(3,t,s); + ROUND(4,s,t); + ROUND(5,t,s); + ROUND(6,s,t); + ROUND(7,t,s); + ROUND(8,s,t); + ROUND(9,t,s); + + rk += Nr << 2; + +#else /* !FULL_UNROLL */ + + /* Nr - 1 full rounds: */ + r = Nr >> 1; + for (;;) { + ROUND(1,t,s); + rk += 8; + if (--r == 0) + break; + ROUND(0,s,t); + } + +#endif /* ?FULL_UNROLL */ + +#undef ROUND + + /* + * apply last round and + * map cipher state to byte array block: + */ + s0 = TE41(t0) ^ TE42(t1) ^ TE43(t2) ^ TE44(t3) ^ rk[0]; + PUTU32(ct , s0); + s1 = TE41(t1) ^ TE42(t2) ^ TE43(t3) ^ TE44(t0) ^ rk[1]; + PUTU32(ct + 4, s1); + s2 = TE41(t2) ^ TE42(t3) ^ TE43(t0) ^ TE44(t1) ^ rk[2]; + PUTU32(ct + 8, s2); + s3 = TE41(t3) ^ TE42(t0) ^ TE43(t1) ^ TE44(t2) ^ rk[3]; + PUTU32(ct + 12, s3); +} +#endif /* CONFIG_NO_AES_ENCRYPT */ + +static void rijndaelDecrypt(const u32 rk[/*44*/], const u8 ct[16], u8 pt[16]) +{ + u32 s0, s1, s2, s3, t0, t1, t2, t3; + const int Nr = 10; +#ifndef FULL_UNROLL + int r; +#endif /* ?FULL_UNROLL */ + + /* + * map byte array block to cipher state + * and add initial round key: + */ + s0 = GETU32(ct ) ^ rk[0]; + s1 = GETU32(ct + 4) ^ rk[1]; + s2 = GETU32(ct + 8) ^ rk[2]; + s3 = GETU32(ct + 12) ^ rk[3]; + +#define ROUND(i,d,s) \ +d##0 = TD0(s##0) ^ TD1(s##3) ^ TD2(s##2) ^ TD3(s##1) ^ rk[4 * i]; \ +d##1 = TD0(s##1) ^ TD1(s##0) ^ TD2(s##3) ^ TD3(s##2) ^ rk[4 * i + 1]; \ +d##2 = TD0(s##2) ^ TD1(s##1) ^ TD2(s##0) ^ TD3(s##3) ^ rk[4 * i + 2]; \ +d##3 = TD0(s##3) ^ TD1(s##2) ^ TD2(s##1) ^ TD3(s##0) ^ rk[4 * i + 3] + +#ifdef FULL_UNROLL + + ROUND(1,t,s); + ROUND(2,s,t); + ROUND(3,t,s); + ROUND(4,s,t); + ROUND(5,t,s); + ROUND(6,s,t); + ROUND(7,t,s); + ROUND(8,s,t); + ROUND(9,t,s); + + rk += Nr << 2; + +#else /* !FULL_UNROLL */ + + /* Nr - 1 full rounds: */ + r = Nr >> 1; + for (;;) { + ROUND(1,t,s); + rk += 8; + if (--r == 0) + break; + ROUND(0,s,t); + } + +#endif /* ?FULL_UNROLL */ + +#undef ROUND + + /* + * apply last round and + * map cipher state to byte array block: + */ + s0 = TD41(t0) ^ TD42(t3) ^ TD43(t2) ^ TD44(t1) ^ rk[0]; + PUTU32(pt , s0); + s1 = TD41(t1) ^ TD42(t0) ^ TD43(t3) ^ TD44(t2) ^ rk[1]; + PUTU32(pt + 4, s1); + s2 = TD41(t2) ^ TD42(t1) ^ TD43(t0) ^ TD44(t3) ^ rk[2]; + PUTU32(pt + 8, s2); + s3 = TD41(t3) ^ TD42(t2) ^ TD43(t1) ^ TD44(t0) ^ rk[3]; + PUTU32(pt + 12, s3); +} + +#define AES_PRIV_SIZE 44 diff --git a/package/network/services/ead/src/ead-client.c b/package/network/services/ead/src/ead-client.c new file mode 100644 index 0000000000..54d8b1343f --- /dev/null +++ b/package/network/services/ead/src/ead-client.c @@ -0,0 +1,433 @@ +/* + * Client for the Emergency Access Daemon + * Copyright (C) 2008 Felix Fietkau <nbd@openwrt.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <sys/types.h> +#include <sys/socket.h> +#include <sys/time.h> +#include <netinet/in.h> +#include <arpa/inet.h> +#include <stdio.h> +#include <stddef.h> +#include <stdint.h> +#include <stdlib.h> +#include <stdbool.h> +#include <string.h> +#include <fcntl.h> +#include <unistd.h> +#include <t_pwd.h> +#include <t_read.h> +#include <t_sha.h> +#include <t_defines.h> +#include <t_client.h> +#include "ead.h" +#include "ead-crypt.h" + +#include "pw_encrypt_md5.c" + +#define EAD_TIMEOUT 400 +#define EAD_TIMEOUT_LONG 2000 + +static char msgbuf[1500]; +static struct ead_msg *msg = (struct ead_msg *) msgbuf; +static uint16_t nid = 0xffff; +struct sockaddr_in local, remote; +static int s = 0; +static int sockflags; +static struct in_addr serverip = { + .s_addr = 0x01010101 /* dummy */ +}; + +static unsigned char *skey = NULL; +static unsigned char bbuf[MAXPARAMLEN]; +static unsigned char saltbuf[MAXSALTLEN]; +static char *username = NULL; +static char password[MAXPARAMLEN] = ""; +static char pw_md5[MD5_OUT_BUFSIZE]; +static char pw_salt[MAXSALTLEN]; + +static struct t_client *tc = NULL; +static struct t_num salt = { .data = saltbuf }; +static struct t_num *A, B; +static struct t_preconf *tcp; +static int auth_type = EAD_AUTH_DEFAULT; +static int timeout = EAD_TIMEOUT; +static uint16_t sid = 0; + +static void +set_nonblock(int enable) +{ + if (enable == !!(sockflags & O_NONBLOCK)); + return; + + sockflags ^= O_NONBLOCK; + fcntl(s, F_SETFL, sockflags); +} + +static int +send_packet(int type, bool (*handler)(void), unsigned int max) +{ + struct timeval tv; + fd_set fds; + int nfds; + int len; + int res = 0; + + type = htonl(type); + memcpy(&msg->ip, &serverip.s_addr, sizeof(msg->ip)); + set_nonblock(0); + sendto(s, msgbuf, sizeof(struct ead_msg) + ntohl(msg->len), 0, (struct sockaddr *) &remote, sizeof(remote)); + set_nonblock(1); + + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout % 1000) * 1000; + + FD_ZERO(&fds); + do { + FD_SET(s, &fds); + nfds = select(s + 1, &fds, NULL, NULL, &tv); + + if (nfds <= 0) + break; + + if (!FD_ISSET(s, &fds)) + break; + + len = read(s, msgbuf, sizeof(msgbuf)); + if (len < 0) + break; + + if (len < sizeof(struct ead_msg)) + continue; + + if (len < sizeof(struct ead_msg) + ntohl(msg->len)) + continue; + + if (msg->magic != htonl(EAD_MAGIC)) + continue; + + if ((nid != 0xffff) && (ntohs(msg->nid) != nid)) + continue; + + if (msg->type != type) + continue; + + if (handler()) + res++; + + if ((max > 0) && (res >= max)) + break; + } while (1); + + return res; +} + +static void +prepare_password(void) +{ + switch(auth_type) { + case EAD_AUTH_DEFAULT: + break; + case EAD_AUTH_MD5: + md5_crypt(pw_md5, (unsigned char *) password, (unsigned char *) pw_salt); + strncpy(password, pw_md5, sizeof(password)); + break; + } +} + +static bool +handle_pong(void) +{ + struct ead_msg_pong *pong = EAD_DATA(msg, pong); + int len = ntohl(msg->len) - sizeof(struct ead_msg_pong); + + if (len <= 0) + return false; + + pong->name[len] = 0; + auth_type = ntohs(pong->auth_type); + if (nid == 0xffff) + printf("%04x: %s\n", ntohs(msg->nid), pong->name); + sid = msg->sid; + return true; +} + +static bool +handle_prime(void) +{ + struct ead_msg_salt *sb = EAD_DATA(msg, salt); + + salt.len = sb->len; + memcpy(salt.data, sb->salt, salt.len); + + if (auth_type == EAD_AUTH_MD5) { + memcpy(pw_salt, sb->ext_salt, MAXSALTLEN); + pw_salt[MAXSALTLEN - 1] = 0; + } + + tcp = t_getpreparam(sb->prime); + tc = t_clientopen(username, &tcp->modulus, &tcp->generator, &salt); + if (!tc) { + fprintf(stderr, "Client open failed\n"); + return false; + } + + return true; +} + +static bool +handle_b(void) +{ + struct ead_msg_number *num = EAD_DATA(msg, number); + int len = ntohl(msg->len) - sizeof(struct ead_msg_number); + + B.data = bbuf; + B.len = len; + memcpy(bbuf, num->data, len); + return true; +} + +static bool +handle_none(void) +{ + return true; +} + +static bool +handle_done_auth(void) +{ + struct ead_msg_auth *auth = EAD_DATA(msg, auth); + if (t_clientverify(tc, auth->data) != 0) { + fprintf(stderr, "Client auth verify failed\n"); + return false; + } + return true; +} + +static bool +handle_cmd_data(void) +{ + struct ead_msg_cmd_data *cmd = EAD_ENC_DATA(msg, cmd_data); + int datalen = ead_decrypt_message(msg) - sizeof(struct ead_msg_cmd_data); + + if (datalen < 0) + return false; + + if (datalen > 0) { + write(1, cmd->data, datalen); + } + + return !!cmd->done; +} +static int +send_ping(void) +{ + msg->type = htonl(EAD_TYPE_PING); + msg->len = 0; + return send_packet(EAD_TYPE_PONG, handle_pong, (nid == 0xffff ? 0 : 1)); +} + +static int +send_username(void) +{ + msg->type = htonl(EAD_TYPE_SET_USERNAME); + msg->len = htonl(sizeof(struct ead_msg_user)); + strcpy(EAD_DATA(msg, user)->username, username); + return send_packet(EAD_TYPE_ACK_USERNAME, handle_none, 1); +} + +static int +get_prime(void) +{ + msg->type = htonl(EAD_TYPE_GET_PRIME); + msg->len = 0; + return send_packet(EAD_TYPE_PRIME, handle_prime, 1); +} + +static int +send_a(void) +{ + struct ead_msg_number *num = EAD_DATA(msg, number); + A = t_clientgenexp(tc); + msg->type = htonl(EAD_TYPE_SEND_A); + msg->len = htonl(sizeof(struct ead_msg_number) + A->len); + memcpy(num->data, A->data, A->len); + return send_packet(EAD_TYPE_SEND_B, handle_b, 1); +} + +static int +send_auth(void) +{ + struct ead_msg_auth *auth = EAD_DATA(msg, auth); + + prepare_password(); + t_clientpasswd(tc, password); + skey = t_clientgetkey(tc, &B); + if (!skey) + return 0; + + ead_set_key(skey); + msg->type = htonl(EAD_TYPE_SEND_AUTH); + msg->len = htonl(sizeof(struct ead_msg_auth)); + memcpy(auth->data, t_clientresponse(tc), sizeof(auth->data)); + return send_packet(EAD_TYPE_DONE_AUTH, handle_done_auth, 1); +} + +static int +send_command(const char *command) +{ + struct ead_msg_cmd *cmd = EAD_ENC_DATA(msg, cmd); + + msg->type = htonl(EAD_TYPE_SEND_CMD); + cmd->type = htons(EAD_CMD_NORMAL); + cmd->timeout = htons(10); + strncpy((char *)cmd->data, command, 1024); + ead_encrypt_message(msg, sizeof(struct ead_msg_cmd) + strlen(command) + 1); + return send_packet(EAD_TYPE_RESULT_CMD, handle_cmd_data, 1); +} + + +static int +usage(const char *prog) +{ + fprintf(stderr, "Usage: %s [-s <addr>] [-b <addr>] <node> <username>[:<password>] <command>\n" + "\n" + "\t-s <addr>: Set the server's source address to <addr>\n" + "\t-b <addr>: Set the broadcast address to <addr>\n" + "\t<node>: Node ID (4 digits hex)\n" + "\t<username>: Username to authenticate with\n" + "\n" + "\tPassing no arguments shows a list of active nodes on the network\n" + "\n", prog); + return -1; +} + + +int main(int argc, char **argv) +{ + int val = 1; + char *st = NULL; + const char *command = NULL; + const char *prog = argv[0]; + int ch; + + msg->magic = htonl(EAD_MAGIC); + msg->sid = 0; + + memset(&local, 0, sizeof(local)); + memset(&remote, 0, sizeof(remote)); + + remote.sin_family = AF_INET; + remote.sin_addr.s_addr = 0xffffffff; + remote.sin_port = htons(EAD_PORT); + + local.sin_family = AF_INET; + local.sin_addr.s_addr = INADDR_ANY; + local.sin_port = 0; + + while ((ch = getopt(argc, argv, "b:s:h")) != -1) { + switch(ch) { + case 's': + inet_aton(optarg, &serverip); + break; + case 'b': + inet_aton(optarg, &remote.sin_addr); + break; + case 'h': + return usage(prog); + } + } + argv += optind; + argc -= optind; + + switch(argc) { + case 3: + command = argv[2]; + /* fall through */ + case 2: + username = argv[1]; + st = strchr(username, ':'); + if (st) { + *st = 0; + st++; + strncpy(password, st, sizeof(password)); + password[sizeof(password) - 1] = 0; + /* hide command line password */ + memset(st, 0, strlen(st)); + } + /* fall through */ + case 1: + nid = strtoul(argv[0], &st, 16); + if (st && st[0] != 0) + return usage(prog); + /* fall through */ + case 0: + break; + default: + return usage(prog); + } + + msg->nid = htons(nid); + s = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); + if (s < 0) { + perror("socket"); + return -1; + } + + setsockopt(s, SOL_SOCKET, SO_BROADCAST, &val, sizeof(val)); + + if (bind(s, (struct sockaddr *)&local, sizeof(local)) < 0) { + perror("bind"); + return -1; + } + sockflags = fcntl(s, F_GETFL); + + if (!send_ping()) { + fprintf(stderr, "No devices found\n"); + return 1; + } + + if (nid == 0xffff) + return 0; + + if (!username || !password[0]) + return 0; + + if (!send_username()) { + fprintf(stderr, "Device did not accept user name\n"); + return 1; + } + timeout = EAD_TIMEOUT_LONG; + if (!get_prime()) { + fprintf(stderr, "Failed to get user password info\n"); + return 1; + } + if (!send_a()) { + fprintf(stderr, "Failed to send local authentication data\n"); + return 1; + } + if (!send_auth()) { + fprintf(stderr, "Authentication failed\n"); + return 1; + } + if (!command) { + fprintf(stderr, "Authentication succesful\n"); + return 0; + } + if (!send_command(command)) { + fprintf(stderr, "Command failed\n"); + return 1; + } + + return 0; +} diff --git a/package/network/services/ead/src/ead-crypt.c b/package/network/services/ead/src/ead-crypt.c new file mode 100644 index 0000000000..03721721d9 --- /dev/null +++ b/package/network/services/ead/src/ead-crypt.c @@ -0,0 +1,179 @@ +/* + * Copyright (C) 2008 Felix Fietkau <nbd@openwrt.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <stddef.h> +#include <stdint.h> +#include <stdlib.h> +#include <stdbool.h> +#include <string.h> +#include <unistd.h> +#include <stdio.h> +#include "ead.h" + +#include "sha1.c" +#include "aes.c" + +#if EAD_DEBUGLEVEL >= 1 +#define DEBUG(n, format, ...) do { \ + if (EAD_DEBUGLEVEL >= n) \ + fprintf(stderr, format, ##__VA_ARGS__); \ +} while (0); + +#else +#define DEBUG(n, format, ...) do {} while(0) +#endif + + +static uint32_t aes_enc_ctx[AES_PRIV_SIZE]; +static uint32_t aes_dec_ctx[AES_PRIV_SIZE]; +static uint32_t ead_rx_iv; +static uint32_t ead_tx_iv; +static uint32_t ivofs_vec; +static unsigned int ivofs_idx = 0; +static uint32_t W[80]; /* work space for sha1 */ + +#define EAD_ENC_PAD 64 + +void +ead_set_key(unsigned char *skey) +{ + uint32_t *ivp = (uint32_t *)skey; + + memset(aes_enc_ctx, 0, sizeof(aes_enc_ctx)); + memset(aes_dec_ctx, 0, sizeof(aes_dec_ctx)); + + /* first 32 bytes of skey are used as aes key for + * encryption and decryption */ + rijndaelKeySetupEnc(aes_enc_ctx, skey); + rijndaelKeySetupDec(aes_dec_ctx, skey); + + /* the following bytes are used as initialization vector for messages + * (highest byte cleared to avoid overflow) */ + ivp += 8; + ead_rx_iv = ntohl(*ivp) & 0x00ffffff; + ead_tx_iv = ead_rx_iv; + + /* the last bytes are used to feed the random iv increment */ + ivp++; + ivofs_vec = *ivp; +} + + +static bool +ead_check_rx_iv(uint32_t iv) +{ + if (iv <= ead_rx_iv) + return false; + + if (iv > ead_rx_iv + EAD_MAX_IV_INCR) + return false; + + ead_rx_iv = iv; + return true; +} + + +static uint32_t +ead_get_tx_iv(void) +{ + unsigned int ofs; + + ofs = 1 + ((ivofs_vec >> 2 * ivofs_idx) & 0x3); + ivofs_idx = (ivofs_idx + 1) % 16; + ead_tx_iv += ofs; + + return ead_tx_iv; +} + +static void +ead_hash_message(struct ead_msg_encrypted *enc, uint32_t *hash, int len) +{ + unsigned char *data = (unsigned char *) enc; + + /* hash the packet with the stored hash part initialized to zero */ + sha_init(hash); + memset(enc->hash, 0, sizeof(enc->hash)); + while (len > 0) { + sha_transform(hash, data, W); + len -= 64; + data += 64; + } +} + +void +ead_encrypt_message(struct ead_msg *msg, unsigned int len) +{ + struct ead_msg_encrypted *enc = EAD_DATA(msg, enc); + unsigned char *data = (unsigned char *) enc; + uint32_t hash[5]; + int enclen, i; + + len += sizeof(struct ead_msg_encrypted); + enc->pad = (EAD_ENC_PAD - (len % EAD_ENC_PAD)) % EAD_ENC_PAD; + enclen = len + enc->pad; + msg->len = htonl(enclen); + enc->iv = htonl(ead_get_tx_iv()); + + ead_hash_message(enc, hash, enclen); + for (i = 0; i < 5; i++) + enc->hash[i] = htonl(hash[i]); + DEBUG(2, "SHA1 generate (0x%08x), len=%d\n", enc->hash[0], enclen); + + while (enclen > 0) { + rijndaelEncrypt(aes_enc_ctx, data, data); + data += 16; + enclen -= 16; + } +} + +int +ead_decrypt_message(struct ead_msg *msg) +{ + struct ead_msg_encrypted *enc = EAD_DATA(msg, enc); + unsigned char *data = (unsigned char *) enc; + uint32_t hash_old[5], hash_new[5]; + int len = ntohl(msg->len); + int i, enclen = len; + + if (!len || (len % EAD_ENC_PAD > 0)) + return 0; + + while (len > 0) { + rijndaelDecrypt(aes_dec_ctx, data, data); + data += 16; + len -= 16; + } + + data = (unsigned char *) enc; + + if (enc->pad >= EAD_ENC_PAD) { + DEBUG(2, "Invalid padding length\n"); + return 0; + } + + if (!ead_check_rx_iv(ntohl(enc->iv))) { + DEBUG(2, "RX IV mismatch (0x%08x <> 0x%08x)\n", ead_rx_iv, ntohl(enc->iv)); + return 0; + } + + for (i = 0; i < 5; i++) + hash_old[i] = ntohl(enc->hash[i]); + ead_hash_message(enc, hash_new, enclen); + if (memcmp(hash_old, hash_new, sizeof(hash_old)) != 0) { + DEBUG(2, "SHA1 mismatch (0x%08x != 0x%08x), len=%d\n", hash_old[0], hash_new[0], enclen); + return 0; + } + + enclen -= enc->pad + sizeof(struct ead_msg_encrypted); + return enclen; +} diff --git a/package/network/services/ead/src/ead-crypt.h b/package/network/services/ead/src/ead-crypt.h new file mode 100644 index 0000000000..831ec8a280 --- /dev/null +++ b/package/network/services/ead/src/ead-crypt.h @@ -0,0 +1,21 @@ +/* + * Copyright (C) 2008 Felix Fietkau <nbd@openwrt.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef __EAD_CRYPT_H +#define __EAD_CRYPT_H + +extern void ead_set_key(unsigned char *skey); +extern void ead_encrypt_message(struct ead_msg *msg, unsigned int len); +extern int ead_decrypt_message(struct ead_msg *msg); + +#endif diff --git a/package/network/services/ead/src/ead-pcap.h b/package/network/services/ead/src/ead-pcap.h new file mode 100644 index 0000000000..0652ab48fd --- /dev/null +++ b/package/network/services/ead/src/ead-pcap.h @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2001-2003, Adam Dunkels. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior + * written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS + * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE + * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * This file was part of the uIP TCP/IP stack. + * + */ +#ifndef __EAD_PCAP_H +#define __EAD_PCAP_H + +#include <net/ethernet.h> +#include <stdint.h> +#include "ead.h" + +typedef uint8_t u8_t; +typedef uint16_t u16_t; + +/* The UDP and IP headers. */ +struct ead_packet { + struct ether_header eh; + /* IP header. */ + u8_t vhl, + tos, + len[2], + ipid[2], + ipoffset[2], + ttl, + proto; + u16_t ipchksum; + u16_t srcipaddr[2], + destipaddr[2]; + + /* UDP header. */ + u16_t srcport, + destport; + u16_t udplen; + u16_t udpchksum; + + struct ead_msg msg; +} __attribute__((packed)); + +#define UIP_PROTO_UDP 17 +#define UIP_IPH_LEN 20 /* Size of IP header */ +#define UIP_UDPH_LEN 8 /* Size of UDP header */ +#define UIP_IPUDPH_LEN (UIP_UDPH_LEN + UIP_IPH_LEN) + +#endif diff --git a/package/network/services/ead/src/ead.c b/package/network/services/ead/src/ead.c new file mode 100644 index 0000000000..36235207bc --- /dev/null +++ b/package/network/services/ead/src/ead.c @@ -0,0 +1,991 @@ +/* + * Emergency Access Daemon + * Copyright (C) 2008 Felix Fietkau <nbd@openwrt.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <sys/types.h> +#include <sys/time.h> +#include <sys/select.h> +#include <stdio.h> +#include <stddef.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <stdbool.h> +#include <fcntl.h> +#include <signal.h> +#include <pcap.h> +#include <pcap-bpf.h> +#include <t_pwd.h> +#include <t_read.h> +#include <t_sha.h> +#include <t_defines.h> +#include <t_server.h> + +#include "list.h" +#include "ead.h" +#include "ead-pcap.h" +#include "ead-crypt.h" + +#include "filter.c" + +#ifdef linux +#include "libbridge_init.c" +#endif + +#ifdef linux +#include <linux/if_packet.h> +#endif + +#define PASSWD_FILE "/etc/passwd" + +#ifndef DEFAULT_IFNAME +#define DEFAULT_IFNAME "eth0" +#endif + +#ifndef DEFAULT_DEVNAME +#define DEFAULT_DEVNAME "Unknown" +#endif + +#define PCAP_MRU 1600 +#define PCAP_TIMEOUT 200 + +#if EAD_DEBUGLEVEL >= 1 +#define DEBUG(n, format, ...) do { \ + if (EAD_DEBUGLEVEL >= n) \ + fprintf(stderr, format, ##__VA_ARGS__); \ +} while (0); + +#else +#define DEBUG(n, format, ...) do {} while(0) +#endif + +struct ead_instance { + struct list_head list; + char ifname[16]; + int pid; + char id; +#ifdef linux + char bridge[16]; + bool br_check; +#endif +}; + +static char ethmac[6] = "\x00\x13\x37\x00\x00\x00"; /* last 3 bytes will be randomized */ +static pcap_t *pcap_fp = NULL; +static pcap_t *pcap_fp_rx = NULL; +static char pktbuf_b[PCAP_MRU]; +static struct ead_packet *pktbuf = (struct ead_packet *)pktbuf_b; +static u16_t nid = 0xffff; /* node id */ +static char username[32] = ""; +static int state = EAD_TYPE_SET_USERNAME; +static const char *passwd_file = PASSWD_FILE; +static const char password[MAXPARAMLEN]; +static bool child_pending = false; + +static unsigned char abuf[MAXPARAMLEN + 1]; +static unsigned char pwbuf[MAXPARAMLEN]; +static unsigned char saltbuf[MAXSALTLEN]; +static unsigned char pw_saltbuf[MAXSALTLEN]; +static struct list_head instances; +static const char *dev_name = DEFAULT_DEVNAME; +static bool nonfork = false; +static struct ead_instance *instance = NULL; + +static struct t_pwent tpe = { + .name = username, + .index = 1, + .password.data = pwbuf, + .password.len = 0, + .salt.data = saltbuf, + .salt.len = 0, +}; +struct t_confent *tce = NULL; +static struct t_server *ts = NULL; +static struct t_num A, *B = NULL; +unsigned char *skey; + +static void +set_recv_type(pcap_t *p, bool rx) +{ +#ifdef PACKET_RECV_TYPE + struct sockaddr_ll sll; + struct ifreq ifr; + int ifindex, mask; + int fd, ret; + + fd = pcap_get_selectable_fd(p); + if (fd < 0) + return; + + if (rx) + mask = 1 << PACKET_BROADCAST; + else + mask = 0; + + ret = setsockopt(fd, SOL_PACKET, PACKET_RECV_TYPE, &mask, sizeof(mask)); +#endif +} + + +static pcap_t * +ead_open_pcap(const char *ifname, char *errbuf, bool rx) +{ + pcap_t *p; + + p = pcap_create(ifname, errbuf); + if (p == NULL) + goto out; + + pcap_set_snaplen(p, PCAP_MRU); + pcap_set_promisc(p, rx); + pcap_set_timeout(p, PCAP_TIMEOUT); +#ifdef HAS_PROTO_EXTENSION + pcap_set_protocol(p, (rx ? htons(ETH_P_IP) : 0)); +#endif + pcap_set_buffer_size(p, (rx ? 10 : 1) * PCAP_MRU); + pcap_activate(p); + set_recv_type(p, rx); +out: + return p; +} + +static void +get_random_bytes(void *ptr, int len) +{ + int fd; + + fd = open("/dev/urandom", O_RDONLY); + if (fd < 0) { + perror("open"); + exit(1); + } + read(fd, ptr, len); + close(fd); +} + +static bool +prepare_password(void) +{ + static char lbuf[1024]; + unsigned char dig[SHA_DIGESTSIZE]; + BigInteger x, v, n, g; + SHA1_CTX ctxt; + int ulen = strlen(username); + FILE *f; + + lbuf[sizeof(lbuf) - 1] = 0; + + f = fopen(passwd_file, "r"); + if (!f) + return false; + + while (fgets(lbuf, sizeof(lbuf) - 1, f) != NULL) { + char *str, *s2; + + if (strncmp(lbuf, username, ulen) != 0) + continue; + + if (lbuf[ulen] != ':') + continue; + + str = &lbuf[ulen + 1]; + + if (strncmp(str, "$1$", 3) != 0) + continue; + + s2 = strchr(str + 3, '$'); + if (!s2) + continue; + + if (s2 - str >= MAXSALTLEN) + continue; + + strncpy((char *) pw_saltbuf, str, s2 - str); + pw_saltbuf[s2 - str] = 0; + + s2 = strchr(s2, ':'); + if (!s2) + continue; + + *s2 = 0; + if (s2 - str >= MAXPARAMLEN) + continue; + + strncpy((char *)password, str, MAXPARAMLEN); + fclose(f); + goto hash_password; + } + + /* not found */ + fclose(f); + return false; + +hash_password: + tce = gettcid(tpe.index); + do { + t_random(tpe.password.data, SALTLEN); + } while (memcmp(saltbuf, (char *)dig, sizeof(saltbuf)) == 0); + if (saltbuf[0] == 0) + saltbuf[0] = 0xff; + + n = BigIntegerFromBytes(tce->modulus.data, tce->modulus.len); + g = BigIntegerFromBytes(tce->generator.data, tce->generator.len); + v = BigIntegerFromInt(0); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, (unsigned char *) username, strlen(username)); + SHA1Update(&ctxt, (unsigned char *) ":", 1); + SHA1Update(&ctxt, (unsigned char *) password, strlen(password)); + SHA1Final(dig, &ctxt); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, saltbuf, tpe.salt.len); + SHA1Update(&ctxt, dig, sizeof(dig)); + SHA1Final(dig, &ctxt); + + /* x = H(s, H(u, ':', p)) */ + x = BigIntegerFromBytes(dig, sizeof(dig)); + + BigIntegerModExp(v, g, x, n); + tpe.password.len = BigIntegerToBytes(v, (unsigned char *)pwbuf); + + BigIntegerFree(v); + BigIntegerFree(x); + BigIntegerFree(g); + BigIntegerFree(n); + return true; +} + +static u16_t +chksum(u16_t sum, const u8_t *data, u16_t len) +{ + u16_t t; + const u8_t *dataptr; + const u8_t *last_byte; + + dataptr = data; + last_byte = data + len - 1; + + while(dataptr < last_byte) { /* At least two more bytes */ + t = (dataptr[0] << 8) + dataptr[1]; + sum += t; + if(sum < t) { + sum++; /* carry */ + } + dataptr += 2; + } + + if(dataptr == last_byte) { + t = (dataptr[0] << 8) + 0; + sum += t; + if(sum < t) { + sum++; /* carry */ + } + } + + /* Return sum in host byte order. */ + return sum; +} + +static void +ead_send_packet_clone(struct ead_packet *pkt) +{ + u16_t len, sum; + + memcpy(pktbuf, pkt, offsetof(struct ead_packet, msg)); + memcpy(pktbuf->eh.ether_shost, ethmac, 6); + memcpy(pktbuf->eh.ether_dhost, pkt->eh.ether_shost, 6); + + /* ip header */ + len = sizeof(struct ead_packet) - sizeof(struct ether_header) + ntohl(pktbuf->msg.len); + pktbuf->len[0] = len >> 8; + pktbuf->len[1] = len & 0xff; + memcpy(pktbuf->srcipaddr, &pkt->msg.ip, 4); + memcpy(pktbuf->destipaddr, pkt->srcipaddr, 4); + + /* ip checksum */ + pktbuf->ipchksum = 0; + sum = chksum(0, (void *) &pktbuf->vhl, UIP_IPH_LEN); + if (sum == 0) + sum = 0xffff; + pktbuf->ipchksum = htons(~sum); + + /* udp header */ + pktbuf->srcport = pkt->destport; + pktbuf->destport = pkt->srcport; + + /* udp checksum */ + len -= UIP_IPH_LEN; + pktbuf->udplen = htons(len); + pktbuf->udpchksum = 0; + sum = len + UIP_PROTO_UDP; + sum = chksum(sum, (void *) &pktbuf->srcipaddr[0], 8); /* src, dest ip */ + sum = chksum(sum, (void *) &pktbuf->srcport, len); + if (sum == 0) + sum = 0xffff; + pktbuf->udpchksum = htons(~sum); + pcap_sendpacket(pcap_fp, (void *) pktbuf, sizeof(struct ead_packet) + ntohl(pktbuf->msg.len)); +} + +static void +set_state(int nstate) +{ + if (state == nstate) + return; + + if (nstate < state) { + if ((nstate < EAD_TYPE_GET_PRIME) && + (state >= EAD_TYPE_GET_PRIME)) { + t_serverclose(ts); + ts = NULL; + } + goto done; + } + + switch(state) { + case EAD_TYPE_SET_USERNAME: + if (!prepare_password()) + goto error; + ts = t_serveropenraw(&tpe, tce); + if (!ts) + goto error; + break; + case EAD_TYPE_GET_PRIME: + B = t_servergenexp(ts); + break; + case EAD_TYPE_SEND_A: + skey = t_servergetkey(ts, &A); + if (!skey) + goto error; + + ead_set_key(skey); + break; + } +done: + state = nstate; +error: + return; +} + +static bool +handle_ping(struct ead_packet *pkt, int len, int *nstate) +{ + struct ead_msg *msg = &pktbuf->msg; + struct ead_msg_pong *pong = EAD_DATA(msg, pong); + int slen; + + slen = strlen(dev_name); + if (slen > 1024) + slen = 1024; + + msg->len = htonl(sizeof(struct ead_msg_pong) + slen); + strncpy(pong->name, dev_name, slen); + pong->name[slen] = 0; + pong->auth_type = htons(EAD_AUTH_MD5); + + return true; +} + +static bool +handle_set_username(struct ead_packet *pkt, int len, int *nstate) +{ + struct ead_msg *msg = &pkt->msg; + struct ead_msg_user *user = EAD_DATA(msg, user); + + set_state(EAD_TYPE_SET_USERNAME); /* clear old state */ + strncpy(username, user->username, sizeof(username)); + username[sizeof(username) - 1] = 0; + + msg = &pktbuf->msg; + msg->len = 0; + + *nstate = EAD_TYPE_GET_PRIME; + return true; +} + +static bool +handle_get_prime(struct ead_packet *pkt, int len, int *nstate) +{ + struct ead_msg *msg = &pktbuf->msg; + struct ead_msg_salt *salt = EAD_DATA(msg, salt); + + msg->len = htonl(sizeof(struct ead_msg_salt)); + salt->prime = tce->index - 1; + salt->len = ts->s.len; + memcpy(salt->salt, ts->s.data, ts->s.len); + memcpy(salt->ext_salt, pw_saltbuf, MAXSALTLEN); + + *nstate = EAD_TYPE_SEND_A; + return true; +} + +static bool +handle_send_a(struct ead_packet *pkt, int len, int *nstate) +{ + struct ead_msg *msg = &pkt->msg; + struct ead_msg_number *number = EAD_DATA(msg, number); + len = ntohl(msg->len) - sizeof(struct ead_msg_number); + + if (len > MAXPARAMLEN + 1) + return false; + + A.len = len; + A.data = abuf; + memcpy(A.data, number->data, len); + + msg = &pktbuf->msg; + number = EAD_DATA(msg, number); + msg->len = htonl(sizeof(struct ead_msg_number) + B->len); + memcpy(number->data, B->data, B->len); + + *nstate = EAD_TYPE_SEND_AUTH; + return true; +} + +static bool +handle_send_auth(struct ead_packet *pkt, int len, int *nstate) +{ + struct ead_msg *msg = &pkt->msg; + struct ead_msg_auth *auth = EAD_DATA(msg, auth); + + if (t_serververify(ts, auth->data) != 0) { + DEBUG(2, "Client authentication failed\n"); + *nstate = EAD_TYPE_SET_USERNAME; + return false; + } + + msg = &pktbuf->msg; + auth = EAD_DATA(msg, auth); + msg->len = htonl(sizeof(struct ead_msg_auth)); + + DEBUG(2, "Client authentication successful\n"); + memcpy(auth->data, t_serverresponse(ts), sizeof(auth->data)); + + *nstate = EAD_TYPE_SEND_CMD; + return true; +} + +static bool +handle_send_cmd(struct ead_packet *pkt, int len, int *nstate) +{ + struct ead_msg *msg = &pkt->msg; + struct ead_msg_cmd *cmd = EAD_ENC_DATA(msg, cmd); + struct ead_msg_cmd_data *cmddata; + struct timeval tv, to, tn; + int pfd[2], fd; + fd_set fds; + pid_t pid; + bool stream = false; + int timeout; + int type; + int datalen; + + datalen = ead_decrypt_message(msg) - sizeof(struct ead_msg_cmd); + if (datalen <= 0) + return false; + + type = ntohs(cmd->type); + timeout = ntohs(cmd->timeout); + + FD_ZERO(&fds); + cmd->data[datalen] = 0; + switch(type) { + case EAD_CMD_NORMAL: + if (pipe(pfd) < 0) + return false; + + fcntl(pfd[0], F_SETFL, O_NONBLOCK | fcntl(pfd[0], F_GETFL)); + child_pending = true; + pid = fork(); + if (pid == 0) { + close(pfd[0]); + fd = open("/dev/null", O_RDWR); + if (fd > 0) { + dup2(fd, 0); + dup2(pfd[1], 1); + dup2(pfd[1], 2); + } + system((char *)cmd->data); + exit(0); + } else if (pid > 0) { + close(pfd[1]); + if (!timeout) + timeout = EAD_CMD_TIMEOUT; + + stream = true; + break; + } + return false; + case EAD_CMD_BACKGROUND: + pid = fork(); + if (pid == 0) { + /* close stdin, stdout, stderr, replace with fd to /dev/null */ + fd = open("/dev/null", O_RDWR); + if (fd > 0) { + dup2(fd, 0); + dup2(fd, 1); + dup2(fd, 2); + } + system((char *)cmd->data); + exit(0); + } else if (pid > 0) { + break; + } + return false; + default: + return false; + } + + msg = &pktbuf->msg; + cmddata = EAD_ENC_DATA(msg, cmd_data); + + if (stream) { + int nfds, bytes; + + /* send keepalive packets every 200 ms so that the client doesn't timeout */ + gettimeofday(&to, NULL); + memcpy(&tn, &to, sizeof(tn)); + tv.tv_usec = PCAP_TIMEOUT * 1000; + tv.tv_sec = 0; + do { + cmddata->done = 0; + FD_SET(pfd[0], &fds); + nfds = select(pfd[0] + 1, &fds, NULL, NULL, &tv); + bytes = 0; + if (nfds > 0) { + bytes = read(pfd[0], cmddata->data, 1024); + if (bytes < 0) + bytes = 0; + } + if (!bytes && !child_pending) + break; + DEBUG(3, "Sending %d bytes of console data, type=%d, timeout=%d\n", bytes, ntohl(msg->type), timeout); + ead_encrypt_message(msg, sizeof(struct ead_msg_cmd_data) + bytes); + ead_send_packet_clone(pkt); + gettimeofday(&tn, NULL); + } while (tn.tv_sec < to.tv_sec + timeout); + if (child_pending) { + kill(pid, SIGKILL); + return false; + } + } + cmddata->done = 1; + ead_encrypt_message(msg, sizeof(struct ead_msg_cmd_data)); + + return true; +} + + + +static void +parse_message(struct ead_packet *pkt, int len) +{ + bool (*handler)(struct ead_packet *pkt, int len, int *nstate); + int min_len = sizeof(struct ead_packet); + int nstate = state; + int type = ntohl(pkt->msg.type); + + if ((type >= EAD_TYPE_GET_PRIME) && + (state != type)) + return; + + if ((type != EAD_TYPE_PING) && + ((ntohs(pkt->msg.sid) & EAD_INSTANCE_MASK) >> + EAD_INSTANCE_SHIFT) != instance->id) + return; + + switch(type) { + case EAD_TYPE_PING: + handler = handle_ping; + break; + case EAD_TYPE_SET_USERNAME: + handler = handle_set_username; + min_len += sizeof(struct ead_msg_user); + break; + case EAD_TYPE_GET_PRIME: + handler = handle_get_prime; + break; + case EAD_TYPE_SEND_A: + handler = handle_send_a; + min_len += sizeof(struct ead_msg_number); + break; + case EAD_TYPE_SEND_AUTH: + handler = handle_send_auth; + min_len += sizeof(struct ead_msg_auth); + break; + case EAD_TYPE_SEND_CMD: + handler = handle_send_cmd; + min_len += sizeof(struct ead_msg_cmd) + sizeof(struct ead_msg_encrypted); + break; + default: + return; + } + + if (len < min_len) { + DEBUG(2, "discarding packet: message too small\n"); + return; + } + + pktbuf->msg.magic = htonl(EAD_MAGIC); + pktbuf->msg.type = htonl(type + 1); + pktbuf->msg.nid = htons(nid); + pktbuf->msg.sid = pkt->msg.sid; + pktbuf->msg.len = 0; + + if (handler(pkt, len, &nstate)) { + DEBUG(2, "sending response to packet type %d: %d\n", type + 1, ntohl(pktbuf->msg.len)); + /* format response packet */ + ead_send_packet_clone(pkt); + } + set_state(nstate); +} + +static void +handle_packet(u_char *user, const struct pcap_pkthdr *h, const u_char *bytes) +{ + struct ead_packet *pkt = (struct ead_packet *) bytes; + + if (h->len < sizeof(struct ead_packet)) + return; + + if (pkt->eh.ether_type != htons(ETHERTYPE_IP)) + return; + + if (memcmp(pkt->eh.ether_dhost, "\xff\xff\xff\xff\xff\xff", 6) != 0) + return; + + if (pkt->proto != UIP_PROTO_UDP) + return; + + if (pkt->destport != htons(EAD_PORT)) + return; + + if (pkt->msg.magic != htonl(EAD_MAGIC)) + return; + + if (h->len < sizeof(struct ead_packet) + ntohl(pkt->msg.len)) + return; + + if ((pkt->msg.nid != 0xffff) && + (pkt->msg.nid != htons(nid))) + return; + + parse_message(pkt, h->len); +} + +static void +ead_pcap_reopen(bool first) +{ + static char errbuf[PCAP_ERRBUF_SIZE] = ""; + + if (pcap_fp_rx && (pcap_fp_rx != pcap_fp)) + pcap_close(pcap_fp_rx); + + if (pcap_fp) + pcap_close(pcap_fp); + + pcap_fp_rx = NULL; + do { +#ifdef linux + if (instance->bridge[0]) { + pcap_fp_rx = ead_open_pcap(instance->bridge, errbuf, 1); + pcap_fp = ead_open_pcap(instance->ifname, errbuf, 0); + } else +#endif + { + pcap_fp = ead_open_pcap(instance->ifname, errbuf, 1); + } + + if (!pcap_fp_rx) + pcap_fp_rx = pcap_fp; + if (first && !pcap_fp) { + DEBUG(1, "WARNING: unable to open interface '%s'\n", instance->ifname); + first = false; + } + if (!pcap_fp) + sleep(1); + } while (!pcap_fp); + pcap_setfilter(pcap_fp_rx, &pktfilter); +} + + +static void +ead_pktloop(void) +{ + while (1) { + if (pcap_dispatch(pcap_fp_rx, 1, handle_packet, NULL) < 0) { + ead_pcap_reopen(false); + continue; + } + } +} + + +static int +usage(const char *prog) +{ + fprintf(stderr, "Usage: %s [<options>]\n" + "Options:\n" + "\t-B Run in background mode\n" + "\t-d <device> Set the device to listen on\n" + "\t-D <name> Set the name of the device visible to clients\n" + "\t-p <file> Set the password file for authenticating\n" + "\t-P <file> Write a pidfile\n" + "\n", prog); + return -1; +} + +static void +server_handle_sigchld(int sig) +{ + struct ead_instance *in; + struct list_head *p; + int pid = 0; + wait(&pid); + + list_for_each(p, &instances) { + in = list_entry(p, struct ead_instance, list); + if (pid != in->pid) + continue; + + in->pid = 0; + break; + } +} + +static void +instance_handle_sigchld(int sig) +{ + int pid = 0; + wait(&pid); + child_pending = false; +} + +static void +start_server(struct ead_instance *i) +{ + if (!nonfork) { + i->pid = fork(); + if (i->pid != 0) { + if (i->pid < 0) + i->pid = 0; + return; + } + } + + instance = i; + signal(SIGCHLD, instance_handle_sigchld); + ead_pcap_reopen(true); + ead_pktloop(); + pcap_close(pcap_fp); + if (pcap_fp_rx != pcap_fp) + pcap_close(pcap_fp_rx); + + exit(0); +} + + +static void +start_servers(bool restart) +{ + struct ead_instance *in; + struct list_head *p; + + list_for_each(p, &instances) { + in = list_entry(p, struct ead_instance, list); + if (in->pid > 0) + continue; + + sleep(1); + start_server(in); + } +} + +static void +stop_server(struct ead_instance *in, bool do_free) +{ + if (in->pid > 0) + kill(in->pid, SIGKILL); + in->pid = 0; + if (do_free) { + list_del(&in->list); + free(in); + } +} + +static void +server_handle_sigint(int sig) +{ + struct ead_instance *in; + struct list_head *p, *tmp; + + list_for_each_safe(p, tmp, &instances) { + in = list_entry(p, struct ead_instance, list); + stop_server(in, true); + } + exit(1); +} + +#ifdef linux +static int +check_bridge_port(const char *br, const char *port, void *arg) +{ + struct ead_instance *in; + struct list_head *p, *tmp; + + list_for_each(p, &instances) { + in = list_entry(p, struct ead_instance, list); + + if (strcmp(in->ifname, port) != 0) + continue; + + in->br_check = true; + if (strcmp(in->bridge, br) == 0) + break; + + strncpy(in->bridge, br, sizeof(in->bridge)); + DEBUG(2, "assigning port %s to bridge %s\n", in->ifname, in->bridge); + stop_server(in, false); + } + return 0; +} + +static int +check_bridge(const char *name, void *arg) +{ + br_foreach_port(name, check_bridge_port, arg); + return 0; +} +#endif + +static void +check_all_interfaces(void) +{ +#ifdef linux + struct ead_instance *in; + struct list_head *p, *tmp; + + br_foreach_bridge(check_bridge, NULL); + + /* look for interfaces that are no longer part of a bridge */ + list_for_each(p, &instances) { + in = list_entry(p, struct ead_instance, list); + + if (in->br_check) { + in->br_check = false; + } else if (in->bridge[0]) { + DEBUG(2, "removing port %s from bridge %s\n", in->ifname, in->bridge); + in->bridge[0] = 0; + stop_server(in, false); + } + } +#endif +} + + +int main(int argc, char **argv) +{ + struct ead_instance *in; + struct timeval tv; + const char *pidfile = NULL; + bool background = false; + int n_iface = 0; + int fd, ch; + + if (argc == 1) + return usage(argv[0]); + + INIT_LIST_HEAD(&instances); + while ((ch = getopt(argc, argv, "Bd:D:fhp:P:")) != -1) { + switch(ch) { + case 'B': + background = true; + break; + case 'f': + nonfork = true; + break; + case 'h': + return usage(argv[0]); + case 'd': + in = malloc(sizeof(struct ead_instance)); + memset(in, 0, sizeof(struct ead_instance)); + INIT_LIST_HEAD(&in->list); + strncpy(in->ifname, optarg, sizeof(in->ifname) - 1); + list_add(&in->list, &instances); + in->id = n_iface++; + break; + case 'D': + dev_name = optarg; + break; + case 'p': + passwd_file = optarg; + break; + case 'P': + pidfile = optarg; + break; + } + } + signal(SIGCHLD, server_handle_sigchld); + signal(SIGINT, server_handle_sigint); + signal(SIGTERM, server_handle_sigint); + signal(SIGKILL, server_handle_sigint); + + if (!n_iface) { + fprintf(stderr, "Error: ead needs at least one interface\n"); + return -1; + } + + if (background) { + if (fork() > 0) + exit(0); + + fd = open("/dev/null", O_RDWR); + dup2(fd, 0); + dup2(fd, 1); + dup2(fd, 2); + } + + if (pidfile) { + char pid[8]; + int len; + + unlink(pidfile); + fd = open(pidfile, O_CREAT|O_WRONLY|O_EXCL, 0644); + if (fd > 0) { + len = sprintf(pid, "%d\n", getpid()); + write(fd, pid, len); + close(fd); + } + } + + /* randomize the mac address */ + get_random_bytes(ethmac + 3, 3); + nid = *(((u16_t *) ethmac) + 2); + + start_servers(false); +#ifdef linux + br_init(); +#endif + tv.tv_sec = 1; + tv.tv_usec = 0; + while (1) { + check_all_interfaces(); + start_servers(true); + sleep(1); + } +#ifdef linux + br_shutdown(); +#endif + + return 0; +} diff --git a/package/network/services/ead/src/ead.h b/package/network/services/ead/src/ead.h new file mode 100644 index 0000000000..54505ce28c --- /dev/null +++ b/package/network/services/ead/src/ead.h @@ -0,0 +1,139 @@ +/* + * Copyright (C) 2008 Felix Fietkau <nbd@openwrt.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef __EAD_H +#define __EAD_H + +#define EAD_DEBUGLEVEL 1 + +#include <stdint.h> +#include <stddef.h> + +#ifndef MAXSALTLEN +#define MAXSALTLEN 32 +#endif + +#define EAD_PORT 56026UL +#define EAD_MAGIC 3671771902UL +#define EAD_CMD_TIMEOUT 10 + +#define EAD_MAX_IV_INCR 128 + +/* request/response types */ +/* response id == request id + 1 */ +enum ead_type { + EAD_TYPE_PING, + EAD_TYPE_PONG, + + EAD_TYPE_SET_USERNAME, + EAD_TYPE_ACK_USERNAME, + + EAD_TYPE_GET_PRIME, + EAD_TYPE_PRIME, + + EAD_TYPE_SEND_A, + EAD_TYPE_SEND_B, + + EAD_TYPE_SEND_AUTH, + EAD_TYPE_DONE_AUTH, + + EAD_TYPE_SEND_CMD, + EAD_TYPE_RESULT_CMD, + + EAD_TYPE_LAST +}; + +enum ead_auth_type { + EAD_AUTH_DEFAULT, + EAD_AUTH_MD5 +}; + +enum ead_cmd_type { + EAD_CMD_NORMAL, + EAD_CMD_BACKGROUND, + EAD_CMD_LAST +}; + +struct ead_msg_pong { + uint16_t auth_type; + char name[]; +} __attribute__((packed)); + +struct ead_msg_number { + uint8_t id; + unsigned char data[]; +} __attribute__((packed)); + +struct ead_msg_salt { + uint8_t prime; + uint8_t len; + unsigned char salt[MAXSALTLEN]; + unsigned char ext_salt[MAXSALTLEN]; +} __attribute__((packed)); + +struct ead_msg_user { + char username[32]; +} __attribute__((packed)); + +struct ead_msg_auth { + unsigned char data[20]; +} __attribute__((packed)); + +struct ead_msg_cmd { + uint8_t type; + uint16_t timeout; + unsigned char data[]; +} __attribute__((packed)); + +struct ead_msg_cmd_data { + uint8_t done; + unsigned char data[]; +} __attribute__((packed)); + +struct ead_msg_encrypted { + uint32_t hash[5]; + uint32_t iv; + uint8_t pad; + union { + struct ead_msg_cmd cmd; + struct ead_msg_cmd_data cmd_data; + } data[]; +} __attribute__((packed)); + + +#define EAD_DATA(_msg, _type) (&((_msg)->data[0]._type)) +#define EAD_ENC_DATA(_msg, _type) (&((_msg)->data[0].enc.data[0]._type)) + +/* for ead_msg::sid */ +#define EAD_INSTANCE_MASK 0xf000 +#define EAD_INSTANCE_SHIFT 12 + +struct ead_msg { + uint32_t magic; + uint32_t len; + uint32_t type; + uint16_t nid; /* node id */ + uint16_t sid; /* session id */ + uint32_t ip; /* source ip for responses from the server */ + union { + struct ead_msg_pong pong; + struct ead_msg_user user; + struct ead_msg_number number; + struct ead_msg_auth auth; + struct ead_msg_salt salt; + struct ead_msg_encrypted enc; + } data[]; +} __attribute__((packed)); + + +#endif diff --git a/package/network/services/ead/src/filter.c b/package/network/services/ead/src/filter.c new file mode 100644 index 0000000000..0759dc330f --- /dev/null +++ b/package/network/services/ead/src/filter.c @@ -0,0 +1,25 @@ +/* precompiled expression: udp and dst port 56026 */ + +static struct bpf_insn pktfilter_insns[] = { + { .code = 0x0028, .jt = 0x00, .jf = 0x00, .k = 0x0000000c }, + { .code = 0x0015, .jt = 0x00, .jf = 0x04, .k = 0x000086dd }, + { .code = 0x0030, .jt = 0x00, .jf = 0x00, .k = 0x00000014 }, + { .code = 0x0015, .jt = 0x00, .jf = 0x0b, .k = 0x00000011 }, + { .code = 0x0028, .jt = 0x00, .jf = 0x00, .k = 0x00000038 }, + { .code = 0x0015, .jt = 0x08, .jf = 0x09, .k = 0x0000dada }, + { .code = 0x0015, .jt = 0x00, .jf = 0x08, .k = 0x00000800 }, + { .code = 0x0030, .jt = 0x00, .jf = 0x00, .k = 0x00000017 }, + { .code = 0x0015, .jt = 0x00, .jf = 0x06, .k = 0x00000011 }, + { .code = 0x0028, .jt = 0x00, .jf = 0x00, .k = 0x00000014 }, + { .code = 0x0045, .jt = 0x04, .jf = 0x00, .k = 0x00001fff }, + { .code = 0x00b1, .jt = 0x00, .jf = 0x00, .k = 0x0000000e }, + { .code = 0x0048, .jt = 0x00, .jf = 0x00, .k = 0x00000010 }, + { .code = 0x0015, .jt = 0x00, .jf = 0x01, .k = 0x0000dada }, + { .code = 0x0006, .jt = 0x00, .jf = 0x00, .k = 0x000005dc }, + { .code = 0x0006, .jt = 0x00, .jf = 0x00, .k = 0x00000000 }, +}; + +static struct bpf_program pktfilter = { + .bf_len = 16, + .bf_insns = pktfilter_insns, +}; diff --git a/package/network/services/ead/src/libbridge.h b/package/network/services/ead/src/libbridge.h new file mode 100644 index 0000000000..6b70e46f6d --- /dev/null +++ b/package/network/services/ead/src/libbridge.h @@ -0,0 +1,84 @@ +/* + * Copyright (C) 2000 Lennert Buytenhek + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + */ + +#ifndef _LIBBRIDGE_H +#define _LIBBRIDGE_H + +#include <sys/socket.h> +#include <linux/if.h> +#include <linux/if_bridge.h> + +/* defined in net/if.h but that conflicts with linux/if.h... */ +extern unsigned int if_nametoindex (const char *__ifname); +extern char *if_indextoname (unsigned int __ifindex, char *__ifname); + +struct bridge_id +{ + unsigned char prio[2]; + unsigned char addr[6]; +}; + +struct bridge_info +{ + struct bridge_id designated_root; + struct bridge_id bridge_id; + unsigned root_path_cost; + struct timeval max_age; + struct timeval hello_time; + struct timeval forward_delay; + struct timeval bridge_max_age; + struct timeval bridge_hello_time; + struct timeval bridge_forward_delay; + u_int16_t root_port; + unsigned char stp_enabled; + unsigned char topology_change; + unsigned char topology_change_detected; + struct timeval ageing_time; + struct timeval hello_timer_value; + struct timeval tcn_timer_value; + struct timeval topology_change_timer_value; + struct timeval gc_timer_value; +}; + +struct fdb_entry +{ + u_int8_t mac_addr[6]; + u_int16_t port_no; + unsigned char is_local; + struct timeval ageing_timer_value; +}; + +struct port_info +{ + unsigned port_no; + struct bridge_id designated_root; + struct bridge_id designated_bridge; + u_int16_t port_id; + u_int16_t designated_port; + u_int8_t priority; + unsigned char top_change_ack; + unsigned char config_pending; + unsigned char state; + unsigned path_cost; + unsigned designated_cost; + struct timeval message_age_timer_value; + struct timeval forward_delay_timer_value; + struct timeval hold_timer_value; +}; + +#endif diff --git a/package/network/services/ead/src/libbridge_init.c b/package/network/services/ead/src/libbridge_init.c new file mode 100644 index 0000000000..36d0eb9b8e --- /dev/null +++ b/package/network/services/ead/src/libbridge_init.c @@ -0,0 +1,208 @@ +/* + * Copyright (C) 2000 Lennert Buytenhek + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + */ + +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <errno.h> +#include <string.h> +#include <dirent.h> +#include <sys/types.h> +#include <sys/stat.h> + +#include "libbridge.h" +#include "libbridge_private.h" + +int br_socket_fd = -1; + +static int br_init(void) +{ + if ((br_socket_fd = socket(AF_LOCAL, SOCK_STREAM, 0)) < 0) + return errno; + return 0; +} + +static void br_shutdown(void) +{ + close(br_socket_fd); + br_socket_fd = -1; +} + +/* If /sys/class/net/XXX/bridge exists then it must be a bridge */ +static int isbridge(const struct dirent *entry) +{ + char path[SYSFS_PATH_MAX]; + struct stat st; + + snprintf(path, SYSFS_PATH_MAX, SYSFS_CLASS_NET "%s/bridge", entry->d_name); + return stat(path, &st) == 0 && S_ISDIR(st.st_mode); +} + +/* + * New interface uses sysfs to find bridges + */ +static int new_foreach_bridge(int (*iterator)(const char *name, void *), + void *arg) +{ + struct dirent **namelist; + int i, count = 0; + + count = scandir(SYSFS_CLASS_NET, &namelist, isbridge, alphasort); + if (count < 0) + return -1; + + for (i = 0; i < count; i++) { + if (iterator(namelist[i]->d_name, arg)) + break; + } + + for (i = 0; i < count; i++) + free(namelist[i]); + free(namelist); + + return count; +} + +/* + * Old interface uses ioctl + */ +static int old_foreach_bridge(int (*iterator)(const char *, void *), + void *iarg) +{ + int i, ret=0, num; + char ifname[IFNAMSIZ]; + int ifindices[MAX_BRIDGES]; + unsigned long args[3] = { BRCTL_GET_BRIDGES, + (unsigned long)ifindices, MAX_BRIDGES }; + + num = ioctl(br_socket_fd, SIOCGIFBR, args); + if (num < 0) { + dprintf("Get bridge indices failed: %s\n", + strerror(errno)); + return -errno; + } + + for (i = 0; i < num; i++) { + if (!if_indextoname(ifindices[i], ifname)) { + dprintf("get find name for ifindex %d\n", + ifindices[i]); + return -errno; + } + + ++ret; + if(iterator(ifname, iarg)) + break; + } + + return ret; + +} + +/* + * Go over all bridges and call iterator function. + * if iterator returns non-zero then stop. + */ +static int br_foreach_bridge(int (*iterator)(const char *, void *), + void *arg) +{ + int ret; + + ret = new_foreach_bridge(iterator, arg); + if (ret <= 0) + ret = old_foreach_bridge(iterator, arg); + + return ret; +} + +/* + * Only used if sysfs is not available. + */ +static int old_foreach_port(const char *brname, + int (*iterator)(const char *br, const char *port, + void *arg), + void *arg) +{ + int i, err, count; + struct ifreq ifr; + char ifname[IFNAMSIZ]; + int ifindices[MAX_PORTS]; + unsigned long args[4] = { BRCTL_GET_PORT_LIST, + (unsigned long)ifindices, MAX_PORTS, 0 }; + + memset(ifindices, 0, sizeof(ifindices)); + strncpy(ifr.ifr_name, brname, IFNAMSIZ); + ifr.ifr_data = (char *) &args; + + err = ioctl(br_socket_fd, SIOCDEVPRIVATE, &ifr); + if (err < 0) { + dprintf("list ports for bridge:'%s' failed: %s\n", + brname, strerror(errno)); + return -errno; + } + + count = 0; + for (i = 0; i < MAX_PORTS; i++) { + if (!ifindices[i]) + continue; + + if (!if_indextoname(ifindices[i], ifname)) { + dprintf("can't find name for ifindex:%d\n", + ifindices[i]); + continue; + } + + ++count; + if (iterator(brname, ifname, arg)) + break; + } + + return count; +} + +/* + * Iterate over all ports in bridge (using sysfs). + */ +static int br_foreach_port(const char *brname, + int (*iterator)(const char *br, const char *port, void *arg), + void *arg) +{ + int i, count; + struct dirent **namelist; + char path[SYSFS_PATH_MAX]; + + snprintf(path, SYSFS_PATH_MAX, SYSFS_CLASS_NET "%s/brif", brname); + count = scandir(path, &namelist, 0, alphasort); + if (count < 0) + return old_foreach_port(brname, iterator, arg); + + for (i = 0; i < count; i++) { + if (namelist[i]->d_name[0] == '.' + && (namelist[i]->d_name[1] == '\0' + || (namelist[i]->d_name[1] == '.' + && namelist[i]->d_name[2] == '\0'))) + continue; + + if (iterator(brname, namelist[i]->d_name, arg)) + break; + } + for (i = 0; i < count; i++) + free(namelist[i]); + free(namelist); + + return count; +} diff --git a/package/network/services/ead/src/libbridge_private.h b/package/network/services/ead/src/libbridge_private.h new file mode 100644 index 0000000000..38fd60ed9b --- /dev/null +++ b/package/network/services/ead/src/libbridge_private.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2000 Lennert Buytenhek + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + */ + +#ifndef _LIBBRIDGE_PRIVATE_H +#define _LIBBRIDGE_PRIVATE_H + +#include <linux/sockios.h> +#include <sys/time.h> +#include <sys/ioctl.h> +#include <linux/if_bridge.h> + +#define MAX_BRIDGES 1024 +#define MAX_PORTS 1024 + +#define SYSFS_CLASS_NET "/sys/class/net/" +#define SYSFS_PATH_MAX 256 + +#define dprintf(fmt,arg...) + +#endif diff --git a/package/network/services/ead/src/list.h b/package/network/services/ead/src/list.h new file mode 100644 index 0000000000..ac429c862f --- /dev/null +++ b/package/network/services/ead/src/list.h @@ -0,0 +1,602 @@ +/* GPL v2, adapted from the Linux kernel */ +#ifndef _LINUX_LIST_H +#define _LINUX_LIST_H + +#include <stddef.h> +/** + * container_of - cast a member of a structure out to the containing structure + * @ptr: the pointer to the member. + * @type: the type of the container struct this is embedded in. + * @member: the name of the member within the struct. + * + */ +#ifndef container_of +#define container_of(ptr, type, member) ( \ + (type *)( (char *)ptr - offsetof(type,member) )) +#endif + + +/* + * Simple doubly linked list implementation. + * + * Some of the internal functions ("__xxx") are useful when + * manipulating whole lists rather than single entries, as + * sometimes we already know the next/prev entries and we can + * generate better code by using them directly rather than + * using the generic single-entry routines. + */ + +struct list_head { + struct list_head *next, *prev; +}; + +#define LIST_HEAD_INIT(name) { &(name), &(name) } + +#define LIST_HEAD(name) \ + struct list_head name = LIST_HEAD_INIT(name) + +static inline void INIT_LIST_HEAD(struct list_head *list) +{ + list->next = list; + list->prev = list; +} + +/* + * Insert a new entry between two known consecutive entries. + * + * This is only for internal list manipulation where we know + * the prev/next entries already! + */ +static inline void __list_add(struct list_head *new, + struct list_head *prev, + struct list_head *next) +{ + next->prev = new; + new->next = next; + new->prev = prev; + prev->next = new; +} + +/** + * list_add - add a new entry + * @new: new entry to be added + * @head: list head to add it after + * + * Insert a new entry after the specified head. + * This is good for implementing stacks. + */ +static inline void list_add(struct list_head *new, struct list_head *head) +{ + __list_add(new, head, head->next); +} + + +/** + * list_add_tail - add a new entry + * @new: new entry to be added + * @head: list head to add it before + * + * Insert a new entry before the specified head. + * This is useful for implementing queues. + */ +static inline void list_add_tail(struct list_head *new, struct list_head *head) +{ + __list_add(new, head->prev, head); +} + + +/* + * Delete a list entry by making the prev/next entries + * point to each other. + * + * This is only for internal list manipulation where we know + * the prev/next entries already! + */ +static inline void __list_del(struct list_head * prev, struct list_head * next) +{ + next->prev = prev; + prev->next = next; +} + +/** + * list_del - deletes entry from list. + * @entry: the element to delete from the list. + * Note: list_empty() on entry does not return true after this, the entry is + * in an undefined state. + */ +static inline void list_del(struct list_head *entry) +{ + __list_del(entry->prev, entry->next); + entry->next = NULL; + entry->prev = NULL; +} + +/** + * list_replace - replace old entry by new one + * @old : the element to be replaced + * @new : the new element to insert + * + * If @old was empty, it will be overwritten. + */ +static inline void list_replace(struct list_head *old, + struct list_head *new) +{ + new->next = old->next; + new->next->prev = new; + new->prev = old->prev; + new->prev->next = new; +} + +static inline void list_replace_init(struct list_head *old, + struct list_head *new) +{ + list_replace(old, new); + INIT_LIST_HEAD(old); +} + +/** + * list_del_init - deletes entry from list and reinitialize it. + * @entry: the element to delete from the list. + */ +static inline void list_del_init(struct list_head *entry) +{ + __list_del(entry->prev, entry->next); + INIT_LIST_HEAD(entry); +} + +/** + * list_move - delete from one list and add as another's head + * @list: the entry to move + * @head: the head that will precede our entry + */ +static inline void list_move(struct list_head *list, struct list_head *head) +{ + __list_del(list->prev, list->next); + list_add(list, head); +} + +/** + * list_move_tail - delete from one list and add as another's tail + * @list: the entry to move + * @head: the head that will follow our entry + */ +static inline void list_move_tail(struct list_head *list, + struct list_head *head) +{ + __list_del(list->prev, list->next); + list_add_tail(list, head); +} + +/** + * list_is_last - tests whether @list is the last entry in list @head + * @list: the entry to test + * @head: the head of the list + */ +static inline int list_is_last(const struct list_head *list, + const struct list_head *head) +{ + return list->next == head; +} + +/** + * list_empty - tests whether a list is empty + * @head: the list to test. + */ +static inline int list_empty(const struct list_head *head) +{ + return head->next == head; +} + +/** + * list_empty_careful - tests whether a list is empty and not being modified + * @head: the list to test + * + * Description: + * tests whether a list is empty _and_ checks that no other CPU might be + * in the process of modifying either member (next or prev) + * + * NOTE: using list_empty_careful() without synchronization + * can only be safe if the only activity that can happen + * to the list entry is list_del_init(). Eg. it cannot be used + * if another CPU could re-list_add() it. + */ +static inline int list_empty_careful(const struct list_head *head) +{ + struct list_head *next = head->next; + return (next == head) && (next == head->prev); +} + +static inline void __list_splice(struct list_head *list, + struct list_head *head) +{ + struct list_head *first = list->next; + struct list_head *last = list->prev; + struct list_head *at = head->next; + + first->prev = head; + head->next = first; + + last->next = at; + at->prev = last; +} + +/** + * list_splice - join two lists + * @list: the new list to add. + * @head: the place to add it in the first list. + */ +static inline void list_splice(struct list_head *list, struct list_head *head) +{ + if (!list_empty(list)) + __list_splice(list, head); +} + +/** + * list_splice_init - join two lists and reinitialise the emptied list. + * @list: the new list to add. + * @head: the place to add it in the first list. + * + * The list at @list is reinitialised + */ +static inline void list_splice_init(struct list_head *list, + struct list_head *head) +{ + if (!list_empty(list)) { + __list_splice(list, head); + INIT_LIST_HEAD(list); + } +} + +/** + * list_entry - get the struct for this entry + * @ptr: the &struct list_head pointer. + * @type: the type of the struct this is embedded in. + * @member: the name of the list_struct within the struct. + */ +#define list_entry(ptr, type, member) \ + container_of(ptr, type, member) + +/** + * list_first_entry - get the first element from a list + * @ptr: the list head to take the element from. + * @type: the type of the struct this is embedded in. + * @member: the name of the list_struct within the struct. + * + * Note, that list is expected to be not empty. + */ +#define list_first_entry(ptr, type, member) \ + list_entry((ptr)->next, type, member) + +/** + * list_for_each - iterate over a list + * @pos: the &struct list_head to use as a loop cursor. + * @head: the head for your list. + */ +#define list_for_each(pos, head) \ + for (pos = (head)->next; pos != (head); \ + pos = pos->next) + +/** + * __list_for_each - iterate over a list + * @pos: the &struct list_head to use as a loop cursor. + * @head: the head for your list. + * + * This variant differs from list_for_each() in that it's the + * simplest possible list iteration code, no prefetching is done. + * Use this for code that knows the list to be very short (empty + * or 1 entry) most of the time. + */ +#define __list_for_each(pos, head) \ + for (pos = (head)->next; pos != (head); pos = pos->next) + +/** + * list_for_each_prev - iterate over a list backwards + * @pos: the &struct list_head to use as a loop cursor. + * @head: the head for your list. + */ +#define list_for_each_prev(pos, head) \ + for (pos = (head)->prev; pos != (head); \ + pos = pos->prev) + +/** + * list_for_each_safe - iterate over a list safe against removal of list entry + * @pos: the &struct list_head to use as a loop cursor. + * @n: another &struct list_head to use as temporary storage + * @head: the head for your list. + */ +#define list_for_each_safe(pos, n, head) \ + for (pos = (head)->next, n = pos->next; pos != (head); \ + pos = n, n = pos->next) + +/** + * list_for_each_prev_safe - iterate over a list backwards safe against removal of list entry + * @pos: the &struct list_head to use as a loop cursor. + * @n: another &struct list_head to use as temporary storage + * @head: the head for your list. + */ +#define list_for_each_prev_safe(pos, n, head) \ + for (pos = (head)->prev, n = pos->prev; \ + pos != (head); \ + pos = n, n = pos->prev) + +/** + * list_for_each_entry - iterate over list of given type + * @pos: the type * to use as a loop cursor. + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + */ +#define list_for_each_entry(pos, head, member) \ + for (pos = list_entry((head)->next, typeof(*pos), member); \ + &pos->member != (head); \ + pos = list_entry(pos->member.next, typeof(*pos), member)) + +/** + * list_for_each_entry_reverse - iterate backwards over list of given type. + * @pos: the type * to use as a loop cursor. + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + */ +#define list_for_each_entry_reverse(pos, head, member) \ + for (pos = list_entry((head)->prev, typeof(*pos), member); \ + &pos->member != (head); \ + pos = list_entry(pos->member.prev, typeof(*pos), member)) + +/** + * list_prepare_entry - prepare a pos entry for use in list_for_each_entry_continue() + * @pos: the type * to use as a start point + * @head: the head of the list + * @member: the name of the list_struct within the struct. + * + * Prepares a pos entry for use as a start point in list_for_each_entry_continue(). + */ +#define list_prepare_entry(pos, head, member) \ + ((pos) ? : list_entry(head, typeof(*pos), member)) + +/** + * list_for_each_entry_continue - continue iteration over list of given type + * @pos: the type * to use as a loop cursor. + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + * + * Continue to iterate over list of given type, continuing after + * the current position. + */ +#define list_for_each_entry_continue(pos, head, member) \ + for (pos = list_entry(pos->member.next, typeof(*pos), member); \ + &pos->member != (head); \ + pos = list_entry(pos->member.next, typeof(*pos), member)) + +/** + * list_for_each_entry_continue_reverse - iterate backwards from the given point + * @pos: the type * to use as a loop cursor. + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + * + * Start to iterate over list of given type backwards, continuing after + * the current position. + */ +#define list_for_each_entry_continue_reverse(pos, head, member) \ + for (pos = list_entry(pos->member.prev, typeof(*pos), member); \ + &pos->member != (head); \ + pos = list_entry(pos->member.prev, typeof(*pos), member)) + +/** + * list_for_each_entry_from - iterate over list of given type from the current point + * @pos: the type * to use as a loop cursor. + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + * + * Iterate over list of given type, continuing from current position. + */ +#define list_for_each_entry_from(pos, head, member) \ + for (; &pos->member != (head); \ + pos = list_entry(pos->member.next, typeof(*pos), member)) + +/** + * list_for_each_entry_safe - iterate over list of given type safe against removal of list entry + * @pos: the type * to use as a loop cursor. + * @n: another type * to use as temporary storage + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + */ +#define list_for_each_entry_safe(pos, n, head, member) \ + for (pos = list_entry((head)->next, typeof(*pos), member), \ + n = list_entry(pos->member.next, typeof(*pos), member); \ + &pos->member != (head); \ + pos = n, n = list_entry(n->member.next, typeof(*n), member)) + +/** + * list_for_each_entry_safe_continue + * @pos: the type * to use as a loop cursor. + * @n: another type * to use as temporary storage + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + * + * Iterate over list of given type, continuing after current point, + * safe against removal of list entry. + */ +#define list_for_each_entry_safe_continue(pos, n, head, member) \ + for (pos = list_entry(pos->member.next, typeof(*pos), member), \ + n = list_entry(pos->member.next, typeof(*pos), member); \ + &pos->member != (head); \ + pos = n, n = list_entry(n->member.next, typeof(*n), member)) + +/** + * list_for_each_entry_safe_from + * @pos: the type * to use as a loop cursor. + * @n: another type * to use as temporary storage + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + * + * Iterate over list of given type from current point, safe against + * removal of list entry. + */ +#define list_for_each_entry_safe_from(pos, n, head, member) \ + for (n = list_entry(pos->member.next, typeof(*pos), member); \ + &pos->member != (head); \ + pos = n, n = list_entry(n->member.next, typeof(*n), member)) + +/** + * list_for_each_entry_safe_reverse + * @pos: the type * to use as a loop cursor. + * @n: another type * to use as temporary storage + * @head: the head for your list. + * @member: the name of the list_struct within the struct. + * + * Iterate backwards over list of given type, safe against removal + * of list entry. + */ +#define list_for_each_entry_safe_reverse(pos, n, head, member) \ + for (pos = list_entry((head)->prev, typeof(*pos), member), \ + n = list_entry(pos->member.prev, typeof(*pos), member); \ + &pos->member != (head); \ + pos = n, n = list_entry(n->member.prev, typeof(*n), member)) + +/* + * Double linked lists with a single pointer list head. + * Mostly useful for hash tables where the two pointer list head is + * too wasteful. + * You lose the ability to access the tail in O(1). + */ + +struct hlist_head { + struct hlist_node *first; +}; + +struct hlist_node { + struct hlist_node *next, **pprev; +}; + +#define HLIST_HEAD_INIT { .first = NULL } +#define HLIST_HEAD(name) struct hlist_head name = { .first = NULL } +#define INIT_HLIST_HEAD(ptr) ((ptr)->first = NULL) +static inline void INIT_HLIST_NODE(struct hlist_node *h) +{ + h->next = NULL; + h->pprev = NULL; +} + +static inline int hlist_unhashed(const struct hlist_node *h) +{ + return !h->pprev; +} + +static inline int hlist_empty(const struct hlist_head *h) +{ + return !h->first; +} + +static inline void __hlist_del(struct hlist_node *n) +{ + struct hlist_node *next = n->next; + struct hlist_node **pprev = n->pprev; + *pprev = next; + if (next) + next->pprev = pprev; +} + +static inline void hlist_del(struct hlist_node *n) +{ + __hlist_del(n); + n->next = NULL; + n->pprev = NULL; +} + +static inline void hlist_del_init(struct hlist_node *n) +{ + if (!hlist_unhashed(n)) { + __hlist_del(n); + INIT_HLIST_NODE(n); + } +} + + +static inline void hlist_add_head(struct hlist_node *n, struct hlist_head *h) +{ + struct hlist_node *first = h->first; + n->next = first; + if (first) + first->pprev = &n->next; + h->first = n; + n->pprev = &h->first; +} + + +/* next must be != NULL */ +static inline void hlist_add_before(struct hlist_node *n, + struct hlist_node *next) +{ + n->pprev = next->pprev; + n->next = next; + next->pprev = &n->next; + *(n->pprev) = n; +} + +static inline void hlist_add_after(struct hlist_node *n, + struct hlist_node *next) +{ + next->next = n->next; + n->next = next; + next->pprev = &n->next; + + if(next->next) + next->next->pprev = &next->next; +} + +#define hlist_entry(ptr, type, member) container_of(ptr,type,member) + +#define hlist_for_each(pos, head) \ + for (pos = (head)->first; pos; pos = pos->next) + +#define hlist_for_each_safe(pos, n, head) \ + for (pos = (head)->first; pos; pos = n) + +/** + * hlist_for_each_entry - iterate over list of given type + * @tpos: the type * to use as a loop cursor. + * @pos: the &struct hlist_node to use as a loop cursor. + * @head: the head for your list. + * @member: the name of the hlist_node within the struct. + */ +#define hlist_for_each_entry(tpos, pos, head, member) \ + for (pos = (head)->first; pos && \ + ({ tpos = hlist_entry(pos, typeof(*tpos), member); 1;}); \ + pos = pos->next) + +/** + * hlist_for_each_entry_continue - iterate over a hlist continuing after current point + * @tpos: the type * to use as a loop cursor. + * @pos: the &struct hlist_node to use as a loop cursor. + * @member: the name of the hlist_node within the struct. + */ +#define hlist_for_each_entry_continue(tpos, pos, member) \ + for (pos = (pos)->next; pos && \ + ({ tpos = hlist_entry(pos, typeof(*tpos), member); 1;}); \ + pos = pos->next) + +/** + * hlist_for_each_entry_from - iterate over a hlist continuing from current point + * @tpos: the type * to use as a loop cursor. + * @pos: the &struct hlist_node to use as a loop cursor. + * @member: the name of the hlist_node within the struct. + */ +#define hlist_for_each_entry_from(tpos, pos, member) \ + for (; pos && \ + ({ tpos = hlist_entry(pos, typeof(*tpos), member); 1;}); \ + pos = pos->next) + +/** + * hlist_for_each_entry_safe - iterate over list of given type safe against removal of list entry + * @tpos: the type * to use as a loop cursor. + * @pos: the &struct hlist_node to use as a loop cursor. + * @n: another &struct hlist_node to use as temporary storage + * @head: the head for your list. + * @member: the name of the hlist_node within the struct. + */ +#define hlist_for_each_entry_safe(tpos, pos, n, head, member) \ + for (pos = (head)->first; \ + pos && ({ n = pos->next; 1; }) && \ + ({ tpos = hlist_entry(pos, typeof(*tpos), member); 1;}); \ + pos = n) + +#endif diff --git a/package/network/services/ead/src/passwd b/package/network/services/ead/src/passwd new file mode 100644 index 0000000000..eee7a89486 --- /dev/null +++ b/package/network/services/ead/src/passwd @@ -0,0 +1,3 @@ +root:$1$MCGAgYw.$Ip1GcyeUliId3wzVcKR/e/:0:0:root:/root:/bin/ash +nobody:*:65534:65534:nobody:/var:/bin/false +daemon:*:65534:65534:daemon:/var:/bin/false diff --git a/package/network/services/ead/src/pfc.c b/package/network/services/ead/src/pfc.c new file mode 100644 index 0000000000..402e37f31d --- /dev/null +++ b/package/network/services/ead/src/pfc.c @@ -0,0 +1,54 @@ +/* + * Small pcap precompiler + * Copyright (C) 2008 Felix Fietkau <nbd@openwrt.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <sys/types.h> +#include <sys/time.h> +#include <string.h> +#include <stdlib.h> +#include <pcap.h> + +int main (int argc, char ** argv) +{ + struct bpf_program filter; + pcap_t *pc; + int i; + + if (argc != 2) + { + printf ("Usage: %s <expression>\n", argv[0]); + return 1; + } + + pc = pcap_open_dead(DLT_EN10MB, 1500); + if (pcap_compile(pc, &filter, argv[1], 1, 0) != 0) { + printf("error in active-filter expression: %s\n", pcap_geterr(pc)); + return 1; + } + + printf("/* precompiled expression: %s */\n\n" + "static struct bpf_insn pktfilter_insns[] = {\n", + argv[1]); + + for (i = 0; i < filter.bf_len; i++) { + struct bpf_insn *in = &filter.bf_insns[i]; + printf("\t{ .code = 0x%04x, .jt = 0x%02x, .jf = 0x%02x, .k = 0x%08x },\n", in->code, in->jt, in->jf, in->k); + } + printf("};\n\n" + "static struct bpf_program pktfilter = {\n" + "\t.bf_len = %d,\n" + "\t.bf_insns = pktfilter_insns,\n" + "};\n", filter.bf_len); + return 0; + +} diff --git a/package/network/services/ead/src/pw_encrypt_md5.c b/package/network/services/ead/src/pw_encrypt_md5.c new file mode 100644 index 0000000000..bc9f249fda --- /dev/null +++ b/package/network/services/ead/src/pw_encrypt_md5.c @@ -0,0 +1,646 @@ +/* + * MD5C.C - RSA Data Security, Inc., MD5 message-digest algorithm + * + * Copyright (C) 1991-2, RSA Data Security, Inc. Created 1991. All + * rights reserved. + * + * License to copy and use this software is granted provided that it + * is identified as the "RSA Data Security, Inc. MD5 Message-Digest + * Algorithm" in all material mentioning or referencing this software + * or this function. + * + * License is also granted to make and use derivative works provided + * that such works are identified as "derived from the RSA Data + * Security, Inc. MD5 Message-Digest Algorithm" in all material + * mentioning or referencing the derived work. + * + * RSA Data Security, Inc. makes no representations concerning either + * the merchantability of this software or the suitability of this + * software for any particular purpose. It is provided "as is" + * without express or implied warranty of any kind. + * + * These notices must be retained in any copies of any part of this + * documentation and/or software. + * + * $FreeBSD: src/lib/libmd/md5c.c,v 1.9.2.1 1999/08/29 14:57:12 peter Exp $ + * + * This code is the same as the code published by RSA Inc. It has been + * edited for clarity and style only. + * + * ---------------------------------------------------------------------------- + * The md5_crypt() function was taken from freeBSD's libcrypt and contains + * this license: + * "THE BEER-WARE LICENSE" (Revision 42): + * <phk@login.dknet.dk> wrote this file. As long as you retain this notice you + * can do whatever you want with this stuff. If we meet some day, and you think + * this stuff is worth it, you can buy me a beer in return. Poul-Henning Kamp + * + * $FreeBSD: src/lib/libcrypt/crypt.c,v 1.7.2.1 1999/08/29 14:56:33 peter Exp $ + * + * ---------------------------------------------------------------------------- + * On April 19th, 2001 md5_crypt() was modified to make it reentrant + * by Erik Andersen <andersen@uclibc.org> + * + * + * June 28, 2001 Manuel Novoa III + * + * "Un-inlined" code using loops and static const tables in order to + * reduce generated code size (on i386 from approx 4k to approx 2.5k). + * + * June 29, 2001 Manuel Novoa III + * + * Completely removed static PADDING array. + * + * Reintroduced the loop unrolling in MD5_Transform and added the + * MD5_SIZE_OVER_SPEED option for configurability. Define below as: + * 0 fully unrolled loops + * 1 partially unrolled (4 ops per loop) + * 2 no unrolling -- introduces the need to swap 4 variables (slow) + * 3 no unrolling and all 4 loops merged into one with switch + * in each loop (glacial) + * On i386, sizes are roughly (-Os -fno-builtin): + * 0: 3k 1: 2.5k 2: 2.2k 3: 2k + * + * + * Since SuSv3 does not require crypt_r, modified again August 7, 2002 + * by Erik Andersen to remove reentrance stuff... + */ + +static const uint8_t ascii64[] = "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; + +/* + * Valid values are 1 (fastest/largest) to 3 (smallest/slowest). + */ +#define MD5_SIZE_OVER_SPEED 3 + +/**********************************************************************/ + +/* MD5 context. */ +struct MD5Context { + uint32_t state[4]; /* state (ABCD) */ + uint32_t count[2]; /* number of bits, modulo 2^64 (lsb first) */ + unsigned char buffer[64]; /* input buffer */ +}; + +static void __md5_Init(struct MD5Context *); +static void __md5_Update(struct MD5Context *, const unsigned char *, unsigned int); +static void __md5_Pad(struct MD5Context *); +static void __md5_Final(unsigned char [16], struct MD5Context *); +static void __md5_Transform(uint32_t [4], const unsigned char [64]); + + +#define MD5_MAGIC_STR "$1$" +#define MD5_MAGIC_LEN (sizeof(MD5_MAGIC_STR) - 1) +static const unsigned char __md5__magic[] = MD5_MAGIC_STR; + + +#ifdef i386 +#define __md5_Encode memcpy +#define __md5_Decode memcpy +#else /* i386 */ + +/* + * __md5_Encodes input (uint32_t) into output (unsigned char). Assumes len is + * a multiple of 4. + */ +static void +__md5_Encode(unsigned char *output, uint32_t *input, unsigned int len) +{ + unsigned int i, j; + + for (i = 0, j = 0; j < len; i++, j += 4) { + output[j] = input[i]; + output[j+1] = (input[i] >> 8); + output[j+2] = (input[i] >> 16); + output[j+3] = (input[i] >> 24); + } +} + +/* + * __md5_Decodes input (unsigned char) into output (uint32_t). Assumes len is + * a multiple of 4. + */ +static void +__md5_Decode(uint32_t *output, const unsigned char *input, unsigned int len) +{ + unsigned int i, j; + + for (i = 0, j = 0; j < len; i++, j += 4) + output[i] = ((uint32_t)input[j]) | (((uint32_t)input[j+1]) << 8) | + (((uint32_t)input[j+2]) << 16) | (((uint32_t)input[j+3]) << 24); +} +#endif /* i386 */ + +/* F, G, H and I are basic MD5 functions. */ +#define F(x, y, z) (((x) & (y)) | (~(x) & (z))) +#define G(x, y, z) (((x) & (z)) | ((y) & ~(z))) +#define H(x, y, z) ((x) ^ (y) ^ (z)) +#define I(x, y, z) ((y) ^ ((x) | ~(z))) + +/* ROTATE_LEFT rotates x left n bits. */ +#define ROTATE_LEFT(x, n) (((x) << (n)) | ((x) >> (32-(n)))) + +/* + * FF, GG, HH, and II transformations for rounds 1, 2, 3, and 4. + * Rotation is separate from addition to prevent recomputation. + */ +#define FF(a, b, c, d, x, s, ac) { \ + (a) += F ((b), (c), (d)) + (x) + (uint32_t)(ac); \ + (a) = ROTATE_LEFT((a), (s)); \ + (a) += (b); \ + } +#define GG(a, b, c, d, x, s, ac) { \ + (a) += G ((b), (c), (d)) + (x) + (uint32_t)(ac); \ + (a) = ROTATE_LEFT((a), (s)); \ + (a) += (b); \ + } +#define HH(a, b, c, d, x, s, ac) { \ + (a) += H ((b), (c), (d)) + (x) + (uint32_t)(ac); \ + (a) = ROTATE_LEFT((a), (s)); \ + (a) += (b); \ + } +#define II(a, b, c, d, x, s, ac) { \ + (a) += I ((b), (c), (d)) + (x) + (uint32_t)(ac); \ + (a) = ROTATE_LEFT((a), (s)); \ + (a) += (b); \ + } + +/* MD5 initialization. Begins an MD5 operation, writing a new context. */ +static void __md5_Init(struct MD5Context *context) +{ + context->count[0] = context->count[1] = 0; + + /* Load magic initialization constants. */ + context->state[0] = 0x67452301; + context->state[1] = 0xefcdab89; + context->state[2] = 0x98badcfe; + context->state[3] = 0x10325476; +} + +/* + * MD5 block update operation. Continues an MD5 message-digest + * operation, processing another message block, and updating the + * context. + */ +static void __md5_Update(struct MD5Context *context, const unsigned char *input, unsigned int inputLen) +{ + unsigned int i, idx, partLen; + + /* Compute number of bytes mod 64 */ + idx = (context->count[0] >> 3) & 0x3F; + + /* Update number of bits */ + context->count[0] += (inputLen << 3); + if (context->count[0] < (inputLen << 3)) + context->count[1]++; + context->count[1] += (inputLen >> 29); + + partLen = 64 - idx; + + /* Transform as many times as possible. */ + if (inputLen >= partLen) { + memcpy(&context->buffer[idx], input, partLen); + __md5_Transform(context->state, context->buffer); + + for (i = partLen; i + 63 < inputLen; i += 64) + __md5_Transform(context->state, &input[i]); + + idx = 0; + } else + i = 0; + + /* Buffer remaining input */ + memcpy(&context->buffer[idx], &input[i], inputLen - i); +} + +/* + * MD5 padding. Adds padding followed by original length. + */ +static void __md5_Pad(struct MD5Context *context) +{ + unsigned char bits[8]; + unsigned int idx, padLen; + unsigned char PADDING[64]; + + memset(PADDING, 0, sizeof(PADDING)); + PADDING[0] = 0x80; + + /* Save number of bits */ + __md5_Encode(bits, context->count, 8); + + /* Pad out to 56 mod 64. */ + idx = (context->count[0] >> 3) & 0x3f; + padLen = (idx < 56) ? (56 - idx) : (120 - idx); + __md5_Update(context, PADDING, padLen); + + /* Append length (before padding) */ + __md5_Update(context, bits, 8); +} + +/* + * MD5 finalization. Ends an MD5 message-digest operation, writing the + * the message digest and zeroizing the context. + */ +static void __md5_Final(unsigned char digest[16], struct MD5Context *context) +{ + /* Do padding. */ + __md5_Pad(context); + + /* Store state in digest */ + __md5_Encode(digest, context->state, 16); + + /* Zeroize sensitive information. */ + memset(context, 0, sizeof(*context)); +} + +/* MD5 basic transformation. Transforms state based on block. */ +static void __md5_Transform(uint32_t state[4], const unsigned char block[64]) +{ + uint32_t a, b, c, d, x[16]; +#if MD5_SIZE_OVER_SPEED > 1 + uint32_t temp; + const unsigned char *ps; + + static const unsigned char S[] = { + 7, 12, 17, 22, + 5, 9, 14, 20, + 4, 11, 16, 23, + 6, 10, 15, 21 + }; +#endif /* MD5_SIZE_OVER_SPEED > 1 */ + +#if MD5_SIZE_OVER_SPEED > 0 + const uint32_t *pc; + const unsigned char *pp; + int i; + + static const uint32_t C[] = { + /* round 1 */ + 0xd76aa478, 0xe8c7b756, 0x242070db, 0xc1bdceee, + 0xf57c0faf, 0x4787c62a, 0xa8304613, 0xfd469501, + 0x698098d8, 0x8b44f7af, 0xffff5bb1, 0x895cd7be, + 0x6b901122, 0xfd987193, 0xa679438e, 0x49b40821, + /* round 2 */ + 0xf61e2562, 0xc040b340, 0x265e5a51, 0xe9b6c7aa, + 0xd62f105d, 0x2441453, 0xd8a1e681, 0xe7d3fbc8, + 0x21e1cde6, 0xc33707d6, 0xf4d50d87, 0x455a14ed, + 0xa9e3e905, 0xfcefa3f8, 0x676f02d9, 0x8d2a4c8a, + /* round 3 */ + 0xfffa3942, 0x8771f681, 0x6d9d6122, 0xfde5380c, + 0xa4beea44, 0x4bdecfa9, 0xf6bb4b60, 0xbebfbc70, + 0x289b7ec6, 0xeaa127fa, 0xd4ef3085, 0x4881d05, + 0xd9d4d039, 0xe6db99e5, 0x1fa27cf8, 0xc4ac5665, + /* round 4 */ + 0xf4292244, 0x432aff97, 0xab9423a7, 0xfc93a039, + 0x655b59c3, 0x8f0ccc92, 0xffeff47d, 0x85845dd1, + 0x6fa87e4f, 0xfe2ce6e0, 0xa3014314, 0x4e0811a1, + 0xf7537e82, 0xbd3af235, 0x2ad7d2bb, 0xeb86d391 + }; + + static const unsigned char P[] = { + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, /* 1 */ + 1, 6, 11, 0, 5, 10, 15, 4, 9, 14, 3, 8, 13, 2, 7, 12, /* 2 */ + 5, 8, 11, 14, 1, 4, 7, 10, 13, 0, 3, 6, 9, 12, 15, 2, /* 3 */ + 0, 7, 14, 5, 12, 3, 10, 1, 8, 15, 6, 13, 4, 11, 2, 9 /* 4 */ + }; + +#endif /* MD5_SIZE_OVER_SPEED > 0 */ + + __md5_Decode(x, block, 64); + + a = state[0]; b = state[1]; c = state[2]; d = state[3]; + +#if MD5_SIZE_OVER_SPEED > 2 + pc = C; pp = P; ps = S - 4; + + for (i = 0; i < 64; i++) { + if ((i & 0x0f) == 0) ps += 4; + temp = a; + switch (i>>4) { + case 0: + temp += F(b, c, d); + break; + case 1: + temp += G(b, c, d); + break; + case 2: + temp += H(b, c, d); + break; + case 3: + temp += I(b, c, d); + break; + } + temp += x[*pp++] + *pc++; + temp = ROTATE_LEFT(temp, ps[i & 3]); + temp += b; + a = d; d = c; c = b; b = temp; + } +#elif MD5_SIZE_OVER_SPEED > 1 + pc = C; pp = P; ps = S; + + /* Round 1 */ + for (i = 0; i < 16; i++) { + FF(a, b, c, d, x[*pp], ps[i & 0x3], *pc); pp++; pc++; + temp = d; d = c; c = b; b = a; a = temp; + } + + /* Round 2 */ + ps += 4; + for (; i < 32; i++) { + GG(a, b, c, d, x[*pp], ps[i & 0x3], *pc); pp++; pc++; + temp = d; d = c; c = b; b = a; a = temp; + } + /* Round 3 */ + ps += 4; + for (; i < 48; i++) { + HH(a, b, c, d, x[*pp], ps[i & 0x3], *pc); pp++; pc++; + temp = d; d = c; c = b; b = a; a = temp; + } + + /* Round 4 */ + ps += 4; + for (; i < 64; i++) { + II(a, b, c, d, x[*pp], ps[i & 0x3], *pc); pp++; pc++; + temp = d; d = c; c = b; b = a; a = temp; + } +#elif MD5_SIZE_OVER_SPEED > 0 + pc = C; pp = P; + + /* Round 1 */ + for (i = 0; i < 4; i++) { + FF(a, b, c, d, x[*pp], 7, *pc); pp++; pc++; + FF(d, a, b, c, x[*pp], 12, *pc); pp++; pc++; + FF(c, d, a, b, x[*pp], 17, *pc); pp++; pc++; + FF(b, c, d, a, x[*pp], 22, *pc); pp++; pc++; + } + + /* Round 2 */ + for (i = 0; i < 4; i++) { + GG(a, b, c, d, x[*pp], 5, *pc); pp++; pc++; + GG(d, a, b, c, x[*pp], 9, *pc); pp++; pc++; + GG(c, d, a, b, x[*pp], 14, *pc); pp++; pc++; + GG(b, c, d, a, x[*pp], 20, *pc); pp++; pc++; + } + /* Round 3 */ + for (i = 0; i < 4; i++) { + HH(a, b, c, d, x[*pp], 4, *pc); pp++; pc++; + HH(d, a, b, c, x[*pp], 11, *pc); pp++; pc++; + HH(c, d, a, b, x[*pp], 16, *pc); pp++; pc++; + HH(b, c, d, a, x[*pp], 23, *pc); pp++; pc++; + } + + /* Round 4 */ + for (i = 0; i < 4; i++) { + II(a, b, c, d, x[*pp], 6, *pc); pp++; pc++; + II(d, a, b, c, x[*pp], 10, *pc); pp++; pc++; + II(c, d, a, b, x[*pp], 15, *pc); pp++; pc++; + II(b, c, d, a, x[*pp], 21, *pc); pp++; pc++; + } +#else + /* Round 1 */ +#define S11 7 +#define S12 12 +#define S13 17 +#define S14 22 + FF(a, b, c, d, x[ 0], S11, 0xd76aa478); /* 1 */ + FF(d, a, b, c, x[ 1], S12, 0xe8c7b756); /* 2 */ + FF(c, d, a, b, x[ 2], S13, 0x242070db); /* 3 */ + FF(b, c, d, a, x[ 3], S14, 0xc1bdceee); /* 4 */ + FF(a, b, c, d, x[ 4], S11, 0xf57c0faf); /* 5 */ + FF(d, a, b, c, x[ 5], S12, 0x4787c62a); /* 6 */ + FF(c, d, a, b, x[ 6], S13, 0xa8304613); /* 7 */ + FF(b, c, d, a, x[ 7], S14, 0xfd469501); /* 8 */ + FF(a, b, c, d, x[ 8], S11, 0x698098d8); /* 9 */ + FF(d, a, b, c, x[ 9], S12, 0x8b44f7af); /* 10 */ + FF(c, d, a, b, x[10], S13, 0xffff5bb1); /* 11 */ + FF(b, c, d, a, x[11], S14, 0x895cd7be); /* 12 */ + FF(a, b, c, d, x[12], S11, 0x6b901122); /* 13 */ + FF(d, a, b, c, x[13], S12, 0xfd987193); /* 14 */ + FF(c, d, a, b, x[14], S13, 0xa679438e); /* 15 */ + FF(b, c, d, a, x[15], S14, 0x49b40821); /* 16 */ + + /* Round 2 */ +#define S21 5 +#define S22 9 +#define S23 14 +#define S24 20 + GG(a, b, c, d, x[ 1], S21, 0xf61e2562); /* 17 */ + GG(d, a, b, c, x[ 6], S22, 0xc040b340); /* 18 */ + GG(c, d, a, b, x[11], S23, 0x265e5a51); /* 19 */ + GG(b, c, d, a, x[ 0], S24, 0xe9b6c7aa); /* 20 */ + GG(a, b, c, d, x[ 5], S21, 0xd62f105d); /* 21 */ + GG(d, a, b, c, x[10], S22, 0x2441453); /* 22 */ + GG(c, d, a, b, x[15], S23, 0xd8a1e681); /* 23 */ + GG(b, c, d, a, x[ 4], S24, 0xe7d3fbc8); /* 24 */ + GG(a, b, c, d, x[ 9], S21, 0x21e1cde6); /* 25 */ + GG(d, a, b, c, x[14], S22, 0xc33707d6); /* 26 */ + GG(c, d, a, b, x[ 3], S23, 0xf4d50d87); /* 27 */ + GG(b, c, d, a, x[ 8], S24, 0x455a14ed); /* 28 */ + GG(a, b, c, d, x[13], S21, 0xa9e3e905); /* 29 */ + GG(d, a, b, c, x[ 2], S22, 0xfcefa3f8); /* 30 */ + GG(c, d, a, b, x[ 7], S23, 0x676f02d9); /* 31 */ + GG(b, c, d, a, x[12], S24, 0x8d2a4c8a); /* 32 */ + + /* Round 3 */ +#define S31 4 +#define S32 11 +#define S33 16 +#define S34 23 + HH(a, b, c, d, x[ 5], S31, 0xfffa3942); /* 33 */ + HH(d, a, b, c, x[ 8], S32, 0x8771f681); /* 34 */ + HH(c, d, a, b, x[11], S33, 0x6d9d6122); /* 35 */ + HH(b, c, d, a, x[14], S34, 0xfde5380c); /* 36 */ + HH(a, b, c, d, x[ 1], S31, 0xa4beea44); /* 37 */ + HH(d, a, b, c, x[ 4], S32, 0x4bdecfa9); /* 38 */ + HH(c, d, a, b, x[ 7], S33, 0xf6bb4b60); /* 39 */ + HH(b, c, d, a, x[10], S34, 0xbebfbc70); /* 40 */ + HH(a, b, c, d, x[13], S31, 0x289b7ec6); /* 41 */ + HH(d, a, b, c, x[ 0], S32, 0xeaa127fa); /* 42 */ + HH(c, d, a, b, x[ 3], S33, 0xd4ef3085); /* 43 */ + HH(b, c, d, a, x[ 6], S34, 0x4881d05); /* 44 */ + HH(a, b, c, d, x[ 9], S31, 0xd9d4d039); /* 45 */ + HH(d, a, b, c, x[12], S32, 0xe6db99e5); /* 46 */ + HH(c, d, a, b, x[15], S33, 0x1fa27cf8); /* 47 */ + HH(b, c, d, a, x[ 2], S34, 0xc4ac5665); /* 48 */ + + /* Round 4 */ +#define S41 6 +#define S42 10 +#define S43 15 +#define S44 21 + II(a, b, c, d, x[ 0], S41, 0xf4292244); /* 49 */ + II(d, a, b, c, x[ 7], S42, 0x432aff97); /* 50 */ + II(c, d, a, b, x[14], S43, 0xab9423a7); /* 51 */ + II(b, c, d, a, x[ 5], S44, 0xfc93a039); /* 52 */ + II(a, b, c, d, x[12], S41, 0x655b59c3); /* 53 */ + II(d, a, b, c, x[ 3], S42, 0x8f0ccc92); /* 54 */ + II(c, d, a, b, x[10], S43, 0xffeff47d); /* 55 */ + II(b, c, d, a, x[ 1], S44, 0x85845dd1); /* 56 */ + II(a, b, c, d, x[ 8], S41, 0x6fa87e4f); /* 57 */ + II(d, a, b, c, x[15], S42, 0xfe2ce6e0); /* 58 */ + II(c, d, a, b, x[ 6], S43, 0xa3014314); /* 59 */ + II(b, c, d, a, x[13], S44, 0x4e0811a1); /* 60 */ + II(a, b, c, d, x[ 4], S41, 0xf7537e82); /* 61 */ + II(d, a, b, c, x[11], S42, 0xbd3af235); /* 62 */ + II(c, d, a, b, x[ 2], S43, 0x2ad7d2bb); /* 63 */ + II(b, c, d, a, x[ 9], S44, 0xeb86d391); /* 64 */ +#endif + + state[0] += a; + state[1] += b; + state[2] += c; + state[3] += d; + + /* Zeroize sensitive information. */ + memset(x, 0, sizeof(x)); +} + + +static char* +__md5_to64(char *s, unsigned v, int n) +{ + while (--n >= 0) { + *s++ = ascii64[v & 0x3f]; + v >>= 6; + } + return s; +} + +/* + * UNIX password + * + * Use MD5 for what it is best at... + */ +#define MD5_OUT_BUFSIZE 36 +static char * +md5_crypt(char passwd[MD5_OUT_BUFSIZE], const unsigned char *pw, const unsigned char *salt) +{ + const unsigned char *sp, *ep; + char *p; + unsigned char final[17]; /* final[16] exists only to aid in looping */ + int sl, pl, i, pw_len; + struct MD5Context ctx, ctx1; + + /* Refine the Salt first */ + sp = salt; + + sp += MD5_MAGIC_LEN; + + /* It stops at the first '$', max 8 chars */ + for (ep = sp; *ep && *ep != '$' && ep < (sp+8); ep++) + continue; + + /* get the length of the true salt */ + sl = ep - sp; + + __md5_Init(&ctx); + + /* The password first, since that is what is most unknown */ + pw_len = strlen((char*)pw); + __md5_Update(&ctx, pw, pw_len); + + /* Then our magic string */ + __md5_Update(&ctx, __md5__magic, MD5_MAGIC_LEN); + + /* Then the raw salt */ + __md5_Update(&ctx, sp, sl); + + /* Then just as many characters of the MD5(pw, salt, pw) */ + __md5_Init(&ctx1); + __md5_Update(&ctx1, pw, pw_len); + __md5_Update(&ctx1, sp, sl); + __md5_Update(&ctx1, pw, pw_len); + __md5_Final(final, &ctx1); + for (pl = pw_len; pl > 0; pl -= 16) + __md5_Update(&ctx, final, pl > 16 ? 16 : pl); + + /* Don't leave anything around in vm they could use. */ +//TODO: the above comment seems to be wrong. final is used later. + memset(final, 0, sizeof(final)); + + /* Then something really weird... */ + for (i = pw_len; i; i >>= 1) { + __md5_Update(&ctx, ((i & 1) ? final : (const unsigned char *) pw), 1); + } + + /* Now make the output string */ + passwd[0] = '$'; + passwd[1] = '1'; + passwd[2] = '$'; + strncpy(passwd + 3, (char*)sp, sl); + passwd[sl + 3] = '$'; + + __md5_Final(final, &ctx); + + /* + * and now, just to make sure things don't run too fast + * On a 60 Mhz Pentium this takes 34 msec, so you would + * need 30 seconds to build a 1000 entry dictionary... + */ + for (i = 0; i < 1000; i++) { + __md5_Init(&ctx1); + if (i & 1) + __md5_Update(&ctx1, pw, pw_len); + else + __md5_Update(&ctx1, final, 16); + + if (i % 3) + __md5_Update(&ctx1, sp, sl); + + if (i % 7) + __md5_Update(&ctx1, pw, pw_len); + + if (i & 1) + __md5_Update(&ctx1, final, 16); + else + __md5_Update(&ctx1, pw, pw_len); + __md5_Final(final, &ctx1); + } + + p = passwd + sl + 4; /* 12 bytes max (sl is up to 8 bytes) */ + + /* Add 5*4+2 = 22 bytes of hash, + NUL byte. */ + final[16] = final[5]; + for (i = 0; i < 5; i++) { + unsigned l = (final[i] << 16) | (final[i+6] << 8) | final[i+12]; + p = __md5_to64(p, l, 4); + } + p = __md5_to64(p, final[11], 2); + *p = '\0'; + + /* Don't leave anything around in vm they could use. */ + memset(final, 0, sizeof(final)); + + return passwd; +} + +#undef MD5_SIZE_OVER_SPEED +#undef MD5_MAGIC_STR +#undef MD5_MAGIC_LEN +#undef __md5_Encode +#undef __md5_Decode +#undef F +#undef G +#undef H +#undef I +#undef ROTATE_LEFT +#undef FF +#undef GG +#undef HH +#undef II +#undef S11 +#undef S12 +#undef S13 +#undef S14 +#undef S21 +#undef S22 +#undef S23 +#undef S24 +#undef S31 +#undef S32 +#undef S33 +#undef S34 +#undef S41 +#undef S42 +#undef S43 +#undef S44 diff --git a/package/network/services/ead/src/sha1.c b/package/network/services/ead/src/sha1.c new file mode 100644 index 0000000000..3683a7da71 --- /dev/null +++ b/package/network/services/ead/src/sha1.c @@ -0,0 +1,104 @@ +/* + * SHA transform algorithm, originally taken from code written by + * Peter Gutmann, and placed in the public domain. + */ + +static uint32_t +rol32(uint32_t word, int shift) +{ + return (word << shift) | (word >> (32 - shift)); +} + +/* The SHA f()-functions. */ + +#define f1(x,y,z) (z ^ (x & (y ^ z))) /* x ? y : z */ +#define f2(x,y,z) (x ^ y ^ z) /* XOR */ +#define f3(x,y,z) ((x & y) + (z & (x ^ y))) /* majority */ + +/* The SHA Mysterious Constants */ + +#define K1 0x5A827999L /* Rounds 0-19: sqrt(2) * 2^30 */ +#define K2 0x6ED9EBA1L /* Rounds 20-39: sqrt(3) * 2^30 */ +#define K3 0x8F1BBCDCL /* Rounds 40-59: sqrt(5) * 2^30 */ +#define K4 0xCA62C1D6L /* Rounds 60-79: sqrt(10) * 2^30 */ + +/** + * sha_transform - single block SHA1 transform + * + * @digest: 160 bit digest to update + * @data: 512 bits of data to hash + * @W: 80 words of workspace (see note) + * + * This function generates a SHA1 digest for a single 512-bit block. + * Be warned, it does not handle padding and message digest, do not + * confuse it with the full FIPS 180-1 digest algorithm for variable + * length messages. + * + * Note: If the hash is security sensitive, the caller should be sure + * to clear the workspace. This is left to the caller to avoid + * unnecessary clears between chained hashing operations. + */ +static void sha_transform(uint32_t *digest, const unsigned char *in, uint32_t *W) +{ + uint32_t a, b, c, d, e, t, i; + + for (i = 0; i < 16; i++) { + int ofs = 4 * i; + + /* word load/store may be unaligned here, so use bytes instead */ + W[i] = + (in[ofs+0] << 24) | + (in[ofs+1] << 16) | + (in[ofs+2] << 8) | + in[ofs+3]; + } + + for (i = 0; i < 64; i++) + W[i+16] = rol32(W[i+13] ^ W[i+8] ^ W[i+2] ^ W[i], 1); + + a = digest[0]; + b = digest[1]; + c = digest[2]; + d = digest[3]; + e = digest[4]; + + for (i = 0; i < 20; i++) { + t = f1(b, c, d) + K1 + rol32(a, 5) + e + W[i]; + e = d; d = c; c = rol32(b, 30); b = a; a = t; + } + + for (; i < 40; i ++) { + t = f2(b, c, d) + K2 + rol32(a, 5) + e + W[i]; + e = d; d = c; c = rol32(b, 30); b = a; a = t; + } + + for (; i < 60; i ++) { + t = f3(b, c, d) + K3 + rol32(a, 5) + e + W[i]; + e = d; d = c; c = rol32(b, 30); b = a; a = t; + } + + for (; i < 80; i ++) { + t = f2(b, c, d) + K4 + rol32(a, 5) + e + W[i]; + e = d; d = c; c = rol32(b, 30); b = a; a = t; + } + + digest[0] += a; + digest[1] += b; + digest[2] += c; + digest[3] += d; + digest[4] += e; +} + +/** + * sha_init - initialize the vectors for a SHA1 digest + * @buf: vector to initialize + */ +static void sha_init(uint32_t *buf) +{ + buf[0] = 0x67452301; + buf[1] = 0xefcdab89; + buf[2] = 0x98badcfe; + buf[3] = 0x10325476; + buf[4] = 0xc3d2e1f0; +} + diff --git a/package/network/services/ead/src/tinysrp/Makefile.am b/package/network/services/ead/src/tinysrp/Makefile.am new file mode 100644 index 0000000000..a8f899fe2c --- /dev/null +++ b/package/network/services/ead/src/tinysrp/Makefile.am @@ -0,0 +1,28 @@ +AUTOMAKE_OPTIONS = foreign no-dependencies + +noinst_HEADERS = t_client.h t_pwd.h t_server.h t_sha.h \ + bn.h bn_lcl.h bn_prime.h t_defines.h t_read.h + +include_HEADERS = tinysrp.h + +lib_LIBRARIES = libtinysrp.a + +CFLAGS = -O2 @signed@ + +libtinysrp_a_SOURCES = \ + tinysrp.c t_client.c t_getconf.c t_conv.c t_getpass.c t_sha.c t_math.c \ + t_misc.c t_pw.c t_read.c t_server.c t_truerand.c \ + bn_add.c bn_ctx.c bn_div.c bn_exp.c bn_mul.c bn_word.c bn_asm.c bn_lib.c \ + bn_shift.c bn_sqr.c + +noinst_PROGRAMS = srvtest clitest +srvtest_SOURCES = srvtest.c +clitest_SOURCES = clitest.c + +bin_PROGRAMS = tconf tphrase +tconf_SOURCES = tconf.c t_conf.c +tphrase_SOURCES = tphrase.c + +LDADD = libtinysrp.a + +EXTRA_DIST = tpasswd Notes diff --git a/package/network/services/ead/src/tinysrp/Makefile.in b/package/network/services/ead/src/tinysrp/Makefile.in new file mode 100644 index 0000000000..4701cd5238 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/Makefile.in @@ -0,0 +1,477 @@ +# Makefile.in generated automatically by automake 1.4a from Makefile.am + +# Copyright (C) 1994, 1995-8, 1999 Free Software Foundation, Inc. +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + + +SHELL = @SHELL@ + +srcdir = @srcdir@ +top_srcdir = @top_srcdir@ +VPATH = @srcdir@ +prefix = @prefix@ +exec_prefix = @exec_prefix@ + +bindir = @bindir@ +sbindir = @sbindir@ +libexecdir = @libexecdir@ +datadir = @datadir@ +sysconfdir = @sysconfdir@ +sharedstatedir = @sharedstatedir@ +localstatedir = @localstatedir@ +libdir = @libdir@ +infodir = @infodir@ +mandir = @mandir@ +includedir = @includedir@ +oldincludedir = /usr/include + +DESTDIR = + +pkgdatadir = $(datadir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ + +top_builddir = . + +ACLOCAL = @ACLOCAL@ +AUTOCONF = @AUTOCONF@ +AUTOMAKE = @AUTOMAKE@ +AUTOHEADER = @AUTOHEADER@ + +INSTALL = @INSTALL@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_FLAG = +transform = @program_transform_name@ + +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +CC = @CC@ +LN_S = @LN_S@ +MAKEINFO = @MAKEINFO@ +PACKAGE = @PACKAGE@ +RANLIB = @RANLIB@ +VERSION = @VERSION@ +signed = @signed@ + +AUTOMAKE_OPTIONS = foreign no-dependencies + +noinst_HEADERS = t_client.h t_pwd.h t_server.h t_sha.h bn.h bn_lcl.h bn_prime.h t_defines.h t_read.h + + +include_HEADERS = tinysrp.h + +lib_LIBRARIES = libtinysrp.a + +CFLAGS = -O2 @signed@ + +libtinysrp_a_SOURCES = tinysrp.c t_client.c t_getconf.c t_conv.c t_getpass.c t_sha.c t_math.c t_misc.c t_pw.c t_read.c t_server.c t_truerand.c bn_add.c bn_ctx.c bn_div.c bn_exp.c bn_mul.c bn_word.c bn_asm.c bn_lib.c bn_shift.c bn_sqr.c + + +noinst_PROGRAMS = srvtest clitest +srvtest_SOURCES = srvtest.c +clitest_SOURCES = clitest.c + +bin_PROGRAMS = tconf tphrase +tconf_SOURCES = tconf.c t_conf.c +tphrase_SOURCES = tphrase.c + +LDADD = libtinysrp.a + +EXTRA_DIST = tpasswd Notes +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs +CONFIG_HEADER = config.h +CONFIG_CLEAN_FILES = +LIBRARIES = $(lib_LIBRARIES) + + +DEFS = @DEFS@ -I. -I$(srcdir) -I. +CPPFLAGS = @CPPFLAGS@ +LDFLAGS = @LDFLAGS@ +LIBS = @LIBS@ +libtinysrp_a_LIBADD = +libtinysrp_a_OBJECTS = tinysrp.o t_client.o t_getconf.o t_conv.o \ +t_getpass.o t_sha.o t_math.o t_misc.o t_pw.o t_read.o t_server.o \ +t_truerand.o bn_add.o bn_ctx.o bn_div.o bn_exp.o bn_mul.o bn_word.o \ +bn_asm.o bn_lib.o bn_shift.o bn_sqr.o +AR = ar +PROGRAMS = $(bin_PROGRAMS) $(noinst_PROGRAMS) + +tconf_OBJECTS = tconf.o t_conf.o +tconf_LDADD = $(LDADD) +tconf_DEPENDENCIES = libtinysrp.a +tconf_LDFLAGS = +tphrase_OBJECTS = tphrase.o +tphrase_LDADD = $(LDADD) +tphrase_DEPENDENCIES = libtinysrp.a +tphrase_LDFLAGS = +srvtest_OBJECTS = srvtest.o +srvtest_LDADD = $(LDADD) +srvtest_DEPENDENCIES = libtinysrp.a +srvtest_LDFLAGS = +clitest_OBJECTS = clitest.o +clitest_LDADD = $(LDADD) +clitest_DEPENDENCIES = libtinysrp.a +clitest_LDFLAGS = +COMPILE = $(CC) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +CCLD = $(CC) +LINK = $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(LDFLAGS) -o $@ +HEADERS = $(include_HEADERS) $(noinst_HEADERS) + +DIST_COMMON = ./stamp-h.in Makefile.am Makefile.in acconfig.h \ +acinclude.m4 aclocal.m4 config.h.in configure configure.in install-sh \ +missing mkinstalldirs + + +DISTFILES = $(DIST_COMMON) $(SOURCES) $(HEADERS) $(TEXINFOS) $(EXTRA_DIST) + +TAR = gtar +GZIP_ENV = --best +SOURCES = $(libtinysrp_a_SOURCES) $(tconf_SOURCES) $(tphrase_SOURCES) $(srvtest_SOURCES) $(clitest_SOURCES) +OBJECTS = $(libtinysrp_a_OBJECTS) $(tconf_OBJECTS) $(tphrase_OBJECTS) $(srvtest_OBJECTS) $(clitest_OBJECTS) + +all: all-redirect +.SUFFIXES: +.SUFFIXES: .S .c .o .s + +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + cd $(top_builddir) \ + && CONFIG_FILES=$@ CONFIG_HEADERS= $(SHELL) ./config.status + +$(ACLOCAL_M4): configure.in acinclude.m4 + cd $(srcdir) && $(ACLOCAL) + +$(srcdir)/configure: $(srcdir)/configure.in $(ACLOCAL_M4) $(CONFIGURE_DEPENDENCIES) + cd $(srcdir) && $(AUTOCONF) + +config.h: stamp-h + @if test ! -f $@; then \ + rm -f stamp-h; \ + $(MAKE) stamp-h; \ + else :; fi +stamp-h: $(srcdir)/config.h.in $(top_builddir)/config.status + cd $(top_builddir) \ + && CONFIG_FILES= CONFIG_HEADERS=config.h \ + $(SHELL) ./config.status + @echo timestamp > stamp-h 2> /dev/null +$(srcdir)/config.h.in: $(srcdir)/stamp-h.in + @if test ! -f $@; then \ + rm -f $(srcdir)/stamp-h.in; \ + $(MAKE) $(srcdir)/stamp-h.in; \ + else :; fi +$(srcdir)/stamp-h.in: $(top_srcdir)/configure.in $(ACLOCAL_M4) acconfig.h + cd $(top_srcdir) && $(AUTOHEADER) + @echo timestamp > $(srcdir)/stamp-h.in 2> /dev/null + +mostlyclean-hdr: + +clean-hdr: + +distclean-hdr: + -rm -f config.h + +maintainer-clean-hdr: + +mostlyclean-libLIBRARIES: + +clean-libLIBRARIES: + -test -z "$(lib_LIBRARIES)" || rm -f $(lib_LIBRARIES) + +distclean-libLIBRARIES: + +maintainer-clean-libLIBRARIES: + +install-libLIBRARIES: $(lib_LIBRARIES) + @$(NORMAL_INSTALL) + $(mkinstalldirs) $(DESTDIR)$(libdir) + @list='$(lib_LIBRARIES)'; for p in $$list; do \ + if test -f $$p; then \ + echo " $(INSTALL_DATA) $$p $(DESTDIR)$(libdir)/$$p"; \ + $(INSTALL_DATA) $$p $(DESTDIR)$(libdir)/$$p; \ + else :; fi; \ + done + @$(POST_INSTALL) + @list='$(lib_LIBRARIES)'; for p in $$list; do \ + if test -f $$p; then \ + echo " $(RANLIB) $(DESTDIR)$(libdir)/$$p"; \ + $(RANLIB) $(DESTDIR)$(libdir)/$$p; \ + else :; fi; \ + done + +uninstall-libLIBRARIES: + @$(NORMAL_UNINSTALL) + list='$(lib_LIBRARIES)'; for p in $$list; do \ + rm -f $(DESTDIR)$(libdir)/$$p; \ + done + +.c.o: + $(COMPILE) -c $< + +.s.o: + $(COMPILE) -c $< + +.S.o: + $(COMPILE) -c $< + +mostlyclean-compile: + -rm -f *.o core *.core + +clean-compile: + +distclean-compile: + -rm -f *.tab.c + +maintainer-clean-compile: + +libtinysrp.a: $(libtinysrp_a_OBJECTS) $(libtinysrp_a_DEPENDENCIES) + -rm -f libtinysrp.a + $(AR) cru libtinysrp.a $(libtinysrp_a_OBJECTS) $(libtinysrp_a_LIBADD) + $(RANLIB) libtinysrp.a + +mostlyclean-binPROGRAMS: + +clean-binPROGRAMS: + -test -z "$(bin_PROGRAMS)" || rm -f $(bin_PROGRAMS) + +distclean-binPROGRAMS: + +maintainer-clean-binPROGRAMS: + +install-binPROGRAMS: $(bin_PROGRAMS) + @$(NORMAL_INSTALL) + $(mkinstalldirs) $(DESTDIR)$(bindir) + @list='$(bin_PROGRAMS)'; for p in $$list; do \ + if test -f $$p; then \ + echo " $(INSTALL_PROGRAM) $(INSTALL_STRIP_FLAG) $$p $(DESTDIR)$(bindir)/`echo $$p|sed 's/$(EXEEXT)$$//'|sed '$(transform)'|sed 's/$$/$(EXEEXT)/'`"; \ + $(INSTALL_PROGRAM) $(INSTALL_STRIP_FLAG) $$p $(DESTDIR)$(bindir)/`echo $$p|sed 's/$(EXEEXT)$$//'|sed '$(transform)'|sed 's/$$/$(EXEEXT)/'`; \ + else :; fi; \ + done + +uninstall-binPROGRAMS: + @$(NORMAL_UNINSTALL) + list='$(bin_PROGRAMS)'; for p in $$list; do \ + rm -f $(DESTDIR)$(bindir)/`echo $$p|sed 's/$(EXEEXT)$$//'|sed '$(transform)'|sed 's/$$/$(EXEEXT)/'`; \ + done + +mostlyclean-noinstPROGRAMS: + +clean-noinstPROGRAMS: + -test -z "$(noinst_PROGRAMS)" || rm -f $(noinst_PROGRAMS) + +distclean-noinstPROGRAMS: + +maintainer-clean-noinstPROGRAMS: + +tconf: $(tconf_OBJECTS) $(tconf_DEPENDENCIES) + @rm -f tconf + $(LINK) $(tconf_LDFLAGS) $(tconf_OBJECTS) $(tconf_LDADD) $(LIBS) + +tphrase: $(tphrase_OBJECTS) $(tphrase_DEPENDENCIES) + @rm -f tphrase + $(LINK) $(tphrase_LDFLAGS) $(tphrase_OBJECTS) $(tphrase_LDADD) $(LIBS) + +srvtest: $(srvtest_OBJECTS) $(srvtest_DEPENDENCIES) + @rm -f srvtest + $(LINK) $(srvtest_LDFLAGS) $(srvtest_OBJECTS) $(srvtest_LDADD) $(LIBS) + +clitest: $(clitest_OBJECTS) $(clitest_DEPENDENCIES) + @rm -f clitest + $(LINK) $(clitest_LDFLAGS) $(clitest_OBJECTS) $(clitest_LDADD) $(LIBS) + +install-includeHEADERS: $(include_HEADERS) + @$(NORMAL_INSTALL) + $(mkinstalldirs) $(DESTDIR)$(includedir) + @list='$(include_HEADERS)'; for p in $$list; do \ + if test -f "$$p"; then d= ; else d="$(srcdir)/"; fi; \ + echo " $(INSTALL_DATA) $$d$$p $(DESTDIR)$(includedir)/$$p"; \ + $(INSTALL_DATA) $$d$$p $(DESTDIR)$(includedir)/$$p; \ + done + +uninstall-includeHEADERS: + @$(NORMAL_UNINSTALL) + list='$(include_HEADERS)'; for p in $$list; do \ + rm -f $(DESTDIR)$(includedir)/$$p; \ + done + +tags: TAGS + +ID: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS)'; \ + unique=`for i in $$list; do echo $$i; done | \ + awk ' { files[$$0] = 1; } \ + END { for (i in files) print i; }'`; \ + here=`pwd` && cd $(srcdir) \ + && mkid -f$$here/ID $$unique $(LISP) + +TAGS: $(HEADERS) $(SOURCES) config.h.in $(TAGS_DEPENDENCIES) $(LISP) + tags=; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS)'; \ + unique=`for i in $$list; do echo $$i; done | \ + awk ' { files[$$0] = 1; } \ + END { for (i in files) print i; }'`; \ + test -z "$(ETAGS_ARGS)config.h.in$$unique$(LISP)$$tags" \ + || (cd $(srcdir) && etags $(ETAGS_ARGS) $$tags config.h.in $$unique $(LISP) -o $$here/TAGS) + +mostlyclean-tags: + +clean-tags: + +distclean-tags: + -rm -f TAGS ID + +maintainer-clean-tags: + +distdir = $(PACKAGE)-$(VERSION) +top_distdir = $(distdir) + +# This target untars the dist file and tries a VPATH configuration. Then +# it guarantees that the distribution is self-contained by making another +# tarfile. +distcheck: dist + -rm -rf $(distdir) + GZIP=$(GZIP_ENV) $(TAR) zxf $(distdir).tar.gz + mkdir $(distdir)/=build + mkdir $(distdir)/=inst + dc_install_base=`cd $(distdir)/=inst && pwd`; \ + cd $(distdir)/=build \ + && ../configure --srcdir=.. --prefix=$$dc_install_base \ + && $(MAKE) $(AM_MAKEFLAGS) \ + && $(MAKE) $(AM_MAKEFLAGS) dvi \ + && $(MAKE) $(AM_MAKEFLAGS) check \ + && $(MAKE) $(AM_MAKEFLAGS) install \ + && $(MAKE) $(AM_MAKEFLAGS) installcheck \ + && $(MAKE) $(AM_MAKEFLAGS) dist + -rm -rf $(distdir) + @banner="$(distdir).tar.gz is ready for distribution"; \ + dashes=`echo "$$banner" | sed s/./=/g`; \ + echo "$$dashes"; \ + echo "$$banner"; \ + echo "$$dashes" +dist: distdir + -chmod -R a+r $(distdir) + GZIP=$(GZIP_ENV) $(TAR) chozf $(distdir).tar.gz $(distdir) + -rm -rf $(distdir) +dist-all: distdir + -chmod -R a+r $(distdir) + GZIP=$(GZIP_ENV) $(TAR) chozf $(distdir).tar.gz $(distdir) + -rm -rf $(distdir) +distdir: $(DISTFILES) + -rm -rf $(distdir) + mkdir $(distdir) + -chmod 777 $(distdir) + @for file in $(DISTFILES); do \ + d=$(srcdir); \ + if test -d $$d/$$file; then \ + cp -pr $$d/$$file $(distdir)/$$file; \ + else \ + test -f $(distdir)/$$file \ + || ln $$d/$$file $(distdir)/$$file 2> /dev/null \ + || cp -p $$d/$$file $(distdir)/$$file || :; \ + fi; \ + done +info-am: +info: info-am +dvi-am: +dvi: dvi-am +check-am: all-am +check: check-am +installcheck-am: +installcheck: installcheck-am +all-recursive-am: config.h + $(MAKE) $(AM_MAKEFLAGS) all-recursive + +install-exec-am: install-libLIBRARIES install-binPROGRAMS +install-exec: install-exec-am + +install-data-am: install-includeHEADERS +install-data: install-data-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am +install: install-am +uninstall-am: uninstall-libLIBRARIES uninstall-binPROGRAMS \ + uninstall-includeHEADERS +uninstall: uninstall-am +all-am: Makefile $(LIBRARIES) $(PROGRAMS) $(HEADERS) config.h +all-redirect: all-am +install-strip: + $(MAKE) $(AM_MAKEFLAGS) INSTALL_STRIP_FLAG=-s install +installdirs: + $(mkinstalldirs) $(DESTDIR)$(libdir) $(DESTDIR)$(bindir) \ + $(DESTDIR)$(includedir) + + +mostlyclean-generic: + +clean-generic: + +distclean-generic: + -rm -f Makefile $(CONFIG_CLEAN_FILES) + -rm -f config.cache config.log stamp-h stamp-h[0-9]* + +maintainer-clean-generic: +mostlyclean-am: mostlyclean-hdr mostlyclean-libLIBRARIES \ + mostlyclean-compile mostlyclean-binPROGRAMS \ + mostlyclean-noinstPROGRAMS mostlyclean-tags \ + mostlyclean-generic + +mostlyclean: mostlyclean-am + +clean-am: clean-hdr clean-libLIBRARIES clean-compile clean-binPROGRAMS \ + clean-noinstPROGRAMS clean-tags clean-generic \ + mostlyclean-am + +clean: clean-am + +distclean-am: distclean-hdr distclean-libLIBRARIES distclean-compile \ + distclean-binPROGRAMS distclean-noinstPROGRAMS \ + distclean-tags distclean-generic clean-am + +distclean: distclean-am + -rm -f config.status + +maintainer-clean-am: maintainer-clean-hdr maintainer-clean-libLIBRARIES \ + maintainer-clean-compile maintainer-clean-binPROGRAMS \ + maintainer-clean-noinstPROGRAMS maintainer-clean-tags \ + maintainer-clean-generic distclean-am + @echo "This command is intended for maintainers to use;" + @echo "it deletes files that may require special tools to rebuild." + +maintainer-clean: maintainer-clean-am + -rm -f config.status + +.PHONY: mostlyclean-hdr distclean-hdr clean-hdr maintainer-clean-hdr \ +mostlyclean-libLIBRARIES distclean-libLIBRARIES clean-libLIBRARIES \ +maintainer-clean-libLIBRARIES uninstall-libLIBRARIES \ +install-libLIBRARIES mostlyclean-compile distclean-compile \ +clean-compile maintainer-clean-compile mostlyclean-binPROGRAMS \ +distclean-binPROGRAMS clean-binPROGRAMS maintainer-clean-binPROGRAMS \ +uninstall-binPROGRAMS install-binPROGRAMS mostlyclean-noinstPROGRAMS \ +distclean-noinstPROGRAMS clean-noinstPROGRAMS \ +maintainer-clean-noinstPROGRAMS uninstall-includeHEADERS \ +install-includeHEADERS tags mostlyclean-tags distclean-tags clean-tags \ +maintainer-clean-tags distdir info-am info dvi-am dvi check check-am \ +installcheck-am installcheck all-recursive-am install-exec-am \ +install-exec install-data-am install-data install-am install \ +uninstall-am uninstall all-redirect all-am all installdirs \ +mostlyclean-generic distclean-generic clean-generic \ +maintainer-clean-generic clean mostlyclean distclean maintainer-clean + + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/package/network/services/ead/src/tinysrp/Notes b/package/network/services/ead/src/tinysrp/Notes new file mode 100644 index 0000000000..a8620aa700 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/Notes @@ -0,0 +1,110 @@ +t_* stuff is from the srp 1.7.1 dist +bn_* stuff is from openssl 0.9.6 + +(The 7 in libtinysrp's version number reflects the srp version.) + +Licensing and copyright for srp and openssl are as indicated in the relevant +source files. Everything else here is GPL, including the tinysrp protocol. + +Changelog since initial release: + +0.7.4 more robust terminal modes in t_getpass + a potential buffer overflow in tinysrp +0.7.5 uninitialized pointer bug in tconf + +Changes from the base srp and openssl distributions: + +I've removed everything that's not needed for client/server operations, and +all the bn_* stuff that's only used for prime generation has been moved to +t_conf.c, which isn't part of the library anymore. Also, all the routines +used for passphrase file maintenance have been moved to tphrase.c. + +The library has been optimized (a bit) for space instead of speed. Since +authentication is usually only done once, this isn't a big problem. Modern +CPUs are plenty fast for this task, and even 100 MHz CPUs are fine. If you +really need the speed, get the regular distributions. + +Note that if the server sends the client a prime that the client doesn't +know about, the client MUST test for primality. Since this is pretty +expensive, and takes 30 seconds on a 100 MHz machine, and uses lots of code, +I've removed that ability from the client. So only KNOWN primes can be +used. You can still generate new ones with tconf, but you have to install +them in the table of known primes (pre_params) in t_getconf.c that's common +to the client and server, and recompile. The configuration file is gone. + +The default prime (the last entry in the table) is 1024 bits; there are +others with more bits but they will be correspondingly slower. + +The default tpasswd file (which is an ascii file that may be editted with a +regular text editor) contains two users: moo (passphrase "glub glub") and +"new user" (passphrase "this is a test"). Passphrases may be added or +changed with tphrase; you can also change the user's prime. To delete a +user, edit the tpasswd file and remove that line. The tpasswd file's +default name is DEFAULT_PASSWD in t_pwd.h. Note that you can't change a +user's username by editting the file: the username is encoded in the +verifier. If you change a username you must set a new passphrase with +tphrase. + +Here is an example session, using the supplied srvtest and clitest. First, +start both programs in different windows, and enter the user names. Normally, +the client would send the username to the server. Server lines are marked +with S>, client lines with C>. + +S> % srvtest +S> Enter username: moo +S> index (to client): 5 +S> salt (to client): 19AI0Hc9jEkdFc + +C> % clitest +C> Enter username: moo +C> Enter index (from server): 5 +C> Enter salt (from server): 19AI0Hc9jEkdFc + +The server reports the index and salt values used for that user. They +are sent over the network to the client. (Simulate this by cutting and +pasting from one window to the other.) + +C> A (to server): 5wCDXRxLIv/zLazYfKupV/OY3BlhTZuJ71wVgI0HcL1kSJEpkMuWF.xEz/BV2wlJl7vk5Eoz9KMS1ccnaatsVP5D6CBm7UA.yVB59EQFN0dNBirvX29NAFdtdMsMppo5tHRy987XjJWrWSLpeibq6emr.gP8nYyX75GQqSiMY1j +C> Enter password: + +S> Enter A (from client): 5wCDXRxLIv/zLazYfKupV/OY3BlhTZuJ71wVgI0HcL1kSJEpkMuWF.xEz/BV2wlJl7vk5Eoz9KMS1ccnaatsVP5D6CBm7UA.yVB59EQFN0dNBirvX29NAFdtdMsMppo5tHRy987XjJWrWSLpeibq6emr.gP8nYyX75GQqSiMY1j + +Now the client calculates A and sends it to the server, and while the +server is munching on that, the client gets the password from the user. + +S> B (to client): 9dcCpulxQAbaDXI0NHWY6B.QH6B9fsoXs/x/5SCNBNJm/6H6bYfbVrwNmdquhLZjYMvpcgGc2mBYqL77RNfw1kVQo17//GfsByECBIjRnrAn02ffX9Y/llJcfscAQiii0hyZhJf9PT5wE7pC7WUjIgSqckIZ0JLNDbSr7fJcrgw +S> Session key: ebbcf3a45c968defdcfff6e144ad8d4f5412167c9716e79cbf7cacfe18257947ad46fa5d6418a1fd + +The server now calculates B and sends it to the client. The session key +is not sent -- it is a shared secret that can be used for encryption. + +C> Enter B (from server): 9dcCpulxQAbaDXI0NHWY6B.QH6B9fsoXs/x/5SCNBNJm/6H6bYfbVrwNmdquhLZjYMvpcgGc2mBYqL77RNfw1kVQo17//GfsByECBIjRnrAn02ffX9Y/llJcfscAQiii0hyZhJf9PT5wE7pC7WUjIgSqckIZ0JLNDbSr7fJcrgw +C> Session key: ebbcf3a45c968defdcfff6e144ad8d4f5412167c9716e79cbf7cacfe18257947ad46fa5d6418a1fd +C> Response (to server): b9ea99094a176c4be28eb469982066cc7146d180 + +The client uses the B value to calculate its own copy of the shared secret +session key, and sends a response to the server proving that it does know +the correct key. + +S> Enter response (from client): b9ea99094a176c4be28eb469982066cc7146d180 +S> Authentication successful. +S> Response (to client): cd46c839ccad2d0c76f3ca1905ae8ceda8d1c1dc + +The server authenticates the client. (You're in!) + +C> Enter server response: cd46c839ccad2d0c76f3ca1905ae8ceda8d1c1dc +C> Server authentication successful. + +The client authenticates the server (prevents server spoofing in the case +where the session key isn't used to encrypt the channel -- a spoofed server +might just respond with random values and _pretend_ to authenticate the +client; but the spoofed server won't know the session key and this check +catches that). + +Final note: + +Remember that many breaches of security involve buggy software, such as +servers susceptible to buffer overflow exploits that totally bypass any +passphrase, secure or not. If an attacker roots your client, or the server, +no form of authentication will work. Consider MAC-based schemes if this +worries you. diff --git a/package/network/services/ead/src/tinysrp/acconfig.h b/package/network/services/ead/src/tinysrp/acconfig.h new file mode 100644 index 0000000000..b74aed08f3 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/acconfig.h @@ -0,0 +1,9 @@ +#undef SHA1HANDSOFF + +#undef POSIX_TERMIOS + +#undef POSIX_SIGTYPE + +#undef VERSION + +#undef volatile diff --git a/package/network/services/ead/src/tinysrp/acinclude.m4 b/package/network/services/ead/src/tinysrp/acinclude.m4 new file mode 100644 index 0000000000..e0d0d04df5 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/acinclude.m4 @@ -0,0 +1,27 @@ +dnl +dnl check for signal type +dnl +dnl AC_RETSIGTYPE isn't quite right, but almost. +dnl +define(TYPE_SIGNAL,[ +AC_MSG_CHECKING([POSIX signal handlers]) +AC_CACHE_VAL(cv_has_posix_signals, +[AC_TRY_COMPILE( +[#include <sys/types.h> +#include <signal.h> +#ifdef signal +#undef signal +#endif +extern void (*signal ()) ();], [], +cv_has_posix_signals=yes, cv_has_posix_signals=no)]) +AC_MSG_RESULT($cv_has_posix_signals) +if test $cv_has_posix_signals = yes; then + AC_DEFINE(RETSIGTYPE, void, [Return type is void]) + AC_DEFINE(POSIX_SIGTYPE, [], [Have POSIX signals]) +else + if test $ac_cv_type_signal = void; then + AC_DEFINE(RETSIGTYPE, void, [Return type is void]) + else + AC_DEFINE(RETSIGTYPE, int, [Return type is int]) + fi +fi])dnl diff --git a/package/network/services/ead/src/tinysrp/aclocal.m4 b/package/network/services/ead/src/tinysrp/aclocal.m4 new file mode 100644 index 0000000000..703fce4b77 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/aclocal.m4 @@ -0,0 +1,157 @@ +dnl aclocal.m4 generated automatically by aclocal 1.4a + +dnl Copyright (C) 1994, 1995-8, 1999 Free Software Foundation, Inc. +dnl This file is free software; the Free Software Foundation +dnl gives unlimited permission to copy and/or distribute it, +dnl with or without modifications, as long as this notice is preserved. + +dnl This program is distributed in the hope that it will be useful, +dnl but WITHOUT ANY WARRANTY, to the extent permitted by law; without +dnl even the implied warranty of MERCHANTABILITY or FITNESS FOR A +dnl PARTICULAR PURPOSE. + +dnl +dnl check for signal type +dnl +dnl AC_RETSIGTYPE isn't quite right, but almost. +dnl +define(TYPE_SIGNAL,[ +AC_MSG_CHECKING([POSIX signal handlers]) +AC_CACHE_VAL(cv_has_posix_signals, +[AC_TRY_COMPILE( +[#include <sys/types.h> +#include <signal.h> +#ifdef signal +#undef signal +#endif +extern void (*signal ()) ();], [], +cv_has_posix_signals=yes, cv_has_posix_signals=no)]) +AC_MSG_RESULT($cv_has_posix_signals) +if test $cv_has_posix_signals = yes; then + AC_DEFINE(RETSIGTYPE, void, [Return type is void]) + AC_DEFINE(POSIX_SIGTYPE, [], [Have POSIX signals]) +else + if test $ac_cv_type_signal = void; then + AC_DEFINE(RETSIGTYPE, void, [Return type is void]) + else + AC_DEFINE(RETSIGTYPE, int, [Return type is int]) + fi +fi])dnl + +# Like AC_CONFIG_HEADER, but automatically create stamp file. + +AC_DEFUN(AM_CONFIG_HEADER, +[AC_PREREQ([2.12]) +AC_CONFIG_HEADER([$1]) +dnl When config.status generates a header, we must update the stamp-h file. +dnl This file resides in the same directory as the config header +dnl that is generated. We must strip everything past the first ":", +dnl and everything past the last "/". +AC_OUTPUT_COMMANDS(changequote(<<,>>)dnl +ifelse(patsubst(<<$1>>, <<[^ ]>>, <<>>), <<>>, +<<test -z "<<$>>CONFIG_HEADERS" || echo timestamp > patsubst(<<$1>>, <<^\([^:]*/\)?.*>>, <<\1>>)stamp-h<<>>dnl>>, +<<am_indx=1 +for am_file in <<$1>>; do + case " <<$>>CONFIG_HEADERS " in + *" <<$>>am_file "*<<)>> + echo timestamp > `echo <<$>>am_file | sed -e 's%:.*%%' -e 's%[^/]*$%%'`stamp-h$am_indx + ;; + esac + am_indx=`expr "<<$>>am_indx" + 1` +done<<>>dnl>>) +changequote([,]))]) + +# Do all the work for Automake. This macro actually does too much -- +# some checks are only needed if your package does certain things. +# But this isn't really a big deal. + +# serial 1 + +dnl Usage: +dnl AM_INIT_AUTOMAKE(package,version, [no-define]) + +AC_DEFUN(AM_INIT_AUTOMAKE, +[AC_REQUIRE([AC_PROG_INSTALL]) +dnl We require 2.13 because we rely on SHELL being computed by configure. +AC_PREREQ([2.13]) +PACKAGE=[$1] +AC_SUBST(PACKAGE) +VERSION=[$2] +AC_SUBST(VERSION) +dnl test to see if srcdir already configured +if test "`cd $srcdir && pwd`" != "`pwd`" && test -f $srcdir/config.status; then + AC_MSG_ERROR([source directory already configured; run "make distclean" there first]) +fi +ifelse([$3],, +AC_DEFINE_UNQUOTED(PACKAGE, "$PACKAGE", [Name of package]) +AC_DEFINE_UNQUOTED(VERSION, "$VERSION", [Version number of package])) +AC_REQUIRE([AM_SANITY_CHECK]) +AC_REQUIRE([AC_ARG_PROGRAM]) +dnl FIXME This is truly gross. +missing_dir=`cd $ac_aux_dir && pwd` +AM_MISSING_PROG(ACLOCAL, aclocal, $missing_dir) +AM_MISSING_PROG(AUTOCONF, autoconf, $missing_dir) +AM_MISSING_PROG(AUTOMAKE, automake, $missing_dir) +AM_MISSING_PROG(AUTOHEADER, autoheader, $missing_dir) +AM_MISSING_PROG(MAKEINFO, makeinfo, $missing_dir) +AC_REQUIRE([AC_PROG_MAKE_SET])]) + +# +# Check to make sure that the build environment is sane. +# + +AC_DEFUN(AM_SANITY_CHECK, +[AC_MSG_CHECKING([whether build environment is sane]) +# Just in case +sleep 1 +echo timestamp > conftestfile +# Do `set' in a subshell so we don't clobber the current shell's +# arguments. Must try -L first in case configure is actually a +# symlink; some systems play weird games with the mod time of symlinks +# (eg FreeBSD returns the mod time of the symlink's containing +# directory). +if ( + set X `ls -Lt $srcdir/configure conftestfile 2> /dev/null` + if test "[$]*" = "X"; then + # -L didn't work. + set X `ls -t $srcdir/configure conftestfile` + fi + if test "[$]*" != "X $srcdir/configure conftestfile" \ + && test "[$]*" != "X conftestfile $srcdir/configure"; then + + # If neither matched, then we have a broken ls. This can happen + # if, for instance, CONFIG_SHELL is bash and it inherits a + # broken ls alias from the environment. This has actually + # happened. Such a system could not be considered "sane". + AC_MSG_ERROR([ls -t appears to fail. Make sure there is not a broken +alias in your environment]) + fi + + test "[$]2" = conftestfile + ) +then + # Ok. + : +else + AC_MSG_ERROR([newly created file is older than distributed files! +Check your system clock]) +fi +rm -f conftest* +AC_MSG_RESULT(yes)]) + +dnl AM_MISSING_PROG(NAME, PROGRAM, DIRECTORY) +dnl The program must properly implement --version. +AC_DEFUN(AM_MISSING_PROG, +[AC_MSG_CHECKING(for working $2) +# Run test in a subshell; some versions of sh will print an error if +# an executable is not found, even if stderr is redirected. +# Redirect stdin to placate older versions of autoconf. Sigh. +if ($2 --version) < /dev/null > /dev/null 2>&1; then + $1=$2 + AC_MSG_RESULT(found) +else + $1="$3/missing $2" + AC_MSG_RESULT(missing) +fi +AC_SUBST($1)]) + diff --git a/package/network/services/ead/src/tinysrp/bn.h b/package/network/services/ead/src/tinysrp/bn.h new file mode 100644 index 0000000000..0144dd9617 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn.h @@ -0,0 +1,471 @@ +/* crypto/bn/bn.h */ +/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#ifndef HEADER_BN_H +#define HEADER_BN_H + +#include <stdio.h> /* FILE */ +#include "config.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef VMS +#undef BN_LLONG /* experimental, so far... */ +#endif + +#undef BN_MUL_COMBA +#undef BN_SQR_COMBA +#undef BN_RECURSION +#undef RECP_MUL_MOD +#undef MONT_MUL_MOD + +#if defined(SIZEOF_LONG_LONG) && SIZEOF_LONG_LONG == 8 +# if SIZEOF_LONG == 4 +# define THIRTY_TWO_BIT +# else +# define SIXTY_FOUR_BIT_LONG +# endif +#else +# if SIZEOF_LONG == 4 +# define THIRTY_TWO_BIT +# endif +#endif + +#undef BN_LLONG + +/* assuming long is 64bit - this is the DEC Alpha + * unsigned long long is only 64 bits :-(, don't define + * BN_LLONG for the DEC Alpha */ +#ifdef SIXTY_FOUR_BIT_LONG +#define BN_ULLONG unsigned long long +#define BN_ULONG unsigned long +#define BN_LONG long +#define BN_BITS 128 +#define BN_BYTES 8 +#define BN_BITS2 64 +#define BN_BITS4 32 +#define BN_MASK (0xffffffffffffffffffffffffffffffffLL) +#define BN_MASK2 (0xffffffffffffffffL) +#define BN_MASK2l (0xffffffffL) +#define BN_MASK2h (0xffffffff00000000L) +#define BN_MASK2h1 (0xffffffff80000000L) +#define BN_TBIT (0x8000000000000000L) +#define BN_DEC_CONV (10000000000000000000UL) +#define BN_DEC_FMT1 "%lu" +#define BN_DEC_FMT2 "%019lu" +#define BN_DEC_NUM 19 +#endif + +/* This is where the long long data type is 64 bits, but long is 32. + * For machines where there are 64bit registers, this is the mode to use. + * IRIX, on R4000 and above should use this mode, along with the relevant + * assembler code :-). Do NOT define BN_LLONG. + */ +#ifdef SIXTY_FOUR_BIT +#undef BN_LLONG +#undef BN_ULLONG +#define BN_ULONG unsigned long long +#define BN_LONG long long +#define BN_BITS 128 +#define BN_BYTES 8 +#define BN_BITS2 64 +#define BN_BITS4 32 +#define BN_MASK2 (0xffffffffffffffffLL) +#define BN_MASK2l (0xffffffffL) +#define BN_MASK2h (0xffffffff00000000LL) +#define BN_MASK2h1 (0xffffffff80000000LL) +#define BN_TBIT (0x8000000000000000LL) +#define BN_DEC_CONV (10000000000000000000LL) +#define BN_DEC_FMT1 "%llu" +#define BN_DEC_FMT2 "%019llu" +#define BN_DEC_NUM 19 +#endif + +#ifdef THIRTY_TWO_BIT +#if defined(WIN32) && !defined(__GNUC__) +#define BN_ULLONG unsigned _int64 +#else +#define BN_ULLONG unsigned long long +#endif +#define BN_ULONG unsigned long +#define BN_LONG long +#define BN_BITS 64 +#define BN_BYTES 4 +#define BN_BITS2 32 +#define BN_BITS4 16 +#ifdef WIN32 +/* VC++ doesn't like the LL suffix */ +#define BN_MASK (0xffffffffffffffffL) +#else +#define BN_MASK (0xffffffffffffffffLL) +#endif +#define BN_MASK2 (0xffffffffL) +#define BN_MASK2l (0xffff) +#define BN_MASK2h1 (0xffff8000L) +#define BN_MASK2h (0xffff0000L) +#define BN_TBIT (0x80000000L) +#define BN_DEC_CONV (1000000000L) +#define BN_DEC_FMT1 "%lu" +#define BN_DEC_FMT2 "%09lu" +#define BN_DEC_NUM 9 +#endif + +#ifdef SIXTEEN_BIT +#ifndef BN_DIV2W +#define BN_DIV2W +#endif +#define BN_ULLONG unsigned long +#define BN_ULONG unsigned short +#define BN_LONG short +#define BN_BITS 32 +#define BN_BYTES 2 +#define BN_BITS2 16 +#define BN_BITS4 8 +#define BN_MASK (0xffffffff) +#define BN_MASK2 (0xffff) +#define BN_MASK2l (0xff) +#define BN_MASK2h1 (0xff80) +#define BN_MASK2h (0xff00) +#define BN_TBIT (0x8000) +#define BN_DEC_CONV (100000) +#define BN_DEC_FMT1 "%u" +#define BN_DEC_FMT2 "%05u" +#define BN_DEC_NUM 5 +#endif + +#ifdef EIGHT_BIT +#ifndef BN_DIV2W +#define BN_DIV2W +#endif +#define BN_ULLONG unsigned short +#define BN_ULONG unsigned char +#define BN_LONG char +#define BN_BITS 16 +#define BN_BYTES 1 +#define BN_BITS2 8 +#define BN_BITS4 4 +#define BN_MASK (0xffff) +#define BN_MASK2 (0xff) +#define BN_MASK2l (0xf) +#define BN_MASK2h1 (0xf8) +#define BN_MASK2h (0xf0) +#define BN_TBIT (0x80) +#define BN_DEC_CONV (100) +#define BN_DEC_FMT1 "%u" +#define BN_DEC_FMT2 "%02u" +#define BN_DEC_NUM 2 +#endif + +#define BN_DEFAULT_BITS 1280 + +#ifdef BIGNUM +#undef BIGNUM +#endif + +#define BN_FLG_MALLOCED 0x01 +#define BN_FLG_STATIC_DATA 0x02 +#define BN_FLG_FREE 0x8000 /* used for debuging */ +#define BN_set_flags(b,n) ((b)->flags|=(n)) +#define BN_get_flags(b,n) ((b)->flags&(n)) + +typedef struct bignum_st + { + BN_ULONG *d; /* Pointer to an array of 'BN_BITS2' bit chunks. */ + int top; /* Index of last used d +1. */ + /* The next are internal book keeping for bn_expand. */ + int dmax; /* Size of the d array. */ + int neg; /* one if the number is negative */ + int flags; + } BIGNUM; + +/* Used for temp variables */ +#define BN_CTX_NUM 12 +#define BN_CTX_NUM_POS 12 +typedef struct bignum_ctx + { + int tos; + BIGNUM bn[BN_CTX_NUM]; + int flags; + int depth; + int pos[BN_CTX_NUM_POS]; + int too_many; + } BN_CTX; + +/* Used for montgomery multiplication */ +typedef struct bn_mont_ctx_st + { + int ri; /* number of bits in R */ + BIGNUM RR; /* used to convert to montgomery form */ + BIGNUM N; /* The modulus */ + BIGNUM Ni; /* R*(1/R mod N) - N*Ni = 1 + * (Ni is only stored for bignum algorithm) */ + BN_ULONG n0; /* least significant word of Ni */ + int flags; + } BN_MONT_CTX; + +/* Used for reciprocal division/mod functions + * It cannot be shared between threads + */ +typedef struct bn_recp_ctx_st + { + BIGNUM N; /* the divisor */ + BIGNUM Nr; /* the reciprocal */ + int num_bits; + int shift; + int flags; + } BN_RECP_CTX; + +#define BN_to_montgomery(r,a,mont,ctx) BN_mod_mul_montgomery(\ + r,a,&((mont)->RR),(mont),ctx) + +#define BN_prime_checks 0 /* default: select number of iterations + based on the size of the number */ + +/* number of Miller-Rabin iterations for an error rate of less than 2^-80 + * for random 'b'-bit input, b >= 100 (taken from table 4.4 in the Handbook + * of Applied Cryptography [Menezes, van Oorschot, Vanstone; CRC Press 1996]; + * original paper: Damgaard, Landrock, Pomerance: Average case error estimates + * for the strong probable prime test. -- Math. Comp. 61 (1993) 177-194) */ +#define BN_prime_checks_for_size(b) ((b) >= 1300 ? 2 : \ + (b) >= 850 ? 3 : \ + (b) >= 650 ? 4 : \ + (b) >= 550 ? 5 : \ + (b) >= 450 ? 6 : \ + (b) >= 400 ? 7 : \ + (b) >= 350 ? 8 : \ + (b) >= 300 ? 9 : \ + (b) >= 250 ? 12 : \ + (b) >= 200 ? 15 : \ + (b) >= 150 ? 18 : \ + /* b >= 100 */ 27) + +#define BN_num_bytes(a) ((BN_num_bits(a)+7)/8) +#define BN_is_word(a,w) (((a)->top == 1) && ((a)->d[0] == (BN_ULONG)(w))) +#define BN_is_zero(a) (((a)->top == 0) || BN_is_word(a,0)) +#define BN_is_one(a) (BN_is_word((a),1)) +#define BN_is_odd(a) (((a)->top > 0) && ((a)->d[0] & 1)) +#define BN_one(a) (BN_set_word((a),1)) +#define BN_zero(a) (BN_set_word((a),0)) + +BIGNUM *BN_value_one(void); +char * BN_options(void); +BN_CTX *BN_CTX_new(void); +void BN_CTX_init(BN_CTX *c); +void BN_CTX_free(BN_CTX *c); +void BN_CTX_start(BN_CTX *ctx); +BIGNUM *BN_CTX_get(BN_CTX *ctx); +void BN_CTX_end(BN_CTX *ctx); +int BN_rand(BIGNUM *rnd, int bits, int top,int bottom); +int BN_pseudo_rand(BIGNUM *rnd, int bits, int top,int bottom); +int BN_num_bits(const BIGNUM *a); +int BN_num_bits_word(BN_ULONG); +BIGNUM *BN_new(void); +void BN_init(BIGNUM *); +void BN_clear_free(BIGNUM *a); +BIGNUM *BN_copy(BIGNUM *a, const BIGNUM *b); +BIGNUM *BN_bin2bn(const unsigned char *s,int len,BIGNUM *ret); +int BN_bn2bin(const BIGNUM *a, unsigned char *to); +int BN_sub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b); +int BN_usub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b); +int BN_uadd(BIGNUM *r, const BIGNUM *a, const BIGNUM *b); +int BN_add(BIGNUM *r, const BIGNUM *a, const BIGNUM *b); +int BN_mod(BIGNUM *rem, const BIGNUM *m, const BIGNUM *d, BN_CTX *ctx); +int BN_div(BIGNUM *dv, BIGNUM *rem, const BIGNUM *m, const BIGNUM *d, + BN_CTX *ctx); +int BN_mul(BIGNUM *r, BIGNUM *a, BIGNUM *b, BN_CTX *ctx); +int BN_sqr(BIGNUM *r, BIGNUM *a,BN_CTX *ctx); +BN_ULONG BN_mod_word(const BIGNUM *a, BN_ULONG w); +BN_ULONG BN_div_word(BIGNUM *a, BN_ULONG w); +int BN_mul_word(BIGNUM *a, BN_ULONG w); +int BN_add_word(BIGNUM *a, BN_ULONG w); +int BN_sub_word(BIGNUM *a, BN_ULONG w); +int BN_set_word(BIGNUM *a, BN_ULONG w); +BN_ULONG BN_get_word(BIGNUM *a); +int BN_cmp(const BIGNUM *a, const BIGNUM *b); +void BN_free(BIGNUM *a); +int BN_is_bit_set(const BIGNUM *a, int n); +int BN_lshift(BIGNUM *r, const BIGNUM *a, int n); +int BN_lshift1(BIGNUM *r, BIGNUM *a); +int BN_exp(BIGNUM *r, BIGNUM *a, BIGNUM *p,BN_CTX *ctx); +int BN_mod_exp(BIGNUM *r, BIGNUM *a, const BIGNUM *p, + const BIGNUM *m,BN_CTX *ctx); +int BN_mod_exp_mont(BIGNUM *r, BIGNUM *a, const BIGNUM *p, + const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx); +int BN_mod_exp_mont_word(BIGNUM *r, BN_ULONG a, const BIGNUM *p, + const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx); +int BN_mod_exp_simple(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, + const BIGNUM *m,BN_CTX *ctx); +int BN_mask_bits(BIGNUM *a,int n); +int BN_mod_mul(BIGNUM *ret, BIGNUM *a, BIGNUM *b, const BIGNUM *m, BN_CTX *ctx); +int BN_reciprocal(BIGNUM *r, BIGNUM *m, int len, BN_CTX *ctx); +int BN_rshift(BIGNUM *r, BIGNUM *a, int n); +int BN_rshift1(BIGNUM *r, BIGNUM *a); +void BN_clear(BIGNUM *a); +BIGNUM *BN_dup(const BIGNUM *a); +int BN_ucmp(const BIGNUM *a, const BIGNUM *b); +int BN_set_bit(BIGNUM *a, int n); +int BN_clear_bit(BIGNUM *a, int n); +int BN_gcd(BIGNUM *r,BIGNUM *in_a,BIGNUM *in_b,BN_CTX *ctx); +BIGNUM *BN_mod_inverse(BIGNUM *ret,BIGNUM *a, const BIGNUM *n,BN_CTX *ctx); +BIGNUM *BN_generate_prime(BIGNUM *ret,int bits,int safe,BIGNUM *add, + BIGNUM *rem,void (*callback)(int,int,void *),void *cb_arg); +int BN_is_prime(const BIGNUM *p,int nchecks, + void (*callback)(int,int,void *), + BN_CTX *ctx,void *cb_arg); +int BN_is_prime_fasttest(const BIGNUM *p,int nchecks, + void (*callback)(int,int,void *),BN_CTX *ctx,void *cb_arg, + int do_trial_division); + +BN_MONT_CTX *BN_MONT_CTX_new(void ); +void BN_MONT_CTX_init(BN_MONT_CTX *ctx); +int BN_mod_mul_montgomery(BIGNUM *r,BIGNUM *a,BIGNUM *b,BN_MONT_CTX *mont, + BN_CTX *ctx); +int BN_from_montgomery(BIGNUM *r,BIGNUM *a,BN_MONT_CTX *mont,BN_CTX *ctx); +void BN_MONT_CTX_free(BN_MONT_CTX *mont); +int BN_MONT_CTX_set(BN_MONT_CTX *mont,const BIGNUM *modulus,BN_CTX *ctx); +BN_MONT_CTX *BN_MONT_CTX_copy(BN_MONT_CTX *to,BN_MONT_CTX *from); + +void BN_set_params(int mul,int high,int low,int mont); +int BN_get_params(int which); /* 0, mul, 1 high, 2 low, 3 mont */ + +void BN_RECP_CTX_init(BN_RECP_CTX *recp); +BN_RECP_CTX *BN_RECP_CTX_new(void); +void BN_RECP_CTX_free(BN_RECP_CTX *recp); +int BN_RECP_CTX_set(BN_RECP_CTX *recp,const BIGNUM *rdiv,BN_CTX *ctx); +int BN_mod_mul_reciprocal(BIGNUM *r, BIGNUM *x, BIGNUM *y, + BN_RECP_CTX *recp,BN_CTX *ctx); +int BN_mod_exp_recp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, + const BIGNUM *m, BN_CTX *ctx); +int BN_div_recp(BIGNUM *dv, BIGNUM *rem, BIGNUM *m, + BN_RECP_CTX *recp, BN_CTX *ctx); + +/* library internal functions */ + +#define bn_expand(a,bits) ((((((bits+BN_BITS2-1))/BN_BITS2)) <= (a)->dmax)?\ + (a):bn_expand2((a),(bits)/BN_BITS2+1)) +#define bn_wexpand(a,words) (((words) <= (a)->dmax)?(a):bn_expand2((a),(words))) +BIGNUM *bn_expand2(BIGNUM *a, int words); + +#define bn_fix_top(a) \ + { \ + BN_ULONG *ftl; \ + if ((a)->top > 0) \ + { \ + for (ftl= &((a)->d[(a)->top-1]); (a)->top > 0; (a)->top--) \ + if (*(ftl--)) break; \ + } \ + } + +BN_ULONG bn_mul_add_words(BN_ULONG *rp, BN_ULONG *ap, int num, BN_ULONG w); +BN_ULONG bn_mul_words(BN_ULONG *rp, BN_ULONG *ap, int num, BN_ULONG w); +void bn_sqr_words(BN_ULONG *rp, BN_ULONG *ap, int num); +BN_ULONG bn_div_words(BN_ULONG h, BN_ULONG l, BN_ULONG d); +BN_ULONG bn_add_words(BN_ULONG *rp, BN_ULONG *ap, BN_ULONG *bp,int num); +BN_ULONG bn_sub_words(BN_ULONG *rp, BN_ULONG *ap, BN_ULONG *bp,int num); + +#ifdef BN_DEBUG + void bn_dump1(FILE *o, const char *a, BN_ULONG *b,int n); +# define bn_print(a) {fprintf(stderr, #a "="); BN_print_fp(stderr,a); \ + fprintf(stderr,"\n");} +# define bn_dump(a,n) bn_dump1(stderr,#a,a,n); +#else +# define bn_print(a) +# define bn_dump(a,b) +#endif + +/* BEGIN ERROR CODES */ +/* The following lines are auto generated by the script mkerr.pl. Any changes + * made after this point may be overwritten when the script is next run. + */ + +/* Error codes for the BN functions. */ + +/* Function codes. */ +#define BN_F_BN_CTX_GET 116 +#define BN_F_BN_CTX_NEW 106 +#define BN_F_BN_DIV 107 +#define BN_F_BN_EXPAND2 108 +#define BN_F_BN_MOD_EXP2_MONT 118 +#define BN_F_BN_MOD_EXP_MONT 109 +#define BN_F_BN_MOD_EXP_MONT_WORD 117 +#define BN_F_BN_MOD_INVERSE 110 +#define BN_F_BN_MOD_MUL_RECIPROCAL 111 +#define BN_F_BN_MPI2BN 112 +#define BN_F_BN_NEW 113 +#define BN_F_BN_RAND 114 +#define BN_F_BN_USUB 115 + +/* Reason codes. */ +#define BN_R_ARG2_LT_ARG3 100 +#define BN_R_BAD_RECIPROCAL 101 +#define BN_R_CALLED_WITH_EVEN_MODULUS 102 +#define BN_R_DIV_BY_ZERO 103 +#define BN_R_ENCODING_ERROR 104 +#define BN_R_EXPAND_ON_STATIC_BIGNUM_DATA 105 +#define BN_R_INVALID_LENGTH 106 +#define BN_R_NOT_INITIALIZED 107 +#define BN_R_NO_INVERSE 108 +#define BN_R_TOO_MANY_TEMPORARY_VARIABLES 109 + +#ifdef __cplusplus +} +#endif +#endif + diff --git a/package/network/services/ead/src/tinysrp/bn_add.c b/package/network/services/ead/src/tinysrp/bn_add.c new file mode 100644 index 0000000000..aae4f2b938 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_add.c @@ -0,0 +1,305 @@ +/* crypto/bn/bn_add.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include <stdio.h> +#include "bn_lcl.h" + +/* r can == a or b */ +int BN_add(BIGNUM *r, const BIGNUM *a, const BIGNUM *b) + { + const BIGNUM *tmp; + + bn_check_top(a); + bn_check_top(b); + + /* a + b a+b + * a + -b a-b + * -a + b b-a + * -a + -b -(a+b) + */ + if (a->neg ^ b->neg) + { + /* only one is negative */ + if (a->neg) + { tmp=a; a=b; b=tmp; } + + /* we are now a - b */ + + if (BN_ucmp(a,b) < 0) + { + if (!BN_usub(r,b,a)) return(0); + r->neg=1; + } + else + { + if (!BN_usub(r,a,b)) return(0); + r->neg=0; + } + return(1); + } + + if (a->neg) /* both are neg */ + r->neg=1; + else + r->neg=0; + + if (!BN_uadd(r,a,b)) return(0); + return(1); + } + +/* unsigned add of b to a, r must be large enough */ +int BN_uadd(BIGNUM *r, const BIGNUM *a, const BIGNUM *b) + { + register int i; + int max,min; + BN_ULONG *ap,*bp,*rp,carry,t1; + const BIGNUM *tmp; + + bn_check_top(a); + bn_check_top(b); + + if (a->top < b->top) + { tmp=a; a=b; b=tmp; } + max=a->top; + min=b->top; + + if (bn_wexpand(r,max+1) == NULL) + return(0); + + r->top=max; + + + ap=a->d; + bp=b->d; + rp=r->d; + carry=0; + + carry=bn_add_words(rp,ap,bp,min); + rp+=min; + ap+=min; + bp+=min; + i=min; + + if (carry) + { + while (i < max) + { + i++; + t1= *(ap++); + if ((*(rp++)=(t1+1)&BN_MASK2) >= t1) + { + carry=0; + break; + } + } + if ((i >= max) && carry) + { + *(rp++)=1; + r->top++; + } + } + if (rp != ap) + { + for (; i<max; i++) + *(rp++)= *(ap++); + } + /* memcpy(rp,ap,sizeof(*ap)*(max-i));*/ + return(1); + } + +/* unsigned subtraction of b from a, a must be larger than b. */ +int BN_usub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b) + { + int max,min; + register BN_ULONG t1,t2,*ap,*bp,*rp; + int i,carry; +#if defined(IRIX_CC_BUG) && !defined(LINT) + int dummy; +#endif + + bn_check_top(a); + bn_check_top(b); + + if (a->top < b->top) /* hmm... should not be happening */ + { + return(0); + } + + max=a->top; + min=b->top; + if (bn_wexpand(r,max) == NULL) return(0); + + ap=a->d; + bp=b->d; + rp=r->d; + +#if 1 + carry=0; + for (i=0; i<min; i++) + { + t1= *(ap++); + t2= *(bp++); + if (carry) + { + carry=(t1 <= t2); + t1=(t1-t2-1)&BN_MASK2; + } + else + { + carry=(t1 < t2); + t1=(t1-t2)&BN_MASK2; + } +#if defined(IRIX_CC_BUG) && !defined(LINT) + dummy=t1; +#endif + *(rp++)=t1&BN_MASK2; + } +#else + carry=bn_sub_words(rp,ap,bp,min); + ap+=min; + bp+=min; + rp+=min; + i=min; +#endif + if (carry) /* subtracted */ + { + while (i < max) + { + i++; + t1= *(ap++); + t2=(t1-1)&BN_MASK2; + *(rp++)=t2; + if (t1 > t2) break; + } + } +#if 0 + memcpy(rp,ap,sizeof(*rp)*(max-i)); +#else + if (rp != ap) + { + for (;;) + { + if (i++ >= max) break; + rp[0]=ap[0]; + if (i++ >= max) break; + rp[1]=ap[1]; + if (i++ >= max) break; + rp[2]=ap[2]; + if (i++ >= max) break; + rp[3]=ap[3]; + rp+=4; + ap+=4; + } + } +#endif + + r->top=max; + bn_fix_top(r); + return(1); + } + +int BN_sub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b) + { + int max; + int add=0,neg=0; + const BIGNUM *tmp; + + bn_check_top(a); + bn_check_top(b); + + /* a - b a-b + * a - -b a+b + * -a - b -(a+b) + * -a - -b b-a + */ + if (a->neg) + { + if (b->neg) + { tmp=a; a=b; b=tmp; } + else + { add=1; neg=1; } + } + else + { + if (b->neg) { add=1; neg=0; } + } + + if (add) + { + if (!BN_uadd(r,a,b)) return(0); + r->neg=neg; + return(1); + } + + /* We are actually doing a - b :-) */ + + max=(a->top > b->top)?a->top:b->top; + if (bn_wexpand(r,max) == NULL) return(0); + if (BN_ucmp(a,b) < 0) + { + if (!BN_usub(r,b,a)) return(0); + r->neg=1; + } + else + { + if (!BN_usub(r,a,b)) return(0); + r->neg=0; + } + return(1); + } + diff --git a/package/network/services/ead/src/tinysrp/bn_asm.c b/package/network/services/ead/src/tinysrp/bn_asm.c new file mode 100644 index 0000000000..b24c9af7c4 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_asm.c @@ -0,0 +1,382 @@ +/* crypto/bn/bn_asm.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#ifndef BN_DEBUG +# undef NDEBUG /* avoid conflicting definitions */ +# define NDEBUG +#endif + +#include <stdio.h> +#include <assert.h> +#include "bn_lcl.h" + +#if defined(BN_LLONG) || defined(BN_UMULT_HIGH) + +BN_ULONG bn_mul_add_words(BN_ULONG *rp, BN_ULONG *ap, int num, BN_ULONG w) + { + BN_ULONG c1=0; + + assert(num >= 0); + if (num <= 0) return(c1); + + while (num&~3) + { + mul_add(rp[0],ap[0],w,c1); + mul_add(rp[1],ap[1],w,c1); + mul_add(rp[2],ap[2],w,c1); + mul_add(rp[3],ap[3],w,c1); + ap+=4; rp+=4; num-=4; + } + if (num) + { + mul_add(rp[0],ap[0],w,c1); if (--num==0) return c1; + mul_add(rp[1],ap[1],w,c1); if (--num==0) return c1; + mul_add(rp[2],ap[2],w,c1); return c1; + } + + return(c1); + } + +BN_ULONG bn_mul_words(BN_ULONG *rp, BN_ULONG *ap, int num, BN_ULONG w) + { + BN_ULONG c1=0; + + assert(num >= 0); + if (num <= 0) return(c1); + + while (num&~3) + { + mul(rp[0],ap[0],w,c1); + mul(rp[1],ap[1],w,c1); + mul(rp[2],ap[2],w,c1); + mul(rp[3],ap[3],w,c1); + ap+=4; rp+=4; num-=4; + } + if (num) + { + mul(rp[0],ap[0],w,c1); if (--num == 0) return c1; + mul(rp[1],ap[1],w,c1); if (--num == 0) return c1; + mul(rp[2],ap[2],w,c1); + } + return(c1); + } + +void bn_sqr_words(BN_ULONG *r, BN_ULONG *a, int n) + { + assert(n >= 0); + if (n <= 0) return; + while (n&~3) + { + sqr(r[0],r[1],a[0]); + sqr(r[2],r[3],a[1]); + sqr(r[4],r[5],a[2]); + sqr(r[6],r[7],a[3]); + a+=4; r+=8; n-=4; + } + if (n) + { + sqr(r[0],r[1],a[0]); if (--n == 0) return; + sqr(r[2],r[3],a[1]); if (--n == 0) return; + sqr(r[4],r[5],a[2]); + } + } + +#else /* !(defined(BN_LLONG) || defined(BN_UMULT_HIGH)) */ + +BN_ULONG bn_mul_add_words(BN_ULONG *rp, BN_ULONG *ap, int num, BN_ULONG w) + { + BN_ULONG c=0; + BN_ULONG bl,bh; + + assert(num >= 0); + if (num <= 0) return((BN_ULONG)0); + + bl=LBITS(w); + bh=HBITS(w); + + for (;;) + { + mul_add(rp[0],ap[0],bl,bh,c); + if (--num == 0) break; + mul_add(rp[1],ap[1],bl,bh,c); + if (--num == 0) break; + mul_add(rp[2],ap[2],bl,bh,c); + if (--num == 0) break; + mul_add(rp[3],ap[3],bl,bh,c); + if (--num == 0) break; + ap+=4; + rp+=4; + } + return(c); + } + +BN_ULONG bn_mul_words(BN_ULONG *rp, BN_ULONG *ap, int num, BN_ULONG w) + { + BN_ULONG carry=0; + BN_ULONG bl,bh; + + assert(num >= 0); + if (num <= 0) return((BN_ULONG)0); + + bl=LBITS(w); + bh=HBITS(w); + + for (;;) + { + mul(rp[0],ap[0],bl,bh,carry); + if (--num == 0) break; + mul(rp[1],ap[1],bl,bh,carry); + if (--num == 0) break; + mul(rp[2],ap[2],bl,bh,carry); + if (--num == 0) break; + mul(rp[3],ap[3],bl,bh,carry); + if (--num == 0) break; + ap+=4; + rp+=4; + } + return(carry); + } + +void bn_sqr_words(BN_ULONG *r, BN_ULONG *a, int n) + { + assert(n >= 0); + if (n <= 0) return; + for (;;) + { + sqr64(r[0],r[1],a[0]); + if (--n == 0) break; + + sqr64(r[2],r[3],a[1]); + if (--n == 0) break; + + sqr64(r[4],r[5],a[2]); + if (--n == 0) break; + + sqr64(r[6],r[7],a[3]); + if (--n == 0) break; + + a+=4; + r+=8; + } + } + +#endif /* !(defined(BN_LLONG) || defined(BN_UMULT_HIGH)) */ + +#if defined(BN_LLONG) && defined(BN_DIV2W) + +BN_ULONG bn_div_words(BN_ULONG h, BN_ULONG l, BN_ULONG d) + { + return((BN_ULONG)(((((BN_ULLONG)h)<<BN_BITS2)|l)/(BN_ULLONG)d)); + } + +#else + +/* Divide h,l by d and return the result. */ +/* I need to test this some more :-( */ +BN_ULONG bn_div_words(BN_ULONG h, BN_ULONG l, BN_ULONG d) + { + BN_ULONG dh,dl,q,ret=0,th,tl,t; + int i,count=2; + + if (d == 0) return(BN_MASK2); + + i=BN_num_bits_word(d); + assert((i == BN_BITS2) || (h > (BN_ULONG)1<<i)); + + i=BN_BITS2-i; + if (h >= d) h-=d; + + if (i) + { + d<<=i; + h=(h<<i)|(l>>(BN_BITS2-i)); + l<<=i; + } + dh=(d&BN_MASK2h)>>BN_BITS4; + dl=(d&BN_MASK2l); + for (;;) + { + if ((h>>BN_BITS4) == dh) + q=BN_MASK2l; + else + q=h/dh; + + th=q*dh; + tl=dl*q; + for (;;) + { + t=h-th; + if ((t&BN_MASK2h) || + ((tl) <= ( + (t<<BN_BITS4)| + ((l&BN_MASK2h)>>BN_BITS4)))) + break; + q--; + th-=dh; + tl-=dl; + } + t=(tl>>BN_BITS4); + tl=(tl<<BN_BITS4)&BN_MASK2h; + th+=t; + + if (l < tl) th++; + l-=tl; + if (h < th) + { + h+=d; + q--; + } + h-=th; + + if (--count == 0) break; + + ret=q<<BN_BITS4; + h=((h<<BN_BITS4)|(l>>BN_BITS4))&BN_MASK2; + l=(l&BN_MASK2l)<<BN_BITS4; + } + ret|=q; + return(ret); + } +#endif /* !defined(BN_LLONG) && defined(BN_DIV2W) */ + +#ifdef BN_LLONG +BN_ULONG bn_add_words(BN_ULONG *r, BN_ULONG *a, BN_ULONG *b, int n) + { + BN_ULLONG ll=0; + + assert(n >= 0); + if (n <= 0) return((BN_ULONG)0); + + for (;;) + { + ll+=(BN_ULLONG)a[0]+b[0]; + r[0]=(BN_ULONG)ll&BN_MASK2; + ll>>=BN_BITS2; + if (--n <= 0) break; + + ll+=(BN_ULLONG)a[1]+b[1]; + r[1]=(BN_ULONG)ll&BN_MASK2; + ll>>=BN_BITS2; + if (--n <= 0) break; + + ll+=(BN_ULLONG)a[2]+b[2]; + r[2]=(BN_ULONG)ll&BN_MASK2; + ll>>=BN_BITS2; + if (--n <= 0) break; + + ll+=(BN_ULLONG)a[3]+b[3]; + r[3]=(BN_ULONG)ll&BN_MASK2; + ll>>=BN_BITS2; + if (--n <= 0) break; + + a+=4; + b+=4; + r+=4; + } + return((BN_ULONG)ll); + } +#else /* !BN_LLONG */ +BN_ULONG bn_add_words(BN_ULONG *r, BN_ULONG *a, BN_ULONG *b, int n) + { + BN_ULONG c,l,t; + + assert(n >= 0); + if (n <= 0) return((BN_ULONG)0); + + c=0; + for (;;) + { + t=a[0]; + t=(t+c)&BN_MASK2; + c=(t < c); + l=(t+b[0])&BN_MASK2; + c+=(l < t); + r[0]=l; + if (--n <= 0) break; + + t=a[1]; + t=(t+c)&BN_MASK2; + c=(t < c); + l=(t+b[1])&BN_MASK2; + c+=(l < t); + r[1]=l; + if (--n <= 0) break; + + t=a[2]; + t=(t+c)&BN_MASK2; + c=(t < c); + l=(t+b[2])&BN_MASK2; + c+=(l < t); + r[2]=l; + if (--n <= 0) break; + + t=a[3]; + t=(t+c)&BN_MASK2; + c=(t < c); + l=(t+b[3])&BN_MASK2; + c+=(l < t); + r[3]=l; + if (--n <= 0) break; + + a+=4; + b+=4; + r+=4; + } + return((BN_ULONG)c); + } +#endif /* !BN_LLONG */ diff --git a/package/network/services/ead/src/tinysrp/bn_ctx.c b/package/network/services/ead/src/tinysrp/bn_ctx.c new file mode 100644 index 0000000000..20a6605ab8 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_ctx.c @@ -0,0 +1,142 @@ +/* crypto/bn/bn_ctx.c */ +/* Written by Ulf Moeller for the OpenSSL project. */ +/* ==================================================================== + * Copyright (c) 1998-2000 The OpenSSL Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. All advertising materials mentioning features or use of this + * software must display the following acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit. (http://www.openssl.org/)" + * + * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to + * endorse or promote products derived from this software without + * prior written permission. For written permission, please contact + * openssl-core@openssl.org. + * + * 5. Products derived from this software may not be called "OpenSSL" + * nor may "OpenSSL" appear in their names without prior written + * permission of the OpenSSL Project. + * + * 6. Redistributions of any form whatsoever must retain the following + * acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit (http://www.openssl.org/)" + * + * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY + * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * ==================================================================== + * + * This product includes cryptographic software written by Eric Young + * (eay@cryptsoft.com). This product includes software written by Tim + * Hudson (tjh@cryptsoft.com). + * + */ + +#ifndef BN_CTX_DEBUG +# undef NDEBUG /* avoid conflicting definitions */ +# define NDEBUG +#endif + +#include <stdio.h> +#include <stdlib.h> +#include <assert.h> +#include <bn.h> + + +BN_CTX *BN_CTX_new(void) + { + BN_CTX *ret; + + ret=(BN_CTX *)malloc(sizeof(BN_CTX)); + if (ret == NULL) + { + return(NULL); + } + + BN_CTX_init(ret); + ret->flags=BN_FLG_MALLOCED; + return(ret); + } + +void BN_CTX_init(BN_CTX *ctx) + { + int i; + ctx->tos = 0; + ctx->flags = 0; + ctx->depth = 0; + ctx->too_many = 0; + for (i = 0; i < BN_CTX_NUM; i++) + BN_init(&(ctx->bn[i])); + } + +void BN_CTX_free(BN_CTX *ctx) + { + int i; + + if (ctx == NULL) return; + assert(ctx->depth == 0); + + for (i=0; i < BN_CTX_NUM; i++) + BN_clear_free(&(ctx->bn[i])); + if (ctx->flags & BN_FLG_MALLOCED) + free(ctx); + } + +void BN_CTX_start(BN_CTX *ctx) + { + if (ctx->depth < BN_CTX_NUM_POS) + ctx->pos[ctx->depth] = ctx->tos; + ctx->depth++; + } + +BIGNUM *BN_CTX_get(BN_CTX *ctx) + { + if (ctx->depth > BN_CTX_NUM_POS || ctx->tos >= BN_CTX_NUM) + { + if (!ctx->too_many) + { + /* disable error code until BN_CTX_end is called: */ + ctx->too_many = 1; + } + return NULL; + } + return (&(ctx->bn[ctx->tos++])); + } + +void BN_CTX_end(BN_CTX *ctx) + { + if (ctx == NULL) return; + assert(ctx->depth > 0); + if (ctx->depth == 0) + /* should never happen, but we can tolerate it if not in + * debug mode (could be a 'goto err' in the calling function + * before BN_CTX_start was reached) */ + BN_CTX_start(ctx); + + ctx->too_many = 0; + ctx->depth--; + if (ctx->depth < BN_CTX_NUM_POS) + ctx->tos = ctx->pos[ctx->depth]; + } diff --git a/package/network/services/ead/src/tinysrp/bn_div.c b/package/network/services/ead/src/tinysrp/bn_div.c new file mode 100644 index 0000000000..fd21913d1e --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_div.c @@ -0,0 +1,378 @@ +/* crypto/bn/bn_div.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include <stdio.h> +#include "bn_lcl.h" + +#define NO_ASM + +/* The old slow way */ +#if 0 +int BN_div(BIGNUM *dv, BIGNUM *rem, const BIGNUM *m, const BIGNUM *d, + BN_CTX *ctx) + { + int i,nm,nd; + int ret = 0; + BIGNUM *D; + + bn_check_top(m); + bn_check_top(d); + if (BN_is_zero(d)) + { + return(0); + } + + if (BN_ucmp(m,d) < 0) + { + if (rem != NULL) + { if (BN_copy(rem,m) == NULL) return(0); } + if (dv != NULL) BN_zero(dv); + return(1); + } + + BN_CTX_start(ctx); + D = BN_CTX_get(ctx); + if (dv == NULL) dv = BN_CTX_get(ctx); + if (rem == NULL) rem = BN_CTX_get(ctx); + if (D == NULL || dv == NULL || rem == NULL) + goto end; + + nd=BN_num_bits(d); + nm=BN_num_bits(m); + if (BN_copy(D,d) == NULL) goto end; + if (BN_copy(rem,m) == NULL) goto end; + + /* The next 2 are needed so we can do a dv->d[0]|=1 later + * since BN_lshift1 will only work once there is a value :-) */ + BN_zero(dv); + bn_wexpand(dv,1); + dv->top=1; + + if (!BN_lshift(D,D,nm-nd)) goto end; + for (i=nm-nd; i>=0; i--) + { + if (!BN_lshift1(dv,dv)) goto end; + if (BN_ucmp(rem,D) >= 0) + { + dv->d[0]|=1; + if (!BN_usub(rem,rem,D)) goto end; + } +/* CAN IMPROVE (and have now :=) */ + if (!BN_rshift1(D,D)) goto end; + } + rem->neg=BN_is_zero(rem)?0:m->neg; + dv->neg=m->neg^d->neg; + ret = 1; + end: + BN_CTX_end(ctx); + return(ret); + } + +#else + +#if !defined(NO_ASM) && !defined(NO_INLINE_ASM) && !defined(PEDANTIC) && !defined(BN_DIV3W) +# if defined(__GNUC__) && __GNUC__>=2 +# if defined(__i386) + /* + * There were two reasons for implementing this template: + * - GNU C generates a call to a function (__udivdi3 to be exact) + * in reply to ((((BN_ULLONG)n0)<<BN_BITS2)|n1)/d0 (I fail to + * understand why...); + * - divl doesn't only calculate quotient, but also leaves + * remainder in %edx which we can definitely use here:-) + * + * <appro@fy.chalmers.se> + */ +# define bn_div_words(n0,n1,d0) \ + ({ asm volatile ( \ + "divl %4" \ + : "=a"(q), "=d"(rem) \ + : "a"(n1), "d"(n0), "g"(d0) \ + : "cc"); \ + q; \ + }) +# define REMAINDER_IS_ALREADY_CALCULATED +# endif /* __<cpu> */ +# endif /* __GNUC__ */ +#endif /* NO_ASM */ + +int BN_div(BIGNUM *dv, BIGNUM *rm, const BIGNUM *num, const BIGNUM *divisor, + BN_CTX *ctx) + { + int norm_shift,i,j,loop; + BIGNUM *tmp,wnum,*snum,*sdiv,*res; + BN_ULONG *resp,*wnump; + BN_ULONG d0,d1; + int num_n,div_n; + + bn_check_top(num); + bn_check_top(divisor); + + if (BN_is_zero(divisor)) + { + return(0); + } + + if (BN_ucmp(num,divisor) < 0) + { + if (rm != NULL) + { if (BN_copy(rm,num) == NULL) return(0); } + if (dv != NULL) BN_zero(dv); + return(1); + } + + BN_CTX_start(ctx); + tmp=BN_CTX_get(ctx); + tmp->neg=0; + snum=BN_CTX_get(ctx); + sdiv=BN_CTX_get(ctx); + if (dv == NULL) + res=BN_CTX_get(ctx); + else res=dv; + if (res == NULL) goto err; + + /* First we normalise the numbers */ + norm_shift=BN_BITS2-((BN_num_bits(divisor))%BN_BITS2); + BN_lshift(sdiv,divisor,norm_shift); + sdiv->neg=0; + norm_shift+=BN_BITS2; + BN_lshift(snum,num,norm_shift); + snum->neg=0; + div_n=sdiv->top; + num_n=snum->top; + loop=num_n-div_n; + + /* Lets setup a 'window' into snum + * This is the part that corresponds to the current + * 'area' being divided */ + BN_init(&wnum); + wnum.d= &(snum->d[loop]); + wnum.top= div_n; + wnum.dmax= snum->dmax+1; /* a bit of a lie */ + + /* Get the top 2 words of sdiv */ + /* i=sdiv->top; */ + d0=sdiv->d[div_n-1]; + d1=(div_n == 1)?0:sdiv->d[div_n-2]; + + /* pointer to the 'top' of snum */ + wnump= &(snum->d[num_n-1]); + + /* Setup to 'res' */ + res->neg= (num->neg^divisor->neg); + if (!bn_wexpand(res,(loop+1))) goto err; + res->top=loop; + resp= &(res->d[loop-1]); + + /* space for temp */ + if (!bn_wexpand(tmp,(div_n+1))) goto err; + + if (BN_ucmp(&wnum,sdiv) >= 0) + { + if (!BN_usub(&wnum,&wnum,sdiv)) goto err; + *resp=1; + res->d[res->top-1]=1; + } + else + res->top--; + resp--; + + for (i=0; i<loop-1; i++) + { + BN_ULONG q,l0; +#ifdef BN_DIV3W + q=bn_div_3_words(wnump,d1,d0); +#else + BN_ULONG n0,n1,rem=0; + + n0=wnump[0]; + n1=wnump[-1]; + if (n0 == d0) + q=BN_MASK2; + else /* n0 < d0 */ + { +#ifdef BN_LLONG + BN_ULLONG t2; + +#if defined(BN_LLONG) && defined(BN_DIV2W) && !defined(bn_div_words) + q=(BN_ULONG)(((((BN_ULLONG)n0)<<BN_BITS2)|n1)/d0); +#else + q=bn_div_words(n0,n1,d0); +#endif + +#ifndef REMAINDER_IS_ALREADY_CALCULATED + /* + * rem doesn't have to be BN_ULLONG. The least we + * know it's less that d0, isn't it? + */ + rem=(n1-q*d0)&BN_MASK2; +#endif + t2=(BN_ULLONG)d1*q; + + for (;;) + { + if (t2 <= ((((BN_ULLONG)rem)<<BN_BITS2)|wnump[-2])) + break; + q--; + rem += d0; + if (rem < d0) break; /* don't let rem overflow */ + t2 -= d1; + } +#else /* !BN_LLONG */ + BN_ULONG t2l,t2h,ql,qh; + + q=bn_div_words(n0,n1,d0); +#ifndef REMAINDER_IS_ALREADY_CALCULATED + rem=(n1-q*d0)&BN_MASK2; +#endif + +#ifdef BN_UMULT_HIGH + t2l = d1 * q; + t2h = BN_UMULT_HIGH(d1,q); +#else + t2l=LBITS(d1); t2h=HBITS(d1); + ql =LBITS(q); qh =HBITS(q); + mul64(t2l,t2h,ql,qh); /* t2=(BN_ULLONG)d1*q; */ +#endif + + for (;;) + { + if ((t2h < rem) || + ((t2h == rem) && (t2l <= wnump[-2]))) + break; + q--; + rem += d0; + if (rem < d0) break; /* don't let rem overflow */ + if (t2l < d1) t2h--; t2l -= d1; + } +#endif /* !BN_LLONG */ + } +#endif /* !BN_DIV3W */ + + l0=bn_mul_words(tmp->d,sdiv->d,div_n,q); + wnum.d--; wnum.top++; + tmp->d[div_n]=l0; + for (j=div_n+1; j>0; j--) + if (tmp->d[j-1]) break; + tmp->top=j; + + j=wnum.top; + BN_sub(&wnum,&wnum,tmp); + + snum->top=snum->top+wnum.top-j; + + if (wnum.neg) + { + q--; + j=wnum.top; + BN_add(&wnum,&wnum,sdiv); + snum->top+=wnum.top-j; + } + *(resp--)=q; + wnump--; + } + if (rm != NULL) + { + BN_rshift(rm,snum,norm_shift); + rm->neg=num->neg; + } + BN_CTX_end(ctx); + return(1); +err: + BN_CTX_end(ctx); + return(0); + } + +#endif + +/* rem != m */ +int BN_mod(BIGNUM *rem, const BIGNUM *m, const BIGNUM *d, BN_CTX *ctx) + { +#if 0 /* The old slow way */ + int i,nm,nd; + BIGNUM *dv; + + if (BN_ucmp(m,d) < 0) + return((BN_copy(rem,m) == NULL)?0:1); + + BN_CTX_start(ctx); + dv=BN_CTX_get(ctx); + + if (!BN_copy(rem,m)) goto err; + + nm=BN_num_bits(rem); + nd=BN_num_bits(d); + if (!BN_lshift(dv,d,nm-nd)) goto err; + for (i=nm-nd; i>=0; i--) + { + if (BN_cmp(rem,dv) >= 0) + { + if (!BN_sub(rem,rem,dv)) goto err; + } + if (!BN_rshift1(dv,dv)) goto err; + } + BN_CTX_end(ctx); + return(1); + err: + BN_CTX_end(ctx); + return(0); +#else + return(BN_div(NULL,rem,m,d,ctx)); +#endif + } + diff --git a/package/network/services/ead/src/tinysrp/bn_exp.c b/package/network/services/ead/src/tinysrp/bn_exp.c new file mode 100644 index 0000000000..09afb79f6d --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_exp.c @@ -0,0 +1,395 @@ +/* crypto/bn/bn_exp.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ +/* ==================================================================== + * Copyright (c) 1998-2000 The OpenSSL Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. All advertising materials mentioning features or use of this + * software must display the following acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit. (http://www.openssl.org/)" + * + * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to + * endorse or promote products derived from this software without + * prior written permission. For written permission, please contact + * openssl-core@openssl.org. + * + * 5. Products derived from this software may not be called "OpenSSL" + * nor may "OpenSSL" appear in their names without prior written + * permission of the OpenSSL Project. + * + * 6. Redistributions of any form whatsoever must retain the following + * acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit (http://www.openssl.org/)" + * + * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY + * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * ==================================================================== + * + * This product includes cryptographic software written by Eric Young + * (eay@cryptsoft.com). This product includes software written by Tim + * Hudson (tjh@cryptsoft.com). + * + */ + + +#include <stdio.h> +#include "bn_lcl.h" + +#define TABLE_SIZE 32 + +/* slow but works */ +int BN_mod_mul(BIGNUM *ret, BIGNUM *a, BIGNUM *b, const BIGNUM *m, BN_CTX *ctx) + { + BIGNUM *t; + int r=0; + + bn_check_top(a); + bn_check_top(b); + bn_check_top(m); + + BN_CTX_start(ctx); + if ((t = BN_CTX_get(ctx)) == NULL) goto err; + if (a == b) + { if (!BN_sqr(t,a,ctx)) goto err; } + else + { if (!BN_mul(t,a,b,ctx)) goto err; } + if (!BN_mod(ret,t,m,ctx)) goto err; + r=1; +err: + BN_CTX_end(ctx); + return(r); + } + +int BN_mod_exp(BIGNUM *r, BIGNUM *a, const BIGNUM *p, const BIGNUM *m, + BN_CTX *ctx) + { + int ret; + + bn_check_top(a); + bn_check_top(p); + bn_check_top(m); + +#ifdef MONT_MUL_MOD + /* I have finally been able to take out this pre-condition of + * the top bit being set. It was caused by an error in BN_div + * with negatives. There was also another problem when for a^b%m + * a >= m. eay 07-May-97 */ +/* if ((m->d[m->top-1]&BN_TBIT) && BN_is_odd(m)) */ + + if (BN_is_odd(m)) + { + if (a->top == 1) + { + BN_ULONG A = a->d[0]; + ret=BN_mod_exp_mont_word(r,A,p,m,ctx,NULL); + } + else + ret=BN_mod_exp_mont(r,a,p,m,ctx,NULL); + } + else +#endif +#ifdef RECP_MUL_MOD + { ret=BN_mod_exp_recp(r,a,p,m,ctx); } +#else + { ret=BN_mod_exp_simple(r,a,p,m,ctx); } +#endif + + return(ret); + } + + +#ifdef RECP_MUL_MOD +int BN_mod_exp_recp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, + const BIGNUM *m, BN_CTX *ctx) + { + int i,j,bits,ret=0,wstart,wend,window,wvalue; + int start=1,ts=0; + BIGNUM *aa; + BIGNUM val[TABLE_SIZE]; + BN_RECP_CTX recp; + + bits=BN_num_bits(p); + + if (bits == 0) + { + BN_one(r); + return(1); + } + + BN_CTX_start(ctx); + if ((aa = BN_CTX_get(ctx)) == NULL) goto err; + + BN_RECP_CTX_init(&recp); + if (BN_RECP_CTX_set(&recp,m,ctx) <= 0) goto err; + + BN_init(&(val[0])); + ts=1; + + if (!BN_mod(&(val[0]),a,m,ctx)) goto err; /* 1 */ + + window = BN_window_bits_for_exponent_size(bits); + if (window > 1) + { + if (!BN_mod_mul_reciprocal(aa,&(val[0]),&(val[0]),&recp,ctx)) + goto err; /* 2 */ + j=1<<(window-1); + for (i=1; i<j; i++) + { + BN_init(&val[i]); + if (!BN_mod_mul_reciprocal(&(val[i]),&(val[i-1]),aa,&recp,ctx)) + goto err; + } + ts=i; + } + + start=1; /* This is used to avoid multiplication etc + * when there is only the value '1' in the + * buffer. */ + wvalue=0; /* The 'value' of the window */ + wstart=bits-1; /* The top bit of the window */ + wend=0; /* The bottom bit of the window */ + + if (!BN_one(r)) goto err; + + for (;;) + { + if (BN_is_bit_set(p,wstart) == 0) + { + if (!start) + if (!BN_mod_mul_reciprocal(r,r,r,&recp,ctx)) + goto err; + if (wstart == 0) break; + wstart--; + continue; + } + /* We now have wstart on a 'set' bit, we now need to work out + * how bit a window to do. To do this we need to scan + * forward until the last set bit before the end of the + * window */ + j=wstart; + wvalue=1; + wend=0; + for (i=1; i<window; i++) + { + if (wstart-i < 0) break; + if (BN_is_bit_set(p,wstart-i)) + { + wvalue<<=(i-wend); + wvalue|=1; + wend=i; + } + } + + /* wend is the size of the current window */ + j=wend+1; + /* add the 'bytes above' */ + if (!start) + for (i=0; i<j; i++) + { + if (!BN_mod_mul_reciprocal(r,r,r,&recp,ctx)) + goto err; + } + + /* wvalue will be an odd number < 2^window */ + if (!BN_mod_mul_reciprocal(r,r,&(val[wvalue>>1]),&recp,ctx)) + goto err; + + /* move the 'window' down further */ + wstart-=wend+1; + wvalue=0; + start=0; + if (wstart < 0) break; + } + ret=1; +err: + BN_CTX_end(ctx); + for (i=0; i<ts; i++) + BN_clear_free(&(val[i])); + BN_RECP_CTX_free(&recp); + return(ret); + } +#else + +/* The old fallback, simple version :-) */ +int BN_mod_exp_simple(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, + const BIGNUM *m, BN_CTX *ctx) + { + int i,j,bits,ret=0,wstart,wend,window,wvalue,ts=0; + int start=1; + BIGNUM *d; + BIGNUM val[TABLE_SIZE]; + + bits=BN_num_bits(p); + + if (bits == 0) + { + BN_one(r); + return(1); + } + + BN_CTX_start(ctx); + if ((d = BN_CTX_get(ctx)) == NULL) goto err; + + BN_init(&(val[0])); + ts=1; + if (!BN_mod(&(val[0]),a,m,ctx)) goto err; /* 1 */ + + window = BN_window_bits_for_exponent_size(bits); + if (window > 1) + { + if (!BN_mod_mul(d,&(val[0]),&(val[0]),m,ctx)) + goto err; /* 2 */ + j=1<<(window-1); + for (i=1; i<j; i++) + { + BN_init(&(val[i])); + if (!BN_mod_mul(&(val[i]),&(val[i-1]),d,m,ctx)) + goto err; + } + ts=i; + } + + start=1; /* This is used to avoid multiplication etc + * when there is only the value '1' in the + * buffer. */ + wvalue=0; /* The 'value' of the window */ + wstart=bits-1; /* The top bit of the window */ + wend=0; /* The bottom bit of the window */ + + if (!BN_one(r)) goto err; + + for (;;) + { + if (BN_is_bit_set(p,wstart) == 0) + { + if (!start) + if (!BN_mod_mul(r,r,r,m,ctx)) + goto err; + if (wstart == 0) break; + wstart--; + continue; + } + /* We now have wstart on a 'set' bit, we now need to work out + * how bit a window to do. To do this we need to scan + * forward until the last set bit before the end of the + * window */ + j=wstart; + wvalue=1; + wend=0; + for (i=1; i<window; i++) + { + if (wstart-i < 0) break; + if (BN_is_bit_set(p,wstart-i)) + { + wvalue<<=(i-wend); + wvalue|=1; + wend=i; + } + } + + /* wend is the size of the current window */ + j=wend+1; + /* add the 'bytes above' */ + if (!start) + for (i=0; i<j; i++) + { + if (!BN_mod_mul(r,r,r,m,ctx)) + goto err; + } + + /* wvalue will be an odd number < 2^window */ + if (!BN_mod_mul(r,r,&(val[wvalue>>1]),m,ctx)) + goto err; + + /* move the 'window' down further */ + wstart-=wend+1; + wvalue=0; + start=0; + if (wstart < 0) break; + } + ret=1; +err: + BN_CTX_end(ctx); + for (i=0; i<ts; i++) + BN_clear_free(&(val[i])); + return(ret); + } +#endif diff --git a/package/network/services/ead/src/tinysrp/bn_lcl.h b/package/network/services/ead/src/tinysrp/bn_lcl.h new file mode 100644 index 0000000000..129ad658af --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_lcl.h @@ -0,0 +1,419 @@ +/* crypto/bn/bn_lcl.h */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ +/* ==================================================================== + * Copyright (c) 1998-2000 The OpenSSL Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. All advertising materials mentioning features or use of this + * software must display the following acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit. (http://www.openssl.org/)" + * + * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to + * endorse or promote products derived from this software without + * prior written permission. For written permission, please contact + * openssl-core@openssl.org. + * + * 5. Products derived from this software may not be called "OpenSSL" + * nor may "OpenSSL" appear in their names without prior written + * permission of the OpenSSL Project. + * + * 6. Redistributions of any form whatsoever must retain the following + * acknowledgment: + * "This product includes software developed by the OpenSSL Project + * for use in the OpenSSL Toolkit (http://www.openssl.org/)" + * + * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY + * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * ==================================================================== + * + * This product includes cryptographic software written by Eric Young + * (eay@cryptsoft.com). This product includes software written by Tim + * Hudson (tjh@cryptsoft.com). + * + */ + +#ifndef HEADER_BN_LCL_H +#define HEADER_BN_LCL_H + +#include <bn.h> + +#ifdef __cplusplus +extern "C" { +#endif + + +/* + * BN_window_bits_for_exponent_size -- macro for sliding window mod_exp functions + * + * + * For window size 'w' (w >= 2) and a random 'b' bits exponent, + * the number of multiplications is a constant plus on average + * + * 2^(w-1) + (b-w)/(w+1); + * + * here 2^(w-1) is for precomputing the table (we actually need + * entries only for windows that have the lowest bit set), and + * (b-w)/(w+1) is an approximation for the expected number of + * w-bit windows, not counting the first one. + * + * Thus we should use + * + * w >= 6 if b > 671 + * w = 5 if 671 > b > 239 + * w = 4 if 239 > b > 79 + * w = 3 if 79 > b > 23 + * w <= 2 if 23 > b + * + * (with draws in between). Very small exponents are often selected + * with low Hamming weight, so we use w = 1 for b <= 23. + */ +#if 1 +#define BN_window_bits_for_exponent_size(b) \ + ((b) > 671 ? 6 : \ + (b) > 239 ? 5 : \ + (b) > 79 ? 4 : \ + (b) > 23 ? 3 : 1) +#else +/* Old SSLeay/OpenSSL table. + * Maximum window size was 5, so this table differs for b==1024; + * but it coincides for other interesting values (b==160, b==512). + */ +#define BN_window_bits_for_exponent_size(b) \ + ((b) > 255 ? 5 : \ + (b) > 127 ? 4 : \ + (b) > 17 ? 3 : 1) +#endif + + + +/* Pentium pro 16,16,16,32,64 */ +/* Alpha 16,16,16,16.64 */ +#define BN_MULL_SIZE_NORMAL (16) /* 32 */ +#define BN_MUL_RECURSIVE_SIZE_NORMAL (16) /* 32 less than */ +#define BN_SQR_RECURSIVE_SIZE_NORMAL (16) /* 32 */ +#define BN_MUL_LOW_RECURSIVE_SIZE_NORMAL (32) /* 32 */ +#define BN_MONT_CTX_SET_SIZE_WORD (64) /* 32 */ + +#if !defined(NO_ASM) && !defined(NO_INLINE_ASM) && !defined(PEDANTIC) +/* + * BN_UMULT_HIGH section. + * + * No, I'm not trying to overwhelm you when stating that the + * product of N-bit numbers is 2*N bits wide:-) No, I don't expect + * you to be impressed when I say that if the compiler doesn't + * support 2*N integer type, then you have to replace every N*N + * multiplication with 4 (N/2)*(N/2) accompanied by some shifts + * and additions which unavoidably results in severe performance + * penalties. Of course provided that the hardware is capable of + * producing 2*N result... That's when you normally start + * considering assembler implementation. However! It should be + * pointed out that some CPUs (most notably Alpha, PowerPC and + * upcoming IA-64 family:-) provide *separate* instruction + * calculating the upper half of the product placing the result + * into a general purpose register. Now *if* the compiler supports + * inline assembler, then it's not impossible to implement the + * "bignum" routines (and have the compiler optimize 'em) + * exhibiting "native" performance in C. That's what BN_UMULT_HIGH + * macro is about:-) + * + * <appro@fy.chalmers.se> + */ +# if defined(__alpha) && (defined(SIXTY_FOUR_BIT_LONG) || defined(SIXTY_FOUR_BIT)) +# if defined(__DECC) +# include <c_asm.h> +# define BN_UMULT_HIGH(a,b) (BN_ULONG)asm("umulh %a0,%a1,%v0",(a),(b)) +# elif defined(__GNUC__) +# define BN_UMULT_HIGH(a,b) ({ \ + register BN_ULONG ret; \ + asm ("umulh %1,%2,%0" \ + : "=r"(ret) \ + : "r"(a), "r"(b)); \ + ret; }) +# endif /* compiler */ +# elif defined(_ARCH_PPC) && defined(__64BIT__) && defined(SIXTY_FOUR_BIT_LONG) +# if defined(__GNUC__) +# define BN_UMULT_HIGH(a,b) ({ \ + register BN_ULONG ret; \ + asm ("mulhdu %0,%1,%2" \ + : "=r"(ret) \ + : "r"(a), "r"(b)); \ + ret; }) +# endif /* compiler */ +# endif /* cpu */ +#endif /* NO_ASM */ + +/************************************************************* + * Using the long long type + */ +#define Lw(t) (((BN_ULONG)(t))&BN_MASK2) +#define Hw(t) (((BN_ULONG)((t)>>BN_BITS2))&BN_MASK2) + +/* This is used for internal error checking and is not normally used */ +#ifdef BN_DEBUG +# include <assert.h> +# define bn_check_top(a) assert ((a)->top >= 0 && (a)->top <= (a)->dmax); +#else +# define bn_check_top(a) +#endif + +/* This macro is to add extra stuff for development checking */ +#ifdef BN_DEBUG +#define bn_set_max(r) ((r)->max=(r)->top,BN_set_flags((r),BN_FLG_STATIC_DATA)) +#else +#define bn_set_max(r) +#endif + +/* These macros are used to 'take' a section of a bignum for read only use */ +#define bn_set_low(r,a,n) \ + { \ + (r)->top=((a)->top > (n))?(n):(a)->top; \ + (r)->d=(a)->d; \ + (r)->neg=(a)->neg; \ + (r)->flags|=BN_FLG_STATIC_DATA; \ + bn_set_max(r); \ + } + +#define bn_set_high(r,a,n) \ + { \ + if ((a)->top > (n)) \ + { \ + (r)->top=(a)->top-n; \ + (r)->d= &((a)->d[n]); \ + } \ + else \ + (r)->top=0; \ + (r)->neg=(a)->neg; \ + (r)->flags|=BN_FLG_STATIC_DATA; \ + bn_set_max(r); \ + } + +#ifdef BN_LLONG +#define mul_add(r,a,w,c) { \ + BN_ULLONG t; \ + t=(BN_ULLONG)w * (a) + (r) + (c); \ + (r)= Lw(t); \ + (c)= Hw(t); \ + } + +#define mul(r,a,w,c) { \ + BN_ULLONG t; \ + t=(BN_ULLONG)w * (a) + (c); \ + (r)= Lw(t); \ + (c)= Hw(t); \ + } + +#define sqr(r0,r1,a) { \ + BN_ULLONG t; \ + t=(BN_ULLONG)(a)*(a); \ + (r0)=Lw(t); \ + (r1)=Hw(t); \ + } + +#elif defined(BN_UMULT_HIGH) +#define mul_add(r,a,w,c) { \ + BN_ULONG high,low,ret,tmp=(a); \ + ret = (r); \ + high= BN_UMULT_HIGH(w,tmp); \ + ret += (c); \ + low = (w) * tmp; \ + (c) = (ret<(c))?1:0; \ + (c) += high; \ + ret += low; \ + (c) += (ret<low)?1:0; \ + (r) = ret; \ + } + +#define mul(r,a,w,c) { \ + BN_ULONG high,low,ret,ta=(a); \ + low = (w) * ta; \ + high= BN_UMULT_HIGH(w,ta); \ + ret = low + (c); \ + (c) = high; \ + (c) += (ret<low)?1:0; \ + (r) = ret; \ + } + +#define sqr(r0,r1,a) { \ + BN_ULONG tmp=(a); \ + (r0) = tmp * tmp; \ + (r1) = BN_UMULT_HIGH(tmp,tmp); \ + } + +#else +/************************************************************* + * No long long type + */ + +#define LBITS(a) ((a)&BN_MASK2l) +#define HBITS(a) (((a)>>BN_BITS4)&BN_MASK2l) +#define L2HBITS(a) ((BN_ULONG)((a)&BN_MASK2l)<<BN_BITS4) + +#define LLBITS(a) ((a)&BN_MASKl) +#define LHBITS(a) (((a)>>BN_BITS2)&BN_MASKl) +#define LL2HBITS(a) ((BN_ULLONG)((a)&BN_MASKl)<<BN_BITS2) + +#define mul64(l,h,bl,bh) \ + { \ + BN_ULONG m,m1,lt,ht; \ + \ + lt=l; \ + ht=h; \ + m =(bh)*(lt); \ + lt=(bl)*(lt); \ + m1=(bl)*(ht); \ + ht =(bh)*(ht); \ + m=(m+m1)&BN_MASK2; if (m < m1) ht+=L2HBITS(1L); \ + ht+=HBITS(m); \ + m1=L2HBITS(m); \ + lt=(lt+m1)&BN_MASK2; if (lt < m1) ht++; \ + (l)=lt; \ + (h)=ht; \ + } + +#define sqr64(lo,ho,in) \ + { \ + BN_ULONG l,h,m; \ + \ + h=(in); \ + l=LBITS(h); \ + h=HBITS(h); \ + m =(l)*(h); \ + l*=l; \ + h*=h; \ + h+=(m&BN_MASK2h1)>>(BN_BITS4-1); \ + m =(m&BN_MASK2l)<<(BN_BITS4+1); \ + l=(l+m)&BN_MASK2; if (l < m) h++; \ + (lo)=l; \ + (ho)=h; \ + } + +#define mul_add(r,a,bl,bh,c) { \ + BN_ULONG l,h; \ + \ + h= (a); \ + l=LBITS(h); \ + h=HBITS(h); \ + mul64(l,h,(bl),(bh)); \ + \ + /* non-multiply part */ \ + l=(l+(c))&BN_MASK2; if (l < (c)) h++; \ + (c)=(r); \ + l=(l+(c))&BN_MASK2; if (l < (c)) h++; \ + (c)=h&BN_MASK2; \ + (r)=l; \ + } + +#define mul(r,a,bl,bh,c) { \ + BN_ULONG l,h; \ + \ + h= (a); \ + l=LBITS(h); \ + h=HBITS(h); \ + mul64(l,h,(bl),(bh)); \ + \ + /* non-multiply part */ \ + l+=(c); if ((l&BN_MASK2) < (c)) h++; \ + (c)=h&BN_MASK2; \ + (r)=l&BN_MASK2; \ + } +#endif /* !BN_LLONG */ + +void bn_mul_normal(BN_ULONG *r,BN_ULONG *a,int na,BN_ULONG *b,int nb); +void bn_mul_comba8(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b); +void bn_mul_comba4(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b); +void bn_sqr_normal(BN_ULONG *r, BN_ULONG *a, int n, BN_ULONG *tmp); +void bn_sqr_comba8(BN_ULONG *r,BN_ULONG *a); +void bn_sqr_comba4(BN_ULONG *r,BN_ULONG *a); +int bn_cmp_words(BN_ULONG *a,BN_ULONG *b,int n); +void bn_mul_recursive(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b,int n2,BN_ULONG *t); +void bn_mul_part_recursive(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b, + int tn, int n,BN_ULONG *t); +void bn_sqr_recursive(BN_ULONG *r,BN_ULONG *a, int n2, BN_ULONG *t); +void bn_mul_low_normal(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b, int n); +void bn_mul_low_recursive(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b,int n2, + BN_ULONG *t); +void bn_mul_high(BN_ULONG *r,BN_ULONG *a,BN_ULONG *b,BN_ULONG *l,int n2, + BN_ULONG *t); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/package/network/services/ead/src/tinysrp/bn_lib.c b/package/network/services/ead/src/tinysrp/bn_lib.c new file mode 100644 index 0000000000..cfa0d75665 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_lib.c @@ -0,0 +1,576 @@ +/* crypto/bn/bn_lib.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#ifndef BN_DEBUG +# undef NDEBUG /* avoid conflicting definitions */ +# define NDEBUG +#endif + +#include <assert.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include "bn_lcl.h" + +const char *BN_version="Big Number"; + +/* For a 32 bit machine + * 2 - 4 == 128 + * 3 - 8 == 256 + * 4 - 16 == 512 + * 5 - 32 == 1024 + * 6 - 64 == 2048 + * 7 - 128 == 4096 + * 8 - 256 == 8192 + */ +static int bn_limit_bits=0; +static int bn_limit_num=8; /* (1<<bn_limit_bits) */ +static int bn_limit_bits_low=0; +static int bn_limit_num_low=8; /* (1<<bn_limit_bits_low) */ +static int bn_limit_bits_high=0; +static int bn_limit_num_high=8; /* (1<<bn_limit_bits_high) */ +static int bn_limit_bits_mont=0; +static int bn_limit_num_mont=8; /* (1<<bn_limit_bits_mont) */ + +int BN_num_bits_word(BN_ULONG l) + { + static const char bits[256]={ + 0,1,2,2,3,3,3,3,4,4,4,4,4,4,4,4, + 5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5, + 6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6, + 6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8, + }; + +#if defined(SIXTY_FOUR_BIT_LONG) + if (l & 0xffffffff00000000L) + { + if (l & 0xffff000000000000L) + { + if (l & 0xff00000000000000L) + { + return(bits[(int)(l>>56)]+56); + } + else return(bits[(int)(l>>48)]+48); + } + else + { + if (l & 0x0000ff0000000000L) + { + return(bits[(int)(l>>40)]+40); + } + else return(bits[(int)(l>>32)]+32); + } + } + else +#else +#ifdef SIXTY_FOUR_BIT + if (l & 0xffffffff00000000LL) + { + if (l & 0xffff000000000000LL) + { + if (l & 0xff00000000000000LL) + { + return(bits[(int)(l>>56)]+56); + } + else return(bits[(int)(l>>48)]+48); + } + else + { + if (l & 0x0000ff0000000000LL) + { + return(bits[(int)(l>>40)]+40); + } + else return(bits[(int)(l>>32)]+32); + } + } + else +#endif +#endif + { +#if defined(THIRTY_TWO_BIT) || defined(SIXTY_FOUR_BIT) || defined(SIXTY_FOUR_BIT_LONG) + if (l & 0xffff0000L) + { + if (l & 0xff000000L) + return(bits[(int)(l>>24L)]+24); + else return(bits[(int)(l>>16L)]+16); + } + else +#endif + { +#if defined(SIXTEEN_BIT) || defined(THIRTY_TWO_BIT) || defined(SIXTY_FOUR_BIT) || defined(SIXTY_FOUR_BIT_LONG) + if (l & 0xff00L) + return(bits[(int)(l>>8)]+8); + else +#endif + return(bits[(int)(l )] ); + } + } + } + +int BN_num_bits(const BIGNUM *a) + { + BN_ULONG l; + int i; + + bn_check_top(a); + + if (a->top == 0) return(0); + l=a->d[a->top-1]; + assert(l != 0); + i=(a->top-1)*BN_BITS2; + return(i+BN_num_bits_word(l)); + } + +void BN_clear_free(BIGNUM *a) + { + int i; + + if (a == NULL) return; + if (a->d != NULL) + { + memset(a->d,0,a->dmax*sizeof(a->d[0])); + if (!(BN_get_flags(a,BN_FLG_STATIC_DATA))) + free(a->d); + } + i=BN_get_flags(a,BN_FLG_MALLOCED); + memset(a,0,sizeof(BIGNUM)); + if (i) + free(a); + } + +void BN_free(BIGNUM *a) + { + if (a == NULL) return; + if ((a->d != NULL) && !(BN_get_flags(a,BN_FLG_STATIC_DATA))) + free(a->d); + a->flags|=BN_FLG_FREE; /* REMOVE? */ + if (a->flags & BN_FLG_MALLOCED) + free(a); + } + +void BN_init(BIGNUM *a) + { + memset(a,0,sizeof(BIGNUM)); + } + +BIGNUM *BN_new(void) + { + BIGNUM *ret; + + if ((ret=(BIGNUM *)malloc(sizeof(BIGNUM))) == NULL) + { + return(NULL); + } + ret->flags=BN_FLG_MALLOCED; + ret->top=0; + ret->neg=0; + ret->dmax=0; + ret->d=NULL; + return(ret); + } + +/* This is an internal function that should not be used in applications. + * It ensures that 'b' has enough room for a 'words' word number number. + * It is mostly used by the various BIGNUM routines. If there is an error, + * NULL is returned. If not, 'b' is returned. */ + +BIGNUM *bn_expand2(BIGNUM *b, int words) + { + BN_ULONG *A,*a; + const BN_ULONG *B; + int i; + + bn_check_top(b); + + if (words > b->dmax) + { + bn_check_top(b); + if (BN_get_flags(b,BN_FLG_STATIC_DATA)) + { + return(NULL); + } + a=A=(BN_ULONG *)malloc(sizeof(BN_ULONG)*(words+1)); + if (A == NULL) + { + return(NULL); + } +#if 1 + B=b->d; + /* Check if the previous number needs to be copied */ + if (B != NULL) + { +#if 0 + /* This lot is an unrolled loop to copy b->top + * BN_ULONGs from B to A + */ +/* + * I have nothing against unrolling but it's usually done for + * several reasons, namely: + * - minimize percentage of decision making code, i.e. branches; + * - avoid cache trashing; + * - make it possible to schedule loads earlier; + * Now let's examine the code below. The cornerstone of C is + * "programmer is always right" and that's what we love it for:-) + * For this very reason C compilers have to be paranoid when it + * comes to data aliasing and assume the worst. Yeah, but what + * does it mean in real life? This means that loop body below will + * be compiled to sequence of loads immediately followed by stores + * as compiler assumes the worst, something in A==B+1 style. As a + * result CPU pipeline is going to starve for incoming data. Secondly + * if A and B happen to share same cache line such code is going to + * cause severe cache trashing. Both factors have severe impact on + * performance of modern CPUs and this is the reason why this + * particular piece of code is #ifdefed away and replaced by more + * "friendly" version found in #else section below. This comment + * also applies to BN_copy function. + * + * <appro@fy.chalmers.se> + */ + for (i=b->top&(~7); i>0; i-=8) + { + A[0]=B[0]; A[1]=B[1]; A[2]=B[2]; A[3]=B[3]; + A[4]=B[4]; A[5]=B[5]; A[6]=B[6]; A[7]=B[7]; + A+=8; + B+=8; + } + switch (b->top&7) + { + case 7: + A[6]=B[6]; + case 6: + A[5]=B[5]; + case 5: + A[4]=B[4]; + case 4: + A[3]=B[3]; + case 3: + A[2]=B[2]; + case 2: + A[1]=B[1]; + case 1: + A[0]=B[0]; + case 0: + /* I need the 'case 0' entry for utrix cc. + * If the optimizer is turned on, it does the + * switch table by doing + * a=top&7 + * a--; + * goto jump_table[a]; + * If top is 0, this makes us jump to 0xffffffc + * which is rather bad :-(. + * eric 23-Apr-1998 + */ + ; + } +#else + for (i=b->top>>2; i>0; i--,A+=4,B+=4) + { + /* + * The fact that the loop is unrolled + * 4-wise is a tribute to Intel. It's + * the one that doesn't have enough + * registers to accomodate more data. + * I'd unroll it 8-wise otherwise:-) + * + * <appro@fy.chalmers.se> + */ + BN_ULONG a0,a1,a2,a3; + a0=B[0]; a1=B[1]; a2=B[2]; a3=B[3]; + A[0]=a0; A[1]=a1; A[2]=a2; A[3]=a3; + } + switch (b->top&3) + { + case 3: A[2]=B[2]; + case 2: A[1]=B[1]; + case 1: A[0]=B[0]; + case 0: ; /* ultrix cc workaround, see above */ + } +#endif + free(b->d); + } + + b->d=a; + b->dmax=words; + + /* Now need to zero any data between b->top and b->max */ + + A= &(b->d[b->top]); + for (i=(b->dmax - b->top)>>3; i>0; i--,A+=8) + { + A[0]=0; A[1]=0; A[2]=0; A[3]=0; + A[4]=0; A[5]=0; A[6]=0; A[7]=0; + } + for (i=(b->dmax - b->top)&7; i>0; i--,A++) + A[0]=0; +#else + memset(A,0,sizeof(BN_ULONG)*(words+1)); + memcpy(A,b->d,sizeof(b->d[0])*b->top); + b->d=a; + b->max=words; +#endif + +/* memset(&(p[b->max]),0,((words+1)-b->max)*sizeof(BN_ULONG)); */ +/* { int i; for (i=b->max; i<words+1; i++) p[i]=i;} */ + + } + return(b); + } + +BIGNUM *BN_copy(BIGNUM *a, const BIGNUM *b) + { + int i; + BN_ULONG *A; + const BN_ULONG *B; + + bn_check_top(b); + + if (a == b) return(a); + if (bn_wexpand(a,b->top) == NULL) return(NULL); + +#if 1 + A=a->d; + B=b->d; + for (i=b->top>>2; i>0; i--,A+=4,B+=4) + { + BN_ULONG a0,a1,a2,a3; + a0=B[0]; a1=B[1]; a2=B[2]; a3=B[3]; + A[0]=a0; A[1]=a1; A[2]=a2; A[3]=a3; + } + switch (b->top&3) + { + case 3: A[2]=B[2]; + case 2: A[1]=B[1]; + case 1: A[0]=B[0]; + case 0: ; /* ultrix cc workaround, see comments in bn_expand2 */ + } +#else + memcpy(a->d,b->d,sizeof(b->d[0])*b->top); +#endif + +/* memset(&(a->d[b->top]),0,sizeof(a->d[0])*(a->max-b->top));*/ + a->top=b->top; + if ((a->top == 0) && (a->d != NULL)) + a->d[0]=0; + a->neg=b->neg; + return(a); + } + +int BN_set_word(BIGNUM *a, BN_ULONG w) + { + int i,n; + if (bn_expand(a,sizeof(BN_ULONG)*8) == NULL) return(0); + + n=sizeof(BN_ULONG)/BN_BYTES; + a->neg=0; + a->top=0; + a->d[0]=(BN_ULONG)w&BN_MASK2; + if (a->d[0] != 0) a->top=1; + for (i=1; i<n; i++) + { + /* the following is done instead of + * w>>=BN_BITS2 so compilers don't complain + * on builds where sizeof(long) == BN_TYPES */ +#ifndef SIXTY_FOUR_BIT /* the data item > unsigned long */ + w>>=BN_BITS4; + w>>=BN_BITS4; +#else + w=0; +#endif + a->d[i]=(BN_ULONG)w&BN_MASK2; + if (a->d[i] != 0) a->top=i+1; + } + return(1); + } + +/* ignore negative */ +BIGNUM *BN_bin2bn(const unsigned char *s, int len, BIGNUM *ret) + { + unsigned int i,m; + unsigned int n; + BN_ULONG l; + + if (ret == NULL) ret=BN_new(); + if (ret == NULL) return(NULL); + l=0; + n=len; + if (n == 0) + { + ret->top=0; + return(ret); + } + if (bn_expand(ret,(int)(n+2)*8) == NULL) + return(NULL); + i=((n-1)/BN_BYTES)+1; + m=((n-1)%(BN_BYTES)); + ret->top=i; + while (n-- > 0) + { + l=(l<<8L)| *(s++); + if (m-- == 0) + { + ret->d[--i]=l; + l=0; + m=BN_BYTES-1; + } + } + /* need to call this due to clear byte at top if avoiding + * having the top bit set (-ve number) */ + bn_fix_top(ret); + return(ret); + } + +/* ignore negative */ +int BN_bn2bin(const BIGNUM *a, unsigned char *to) + { + int n,i; + BN_ULONG l; + + n=i=BN_num_bytes(a); + while (i-- > 0) + { + l=a->d[i/BN_BYTES]; + *(to++)=(unsigned char)(l>>(8*(i%BN_BYTES)))&0xff; + } + return(n); + } + +int BN_ucmp(const BIGNUM *a, const BIGNUM *b) + { + int i; + BN_ULONG t1,t2,*ap,*bp; + + bn_check_top(a); + bn_check_top(b); + + i=a->top-b->top; + if (i != 0) return(i); + ap=a->d; + bp=b->d; + for (i=a->top-1; i>=0; i--) + { + t1= ap[i]; + t2= bp[i]; + if (t1 != t2) + return(t1 > t2?1:-1); + } + return(0); + } + +int BN_cmp(const BIGNUM *a, const BIGNUM *b) + { + int i; + int gt,lt; + BN_ULONG t1,t2; + + if ((a == NULL) || (b == NULL)) + { + if (a != NULL) + return(-1); + else if (b != NULL) + return(1); + else + return(0); + } + + bn_check_top(a); + bn_check_top(b); + + if (a->neg != b->neg) + { + if (a->neg) + return(-1); + else return(1); + } + if (a->neg == 0) + { gt=1; lt= -1; } + else { gt= -1; lt=1; } + + if (a->top > b->top) return(gt); + if (a->top < b->top) return(lt); + for (i=a->top-1; i>=0; i--) + { + t1=a->d[i]; + t2=b->d[i]; + if (t1 > t2) return(gt); + if (t1 < t2) return(lt); + } + return(0); + } + +int BN_is_bit_set(const BIGNUM *a, int n) + { + int i,j; + + if (n < 0) return(0); + i=n/BN_BITS2; + j=n%BN_BITS2; + if (a->top <= i) return(0); + return((a->d[i]&(((BN_ULONG)1)<<j))?1:0); + } diff --git a/package/network/services/ead/src/tinysrp/bn_mul.c b/package/network/services/ead/src/tinysrp/bn_mul.c new file mode 100644 index 0000000000..d2d9fc5571 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_mul.c @@ -0,0 +1,176 @@ +/* crypto/bn/bn_mul.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include <stdio.h> +#include <string.h> +#include "bn_lcl.h" + +int BN_mul(BIGNUM *r, BIGNUM *a, BIGNUM *b, BN_CTX *ctx) + { + int top,al,bl; + BIGNUM *rr; + int ret = 0; +#if defined(BN_MUL_COMBA) || defined(BN_RECURSION) + int i; +#endif +#ifdef BN_RECURSION + BIGNUM *t; + int j,k; +#endif + +#ifdef BN_COUNT + printf("BN_mul %d * %d\n",a->top,b->top); +#endif + + bn_check_top(a); + bn_check_top(b); + bn_check_top(r); + + al=a->top; + bl=b->top; + + if ((al == 0) || (bl == 0)) + { + BN_zero(r); + return(1); + } + top=al+bl; + + BN_CTX_start(ctx); + if ((r == a) || (r == b)) + { + if ((rr = BN_CTX_get(ctx)) == NULL) goto err; + } + else + rr = r; + rr->neg=a->neg^b->neg; + +#if defined(BN_MUL_COMBA) || defined(BN_RECURSION) + i = al-bl; +#endif +#ifdef BN_MUL_COMBA + if (i == 0) + { +# if 0 + if (al == 4) + { + if (bn_wexpand(rr,8) == NULL) goto err; + rr->top=8; + bn_mul_comba4(rr->d,a->d,b->d); + goto end; + } +# endif + if (al == 8) + { + if (bn_wexpand(rr,16) == NULL) goto err; + rr->top=16; + bn_mul_comba8(rr->d,a->d,b->d); + goto end; + } + } +#endif /* BN_MUL_COMBA */ + if (bn_wexpand(rr,top) == NULL) goto err; + rr->top=top; + bn_mul_normal(rr->d,a->d,al,b->d,bl); + +#if defined(BN_MUL_COMBA) || defined(BN_RECURSION) +end: +#endif + bn_fix_top(rr); + if (r != rr) BN_copy(r,rr); + ret=1; +err: + BN_CTX_end(ctx); + return(ret); + } + +void bn_mul_normal(BN_ULONG *r, BN_ULONG *a, int na, BN_ULONG *b, int nb) + { + BN_ULONG *rr; + +#ifdef BN_COUNT + printf(" bn_mul_normal %d * %d\n",na,nb); +#endif + + if (na < nb) + { + int itmp; + BN_ULONG *ltmp; + + itmp=na; na=nb; nb=itmp; + ltmp=a; a=b; b=ltmp; + + } + rr= &(r[na]); + rr[0]=bn_mul_words(r,a,na,b[0]); + + for (;;) + { + if (--nb <= 0) return; + rr[1]=bn_mul_add_words(&(r[1]),a,na,b[1]); + if (--nb <= 0) return; + rr[2]=bn_mul_add_words(&(r[2]),a,na,b[2]); + if (--nb <= 0) return; + rr[3]=bn_mul_add_words(&(r[3]),a,na,b[3]); + if (--nb <= 0) return; + rr[4]=bn_mul_add_words(&(r[4]),a,na,b[4]); + rr+=4; + r+=4; + b+=4; + } + } diff --git a/package/network/services/ead/src/tinysrp/bn_prime.h b/package/network/services/ead/src/tinysrp/bn_prime.h new file mode 100644 index 0000000000..b7cf9a9bfe --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_prime.h @@ -0,0 +1,325 @@ +/* Auto generated by bn_prime.pl */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#ifndef EIGHT_BIT +#define NUMPRIMES 2048 +#else +#define NUMPRIMES 54 +#endif +static const unsigned int primes[NUMPRIMES]= + { + 2, 3, 5, 7, 11, 13, 17, 19, + 23, 29, 31, 37, 41, 43, 47, 53, + 59, 61, 67, 71, 73, 79, 83, 89, + 97, 101, 103, 107, 109, 113, 127, 131, + 137, 139, 149, 151, 157, 163, 167, 173, + 179, 181, 191, 193, 197, 199, 211, 223, + 227, 229, 233, 239, 241, 251, +#ifndef EIGHT_BIT + 257, 263, + 269, 271, 277, 281, 283, 293, 307, 311, + 313, 317, 331, 337, 347, 349, 353, 359, + 367, 373, 379, 383, 389, 397, 401, 409, + 419, 421, 431, 433, 439, 443, 449, 457, + 461, 463, 467, 479, 487, 491, 499, 503, + 509, 521, 523, 541, 547, 557, 563, 569, + 571, 577, 587, 593, 599, 601, 607, 613, + 617, 619, 631, 641, 643, 647, 653, 659, + 661, 673, 677, 683, 691, 701, 709, 719, + 727, 733, 739, 743, 751, 757, 761, 769, + 773, 787, 797, 809, 811, 821, 823, 827, + 829, 839, 853, 857, 859, 863, 877, 881, + 883, 887, 907, 911, 919, 929, 937, 941, + 947, 953, 967, 971, 977, 983, 991, 997, + 1009,1013,1019,1021,1031,1033,1039,1049, + 1051,1061,1063,1069,1087,1091,1093,1097, + 1103,1109,1117,1123,1129,1151,1153,1163, + 1171,1181,1187,1193,1201,1213,1217,1223, + 1229,1231,1237,1249,1259,1277,1279,1283, + 1289,1291,1297,1301,1303,1307,1319,1321, + 1327,1361,1367,1373,1381,1399,1409,1423, + 1427,1429,1433,1439,1447,1451,1453,1459, + 1471,1481,1483,1487,1489,1493,1499,1511, + 1523,1531,1543,1549,1553,1559,1567,1571, + 1579,1583,1597,1601,1607,1609,1613,1619, + 1621,1627,1637,1657,1663,1667,1669,1693, + 1697,1699,1709,1721,1723,1733,1741,1747, + 1753,1759,1777,1783,1787,1789,1801,1811, + 1823,1831,1847,1861,1867,1871,1873,1877, + 1879,1889,1901,1907,1913,1931,1933,1949, + 1951,1973,1979,1987,1993,1997,1999,2003, + 2011,2017,2027,2029,2039,2053,2063,2069, + 2081,2083,2087,2089,2099,2111,2113,2129, + 2131,2137,2141,2143,2153,2161,2179,2203, + 2207,2213,2221,2237,2239,2243,2251,2267, + 2269,2273,2281,2287,2293,2297,2309,2311, + 2333,2339,2341,2347,2351,2357,2371,2377, + 2381,2383,2389,2393,2399,2411,2417,2423, + 2437,2441,2447,2459,2467,2473,2477,2503, + 2521,2531,2539,2543,2549,2551,2557,2579, + 2591,2593,2609,2617,2621,2633,2647,2657, + 2659,2663,2671,2677,2683,2687,2689,2693, + 2699,2707,2711,2713,2719,2729,2731,2741, + 2749,2753,2767,2777,2789,2791,2797,2801, + 2803,2819,2833,2837,2843,2851,2857,2861, + 2879,2887,2897,2903,2909,2917,2927,2939, + 2953,2957,2963,2969,2971,2999,3001,3011, + 3019,3023,3037,3041,3049,3061,3067,3079, + 3083,3089,3109,3119,3121,3137,3163,3167, + 3169,3181,3187,3191,3203,3209,3217,3221, + 3229,3251,3253,3257,3259,3271,3299,3301, + 3307,3313,3319,3323,3329,3331,3343,3347, + 3359,3361,3371,3373,3389,3391,3407,3413, + 3433,3449,3457,3461,3463,3467,3469,3491, + 3499,3511,3517,3527,3529,3533,3539,3541, + 3547,3557,3559,3571,3581,3583,3593,3607, + 3613,3617,3623,3631,3637,3643,3659,3671, + 3673,3677,3691,3697,3701,3709,3719,3727, + 3733,3739,3761,3767,3769,3779,3793,3797, + 3803,3821,3823,3833,3847,3851,3853,3863, + 3877,3881,3889,3907,3911,3917,3919,3923, + 3929,3931,3943,3947,3967,3989,4001,4003, + 4007,4013,4019,4021,4027,4049,4051,4057, + 4073,4079,4091,4093,4099,4111,4127,4129, + 4133,4139,4153,4157,4159,4177,4201,4211, + 4217,4219,4229,4231,4241,4243,4253,4259, + 4261,4271,4273,4283,4289,4297,4327,4337, + 4339,4349,4357,4363,4373,4391,4397,4409, + 4421,4423,4441,4447,4451,4457,4463,4481, + 4483,4493,4507,4513,4517,4519,4523,4547, + 4549,4561,4567,4583,4591,4597,4603,4621, + 4637,4639,4643,4649,4651,4657,4663,4673, + 4679,4691,4703,4721,4723,4729,4733,4751, + 4759,4783,4787,4789,4793,4799,4801,4813, + 4817,4831,4861,4871,4877,4889,4903,4909, + 4919,4931,4933,4937,4943,4951,4957,4967, + 4969,4973,4987,4993,4999,5003,5009,5011, + 5021,5023,5039,5051,5059,5077,5081,5087, + 5099,5101,5107,5113,5119,5147,5153,5167, + 5171,5179,5189,5197,5209,5227,5231,5233, + 5237,5261,5273,5279,5281,5297,5303,5309, + 5323,5333,5347,5351,5381,5387,5393,5399, + 5407,5413,5417,5419,5431,5437,5441,5443, + 5449,5471,5477,5479,5483,5501,5503,5507, + 5519,5521,5527,5531,5557,5563,5569,5573, + 5581,5591,5623,5639,5641,5647,5651,5653, + 5657,5659,5669,5683,5689,5693,5701,5711, + 5717,5737,5741,5743,5749,5779,5783,5791, + 5801,5807,5813,5821,5827,5839,5843,5849, + 5851,5857,5861,5867,5869,5879,5881,5897, + 5903,5923,5927,5939,5953,5981,5987,6007, + 6011,6029,6037,6043,6047,6053,6067,6073, + 6079,6089,6091,6101,6113,6121,6131,6133, + 6143,6151,6163,6173,6197,6199,6203,6211, + 6217,6221,6229,6247,6257,6263,6269,6271, + 6277,6287,6299,6301,6311,6317,6323,6329, + 6337,6343,6353,6359,6361,6367,6373,6379, + 6389,6397,6421,6427,6449,6451,6469,6473, + 6481,6491,6521,6529,6547,6551,6553,6563, + 6569,6571,6577,6581,6599,6607,6619,6637, + 6653,6659,6661,6673,6679,6689,6691,6701, + 6703,6709,6719,6733,6737,6761,6763,6779, + 6781,6791,6793,6803,6823,6827,6829,6833, + 6841,6857,6863,6869,6871,6883,6899,6907, + 6911,6917,6947,6949,6959,6961,6967,6971, + 6977,6983,6991,6997,7001,7013,7019,7027, + 7039,7043,7057,7069,7079,7103,7109,7121, + 7127,7129,7151,7159,7177,7187,7193,7207, + 7211,7213,7219,7229,7237,7243,7247,7253, + 7283,7297,7307,7309,7321,7331,7333,7349, + 7351,7369,7393,7411,7417,7433,7451,7457, + 7459,7477,7481,7487,7489,7499,7507,7517, + 7523,7529,7537,7541,7547,7549,7559,7561, + 7573,7577,7583,7589,7591,7603,7607,7621, + 7639,7643,7649,7669,7673,7681,7687,7691, + 7699,7703,7717,7723,7727,7741,7753,7757, + 7759,7789,7793,7817,7823,7829,7841,7853, + 7867,7873,7877,7879,7883,7901,7907,7919, + 7927,7933,7937,7949,7951,7963,7993,8009, + 8011,8017,8039,8053,8059,8069,8081,8087, + 8089,8093,8101,8111,8117,8123,8147,8161, + 8167,8171,8179,8191,8209,8219,8221,8231, + 8233,8237,8243,8263,8269,8273,8287,8291, + 8293,8297,8311,8317,8329,8353,8363,8369, + 8377,8387,8389,8419,8423,8429,8431,8443, + 8447,8461,8467,8501,8513,8521,8527,8537, + 8539,8543,8563,8573,8581,8597,8599,8609, + 8623,8627,8629,8641,8647,8663,8669,8677, + 8681,8689,8693,8699,8707,8713,8719,8731, + 8737,8741,8747,8753,8761,8779,8783,8803, + 8807,8819,8821,8831,8837,8839,8849,8861, + 8863,8867,8887,8893,8923,8929,8933,8941, + 8951,8963,8969,8971,8999,9001,9007,9011, + 9013,9029,9041,9043,9049,9059,9067,9091, + 9103,9109,9127,9133,9137,9151,9157,9161, + 9173,9181,9187,9199,9203,9209,9221,9227, + 9239,9241,9257,9277,9281,9283,9293,9311, + 9319,9323,9337,9341,9343,9349,9371,9377, + 9391,9397,9403,9413,9419,9421,9431,9433, + 9437,9439,9461,9463,9467,9473,9479,9491, + 9497,9511,9521,9533,9539,9547,9551,9587, + 9601,9613,9619,9623,9629,9631,9643,9649, + 9661,9677,9679,9689,9697,9719,9721,9733, + 9739,9743,9749,9767,9769,9781,9787,9791, + 9803,9811,9817,9829,9833,9839,9851,9857, + 9859,9871,9883,9887,9901,9907,9923,9929, + 9931,9941,9949,9967,9973,10007,10009,10037, + 10039,10061,10067,10069,10079,10091,10093,10099, + 10103,10111,10133,10139,10141,10151,10159,10163, + 10169,10177,10181,10193,10211,10223,10243,10247, + 10253,10259,10267,10271,10273,10289,10301,10303, + 10313,10321,10331,10333,10337,10343,10357,10369, + 10391,10399,10427,10429,10433,10453,10457,10459, + 10463,10477,10487,10499,10501,10513,10529,10531, + 10559,10567,10589,10597,10601,10607,10613,10627, + 10631,10639,10651,10657,10663,10667,10687,10691, + 10709,10711,10723,10729,10733,10739,10753,10771, + 10781,10789,10799,10831,10837,10847,10853,10859, + 10861,10867,10883,10889,10891,10903,10909,10937, + 10939,10949,10957,10973,10979,10987,10993,11003, + 11027,11047,11057,11059,11069,11071,11083,11087, + 11093,11113,11117,11119,11131,11149,11159,11161, + 11171,11173,11177,11197,11213,11239,11243,11251, + 11257,11261,11273,11279,11287,11299,11311,11317, + 11321,11329,11351,11353,11369,11383,11393,11399, + 11411,11423,11437,11443,11447,11467,11471,11483, + 11489,11491,11497,11503,11519,11527,11549,11551, + 11579,11587,11593,11597,11617,11621,11633,11657, + 11677,11681,11689,11699,11701,11717,11719,11731, + 11743,11777,11779,11783,11789,11801,11807,11813, + 11821,11827,11831,11833,11839,11863,11867,11887, + 11897,11903,11909,11923,11927,11933,11939,11941, + 11953,11959,11969,11971,11981,11987,12007,12011, + 12037,12041,12043,12049,12071,12073,12097,12101, + 12107,12109,12113,12119,12143,12149,12157,12161, + 12163,12197,12203,12211,12227,12239,12241,12251, + 12253,12263,12269,12277,12281,12289,12301,12323, + 12329,12343,12347,12373,12377,12379,12391,12401, + 12409,12413,12421,12433,12437,12451,12457,12473, + 12479,12487,12491,12497,12503,12511,12517,12527, + 12539,12541,12547,12553,12569,12577,12583,12589, + 12601,12611,12613,12619,12637,12641,12647,12653, + 12659,12671,12689,12697,12703,12713,12721,12739, + 12743,12757,12763,12781,12791,12799,12809,12821, + 12823,12829,12841,12853,12889,12893,12899,12907, + 12911,12917,12919,12923,12941,12953,12959,12967, + 12973,12979,12983,13001,13003,13007,13009,13033, + 13037,13043,13049,13063,13093,13099,13103,13109, + 13121,13127,13147,13151,13159,13163,13171,13177, + 13183,13187,13217,13219,13229,13241,13249,13259, + 13267,13291,13297,13309,13313,13327,13331,13337, + 13339,13367,13381,13397,13399,13411,13417,13421, + 13441,13451,13457,13463,13469,13477,13487,13499, + 13513,13523,13537,13553,13567,13577,13591,13597, + 13613,13619,13627,13633,13649,13669,13679,13681, + 13687,13691,13693,13697,13709,13711,13721,13723, + 13729,13751,13757,13759,13763,13781,13789,13799, + 13807,13829,13831,13841,13859,13873,13877,13879, + 13883,13901,13903,13907,13913,13921,13931,13933, + 13963,13967,13997,13999,14009,14011,14029,14033, + 14051,14057,14071,14081,14083,14087,14107,14143, + 14149,14153,14159,14173,14177,14197,14207,14221, + 14243,14249,14251,14281,14293,14303,14321,14323, + 14327,14341,14347,14369,14387,14389,14401,14407, + 14411,14419,14423,14431,14437,14447,14449,14461, + 14479,14489,14503,14519,14533,14537,14543,14549, + 14551,14557,14561,14563,14591,14593,14621,14627, + 14629,14633,14639,14653,14657,14669,14683,14699, + 14713,14717,14723,14731,14737,14741,14747,14753, + 14759,14767,14771,14779,14783,14797,14813,14821, + 14827,14831,14843,14851,14867,14869,14879,14887, + 14891,14897,14923,14929,14939,14947,14951,14957, + 14969,14983,15013,15017,15031,15053,15061,15073, + 15077,15083,15091,15101,15107,15121,15131,15137, + 15139,15149,15161,15173,15187,15193,15199,15217, + 15227,15233,15241,15259,15263,15269,15271,15277, + 15287,15289,15299,15307,15313,15319,15329,15331, + 15349,15359,15361,15373,15377,15383,15391,15401, + 15413,15427,15439,15443,15451,15461,15467,15473, + 15493,15497,15511,15527,15541,15551,15559,15569, + 15581,15583,15601,15607,15619,15629,15641,15643, + 15647,15649,15661,15667,15671,15679,15683,15727, + 15731,15733,15737,15739,15749,15761,15767,15773, + 15787,15791,15797,15803,15809,15817,15823,15859, + 15877,15881,15887,15889,15901,15907,15913,15919, + 15923,15937,15959,15971,15973,15991,16001,16007, + 16033,16057,16061,16063,16067,16069,16073,16087, + 16091,16097,16103,16111,16127,16139,16141,16183, + 16187,16189,16193,16217,16223,16229,16231,16249, + 16253,16267,16273,16301,16319,16333,16339,16349, + 16361,16363,16369,16381,16411,16417,16421,16427, + 16433,16447,16451,16453,16477,16481,16487,16493, + 16519,16529,16547,16553,16561,16567,16573,16603, + 16607,16619,16631,16633,16649,16651,16657,16661, + 16673,16691,16693,16699,16703,16729,16741,16747, + 16759,16763,16787,16811,16823,16829,16831,16843, + 16871,16879,16883,16889,16901,16903,16921,16927, + 16931,16937,16943,16963,16979,16981,16987,16993, + 17011,17021,17027,17029,17033,17041,17047,17053, + 17077,17093,17099,17107,17117,17123,17137,17159, + 17167,17183,17189,17191,17203,17207,17209,17231, + 17239,17257,17291,17293,17299,17317,17321,17327, + 17333,17341,17351,17359,17377,17383,17387,17389, + 17393,17401,17417,17419,17431,17443,17449,17467, + 17471,17477,17483,17489,17491,17497,17509,17519, + 17539,17551,17569,17573,17579,17581,17597,17599, + 17609,17623,17627,17657,17659,17669,17681,17683, + 17707,17713,17729,17737,17747,17749,17761,17783, + 17789,17791,17807,17827,17837,17839,17851,17863, +#endif + }; diff --git a/package/network/services/ead/src/tinysrp/bn_shift.c b/package/network/services/ead/src/tinysrp/bn_shift.c new file mode 100644 index 0000000000..f403720ecc --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_shift.c @@ -0,0 +1,139 @@ +/* crypto/bn/bn_shift.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include <stdio.h> +#include <string.h> +#include "bn_lcl.h" + +int BN_lshift(BIGNUM *r, const BIGNUM *a, int n) + { + int i,nw,lb,rb; + BN_ULONG *t,*f; + BN_ULONG l; + + r->neg=a->neg; + if (bn_wexpand(r,a->top+(n/BN_BITS2)+1) == NULL) return(0); + nw=n/BN_BITS2; + lb=n%BN_BITS2; + rb=BN_BITS2-lb; + f=a->d; + t=r->d; + t[a->top+nw]=0; + if (lb == 0) + for (i=a->top-1; i>=0; i--) + t[nw+i]=f[i]; + else + for (i=a->top-1; i>=0; i--) + { + l=f[i]; + t[nw+i+1]|=(l>>rb)&BN_MASK2; + t[nw+i]=(l<<lb)&BN_MASK2; + } + memset(t,0,nw*sizeof(t[0])); +/* for (i=0; i<nw; i++) + t[i]=0;*/ + r->top=a->top+nw+1; + bn_fix_top(r); + return(1); + } + +int BN_rshift(BIGNUM *r, BIGNUM *a, int n) + { + int i,j,nw,lb,rb; + BN_ULONG *t,*f; + BN_ULONG l,tmp; + + nw=n/BN_BITS2; + rb=n%BN_BITS2; + lb=BN_BITS2-rb; + if (nw > a->top || a->top == 0) + { + BN_zero(r); + return(1); + } + if (r != a) + { + r->neg=a->neg; + if (bn_wexpand(r,a->top-nw+1) == NULL) return(0); + } + + f= &(a->d[nw]); + t=r->d; + j=a->top-nw; + r->top=j; + + if (rb == 0) + { + for (i=j+1; i > 0; i--) + *(t++)= *(f++); + } + else + { + l= *(f++); + for (i=1; i<j; i++) + { + tmp =(l>>rb)&BN_MASK2; + l= *(f++); + *(t++) =(tmp|(l<<lb))&BN_MASK2; + } + *(t++) =(l>>rb)&BN_MASK2; + } + *t=0; + bn_fix_top(r); + return(1); + } diff --git a/package/network/services/ead/src/tinysrp/bn_sqr.c b/package/network/services/ead/src/tinysrp/bn_sqr.c new file mode 100644 index 0000000000..2d3db70e35 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_sqr.c @@ -0,0 +1,160 @@ +/* crypto/bn/bn_sqr.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include <stdio.h> +#include <string.h> +#include "bn_lcl.h" + +/* r must not be a */ +/* I've just gone over this and it is now %20 faster on x86 - eay - 27 Jun 96 */ +int BN_sqr(BIGNUM *r, BIGNUM *a, BN_CTX *ctx) + { + int max,al; + int ret = 0; + BIGNUM *tmp,*rr; + +#ifdef BN_COUNT +printf("BN_sqr %d * %d\n",a->top,a->top); +#endif + bn_check_top(a); + + al=a->top; + if (al <= 0) + { + r->top=0; + return(1); + } + + BN_CTX_start(ctx); + rr=(a != r) ? r : BN_CTX_get(ctx); + tmp=BN_CTX_get(ctx); + if (tmp == NULL) goto err; + + max=(al+al); + if (bn_wexpand(rr,max+1) == NULL) goto err; + + r->neg=0; + if (al == 4) + { +#ifndef BN_SQR_COMBA + BN_ULONG t[8]; + bn_sqr_normal(rr->d,a->d,4,t); +#else + bn_sqr_comba4(rr->d,a->d); +#endif + } + else if (al == 8) + { +#ifndef BN_SQR_COMBA + BN_ULONG t[16]; + bn_sqr_normal(rr->d,a->d,8,t); +#else + bn_sqr_comba8(rr->d,a->d); +#endif + } + else + { + if (bn_wexpand(tmp,max) == NULL) goto err; + bn_sqr_normal(rr->d,a->d,al,tmp->d); + } + + rr->top=max; + if ((max > 0) && (rr->d[max-1] == 0)) rr->top--; + if (rr != r) BN_copy(r,rr); + ret = 1; + err: + BN_CTX_end(ctx); + return(ret); + } + +/* tmp must have 2*n words */ +void bn_sqr_normal(BN_ULONG *r, BN_ULONG *a, int n, BN_ULONG *tmp) + { + int i,j,max; + BN_ULONG *ap,*rp; + + max=n*2; + ap=a; + rp=r; + rp[0]=rp[max-1]=0; + rp++; + j=n; + + if (--j > 0) + { + ap++; + rp[j]=bn_mul_words(rp,ap,j,ap[-1]); + rp+=2; + } + + for (i=n-2; i>0; i--) + { + j--; + ap++; + rp[j]=bn_mul_add_words(rp,ap,j,ap[-1]); + rp+=2; + } + + bn_add_words(r,r,r,max); + + /* There will not be a carry */ + + bn_sqr_words(tmp,a,n); + + bn_add_words(r,r,tmp,max); + } diff --git a/package/network/services/ead/src/tinysrp/bn_word.c b/package/network/services/ead/src/tinysrp/bn_word.c new file mode 100644 index 0000000000..7820e08a8a --- /dev/null +++ b/package/network/services/ead/src/tinysrp/bn_word.c @@ -0,0 +1,130 @@ +/* crypto/bn/bn_word.c */ +/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) + * All rights reserved. + * + * This package is an SSL implementation written + * by Eric Young (eay@cryptsoft.com). + * The implementation was written so as to conform with Netscapes SSL. + * + * This library is free for commercial and non-commercial use as long as + * the following conditions are aheared to. The following conditions + * apply to all code found in this distribution, be it the RC4, RSA, + * lhash, DES, etc., code; not just the SSL code. The SSL documentation + * included with this distribution is covered by the same copyright terms + * except that the holder is Tim Hudson (tjh@cryptsoft.com). + * + * Copyright remains Eric Young's, and as such any Copyright notices in + * the code are not to be removed. + * If this package is used in a product, Eric Young should be given attribution + * as the author of the parts of the library used. + * This can be in the form of a textual message at program startup or + * in documentation (online or textual) provided with the package. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * "This product includes cryptographic software written by + * Eric Young (eay@cryptsoft.com)" + * The word 'cryptographic' can be left out if the rouines from the library + * being used are not cryptographic related :-). + * 4. If you include any Windows specific code (or a derivative thereof) from + * the apps directory (application code) you must include an acknowledgement: + * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" + * + * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * The licence and distribution terms for any publically available version or + * derivative of this code cannot be changed. i.e. this code cannot simply be + * copied and put under another distribution licence + * [including the GNU Public Licence.] + */ + +#include <stdio.h> +#include "bn_lcl.h" + +int BN_add_word(BIGNUM *a, BN_ULONG w) + { + BN_ULONG l; + int i; + + if (a->neg) + { + a->neg=0; + i=BN_sub_word(a,w); + if (!BN_is_zero(a)) + a->neg=!(a->neg); + return(i); + } + w&=BN_MASK2; + if (bn_wexpand(a,a->top+1) == NULL) return(0); + i=0; + for (;;) + { + l=(a->d[i]+(BN_ULONG)w)&BN_MASK2; + a->d[i]=l; + if (w > l) + w=1; + else + break; + i++; + } + if (i >= a->top) + a->top++; + return(1); + } + +int BN_sub_word(BIGNUM *a, BN_ULONG w) + { + int i; + + if (BN_is_zero(a) || a->neg) + { + a->neg=0; + i=BN_add_word(a,w); + a->neg=1; + return(i); + } + + w&=BN_MASK2; + if ((a->top == 1) && (a->d[0] < w)) + { + a->d[0]=w-a->d[0]; + a->neg=1; + return(1); + } + i=0; + for (;;) + { + if (a->d[i] >= w) + { + a->d[i]-=w; + break; + } + else + { + a->d[i]=(a->d[i]-w)&BN_MASK2; + i++; + w=1; + } + } + if ((a->d[i] == 0) && (i == (a->top-1))) + a->top--; + return(1); + } diff --git a/package/network/services/ead/src/tinysrp/clitest.c b/package/network/services/ead/src/tinysrp/clitest.c new file mode 100644 index 0000000000..faaa5dd90d --- /dev/null +++ b/package/network/services/ead/src/tinysrp/clitest.c @@ -0,0 +1,112 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> +#include "t_defines.h" +#include "t_pwd.h" +#include "t_client.h" + +int +main() +{ + int index; + struct t_client * tc; + struct t_preconf *tcp; + struct t_num n; + struct t_num g; + struct t_num s; + struct t_num B; + char username[MAXUSERLEN]; + char hexbuf[MAXHEXPARAMLEN]; + char buf1[MAXPARAMLEN], buf2[MAXPARAMLEN], buf3[MAXSALTLEN]; + unsigned char cbuf[20]; + struct t_num * A; + unsigned char * skey; + char pass[128]; + + printf("Enter username: "); + fgets(username, sizeof(username), stdin); + username[strlen(username) - 1] = '\0'; + printf("Enter index (from server): "); + fgets(hexbuf, sizeof(hexbuf), stdin); + index = atoi(hexbuf); + tcp = t_getpreparam(index - 1); + printf("Enter salt (from server): "); + fgets(hexbuf, sizeof(hexbuf), stdin); + s.data = buf3; + s.len = t_fromb64(s.data, hexbuf); + + tc = t_clientopen(username, &tcp->modulus, &tcp->generator, &s); + if (tc == 0) { + printf("invalid n, g\n"); + exit(1); + } + + A = t_clientgenexp(tc); + printf("A (to server): %s\n", t_tob64(hexbuf, A->data, A->len)); + + t_getpass(pass, 128, "Enter password:"); + t_clientpasswd(tc, pass); + + printf("Enter B (from server): "); + fgets(hexbuf, sizeof(hexbuf), stdin); + B.data = buf1; + B.len = t_fromb64(B.data, hexbuf); + + skey = t_clientgetkey(tc, &B); + printf("Session key: %s\n", t_tohex(hexbuf, skey, 40)); + printf("Response (to server): %s\n", + t_tohex(hexbuf, t_clientresponse(tc), RESPONSE_LEN)); + + printf("Enter server response: "); + fgets(hexbuf, sizeof(hexbuf), stdin); + hexbuf[strlen(hexbuf) - 1] = '\0'; + t_fromhex(cbuf, hexbuf); + + if (t_clientverify(tc, cbuf) == 0) + printf("Server authentication successful.\n"); + else + printf("Server authentication failed.\n"); + + t_clientclose(tc); + + return 0; +} diff --git a/package/network/services/ead/src/tinysrp/config.h.in b/package/network/services/ead/src/tinysrp/config.h.in new file mode 100644 index 0000000000..a4b50c714a --- /dev/null +++ b/package/network/services/ead/src/tinysrp/config.h.in @@ -0,0 +1,79 @@ +/* config.h.in. Generated automatically from configure.in by autoheader. */ + +/* Define if type char is unsigned and you are not using gcc. */ +#ifndef __CHAR_UNSIGNED__ +#undef __CHAR_UNSIGNED__ +#endif + +/* Define to empty if the keyword does not work. */ +#undef const + +/* Define as __inline if that's what the C compiler calls it. */ +#undef inline + +/* Define as the return type of signal handlers (int or void). */ +#undef RETSIGTYPE + +/* Define if you have the ANSI C header files. */ +#undef STDC_HEADERS + +/* Define if you can safely include both <sys/time.h> and <time.h>. */ +#undef TIME_WITH_SYS_TIME + +/* Define if your processor stores words with the most significant + byte first (like Motorola and SPARC, unlike Intel and VAX). */ +#undef WORDS_BIGENDIAN + +#undef SHA1HANDSOFF + +#undef POSIX_TERMIOS + +#undef POSIX_SIGTYPE + +#undef volatile + +/* The number of bytes in a int. */ +#undef SIZEOF_INT + +/* The number of bytes in a long. */ +#undef SIZEOF_LONG + +/* The number of bytes in a long long. */ +#undef SIZEOF_LONG_LONG + +/* The number of bytes in a short. */ +#undef SIZEOF_SHORT + +/* Define if you have the memcpy function. */ +#undef HAVE_MEMCPY + +/* Define if you have the sigaction function. */ +#undef HAVE_SIGACTION + +/* Define if you have the strchr function. */ +#undef HAVE_STRCHR + +/* Define if you have the <sgtty.h> header file. */ +#undef HAVE_SGTTY_H + +/* Define if you have the <sys/ioctl.h> header file. */ +#undef HAVE_SYS_IOCTL_H + +/* Define if you have the <sys/time.h> header file. */ +#undef HAVE_SYS_TIME_H + +/* Define if you have the <termio.h> header file. */ +#undef HAVE_TERMIO_H + +/* Define if you have the <termios.h> header file. */ +#undef HAVE_TERMIOS_H + +/* Define if you have the <unistd.h> header file. */ +#undef HAVE_UNISTD_H + +/* Name of package */ +#undef PACKAGE + +/* Version number of package */ +#undef VERSION + diff --git a/package/network/services/ead/src/tinysrp/configure b/package/network/services/ead/src/tinysrp/configure new file mode 100755 index 0000000000..6ee76bf436 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/configure @@ -0,0 +1,2421 @@ +#! /bin/sh + +# Guess values for system-dependent variables and create Makefiles. +# Generated automatically using autoconf version 2.13 +# Copyright (C) 1992, 93, 94, 95, 96 Free Software Foundation, Inc. +# +# This configure script is free software; the Free Software Foundation +# gives unlimited permission to copy, distribute and modify it. + +# Defaults: +ac_help= +ac_default_prefix=/usr/local +# Any additions from configure.in: + +# Initialize some variables set by options. +# The variables have the same names as the options, with +# dashes changed to underlines. +build=NONE +cache_file=./config.cache +exec_prefix=NONE +host=NONE +no_create= +nonopt=NONE +no_recursion= +prefix=NONE +program_prefix=NONE +program_suffix=NONE +program_transform_name=s,x,x, +silent= +site= +srcdir= +target=NONE +verbose= +x_includes=NONE +x_libraries=NONE +bindir='${exec_prefix}/bin' +sbindir='${exec_prefix}/sbin' +libexecdir='${exec_prefix}/libexec' +datadir='${prefix}/share' +sysconfdir='${prefix}/etc' +sharedstatedir='${prefix}/com' +localstatedir='${prefix}/var' +libdir='${exec_prefix}/lib' +includedir='${prefix}/include' +oldincludedir='/usr/include' +infodir='${prefix}/info' +mandir='${prefix}/man' + +# Initialize some other variables. +subdirs= +MFLAGS= MAKEFLAGS= +SHELL=${CONFIG_SHELL-/bin/sh} +# Maximum number of lines to put in a shell here document. +ac_max_here_lines=12 + +ac_prev= +for ac_option +do + + # If the previous option needs an argument, assign it. + if test -n "$ac_prev"; then + eval "$ac_prev=\$ac_option" + ac_prev= + continue + fi + + case "$ac_option" in + -*=*) ac_optarg=`echo "$ac_option" | sed 's/[-_a-zA-Z0-9]*=//'` ;; + *) ac_optarg= ;; + esac + + # Accept the important Cygnus configure options, so we can diagnose typos. + + case "$ac_option" in + + -bindir | --bindir | --bindi | --bind | --bin | --bi) + ac_prev=bindir ;; + -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) + bindir="$ac_optarg" ;; + + -build | --build | --buil | --bui | --bu) + ac_prev=build ;; + -build=* | --build=* | --buil=* | --bui=* | --bu=*) + build="$ac_optarg" ;; + + -cache-file | --cache-file | --cache-fil | --cache-fi \ + | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) + ac_prev=cache_file ;; + -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ + | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) + cache_file="$ac_optarg" ;; + + -datadir | --datadir | --datadi | --datad | --data | --dat | --da) + ac_prev=datadir ;; + -datadir=* | --datadir=* | --datadi=* | --datad=* | --data=* | --dat=* \ + | --da=*) + datadir="$ac_optarg" ;; + + -disable-* | --disable-*) + ac_feature=`echo $ac_option|sed -e 's/-*disable-//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_feature| sed 's/[-a-zA-Z0-9_]//g'`"; then + { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } + fi + ac_feature=`echo $ac_feature| sed 's/-/_/g'` + eval "enable_${ac_feature}=no" ;; + + -enable-* | --enable-*) + ac_feature=`echo $ac_option|sed -e 's/-*enable-//' -e 's/=.*//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_feature| sed 's/[-_a-zA-Z0-9]//g'`"; then + { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } + fi + ac_feature=`echo $ac_feature| sed 's/-/_/g'` + case "$ac_option" in + *=*) ;; + *) ac_optarg=yes ;; + esac + eval "enable_${ac_feature}='$ac_optarg'" ;; + + -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ + | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ + | --exec | --exe | --ex) + ac_prev=exec_prefix ;; + -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ + | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ + | --exec=* | --exe=* | --ex=*) + exec_prefix="$ac_optarg" ;; + + -gas | --gas | --ga | --g) + # Obsolete; use --with-gas. + with_gas=yes ;; + + -help | --help | --hel | --he) + # Omit some internal or obsolete options to make the list less imposing. + # This message is too long to be a string in the A/UX 3.1 sh. + cat << EOF +Usage: configure [options] [host] +Options: [defaults in brackets after descriptions] +Configuration: + --cache-file=FILE cache test results in FILE + --help print this message + --no-create do not create output files + --quiet, --silent do not print \`checking...' messages + --version print the version of autoconf that created configure +Directory and file names: + --prefix=PREFIX install architecture-independent files in PREFIX + [$ac_default_prefix] + --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX + [same as prefix] + --bindir=DIR user executables in DIR [EPREFIX/bin] + --sbindir=DIR system admin executables in DIR [EPREFIX/sbin] + --libexecdir=DIR program executables in DIR [EPREFIX/libexec] + --datadir=DIR read-only architecture-independent data in DIR + [PREFIX/share] + --sysconfdir=DIR read-only single-machine data in DIR [PREFIX/etc] + --sharedstatedir=DIR modifiable architecture-independent data in DIR + [PREFIX/com] + --localstatedir=DIR modifiable single-machine data in DIR [PREFIX/var] + --libdir=DIR object code libraries in DIR [EPREFIX/lib] + --includedir=DIR C header files in DIR [PREFIX/include] + --oldincludedir=DIR C header files for non-gcc in DIR [/usr/include] + --infodir=DIR info documentation in DIR [PREFIX/info] + --mandir=DIR man documentation in DIR [PREFIX/man] + --srcdir=DIR find the sources in DIR [configure dir or ..] + --program-prefix=PREFIX prepend PREFIX to installed program names + --program-suffix=SUFFIX append SUFFIX to installed program names + --program-transform-name=PROGRAM + run sed PROGRAM on installed program names +EOF + cat << EOF +Host type: + --build=BUILD configure for building on BUILD [BUILD=HOST] + --host=HOST configure for HOST [guessed] + --target=TARGET configure for TARGET [TARGET=HOST] +Features and packages: + --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) + --enable-FEATURE[=ARG] include FEATURE [ARG=yes] + --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] + --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) + --x-includes=DIR X include files are in DIR + --x-libraries=DIR X library files are in DIR +EOF + if test -n "$ac_help"; then + echo "--enable and --with options recognized:$ac_help" + fi + exit 0 ;; + + -host | --host | --hos | --ho) + ac_prev=host ;; + -host=* | --host=* | --hos=* | --ho=*) + host="$ac_optarg" ;; + + -includedir | --includedir | --includedi | --included | --include \ + | --includ | --inclu | --incl | --inc) + ac_prev=includedir ;; + -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ + | --includ=* | --inclu=* | --incl=* | --inc=*) + includedir="$ac_optarg" ;; + + -infodir | --infodir | --infodi | --infod | --info | --inf) + ac_prev=infodir ;; + -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) + infodir="$ac_optarg" ;; + + -libdir | --libdir | --libdi | --libd) + ac_prev=libdir ;; + -libdir=* | --libdir=* | --libdi=* | --libd=*) + libdir="$ac_optarg" ;; + + -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ + | --libexe | --libex | --libe) + ac_prev=libexecdir ;; + -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ + | --libexe=* | --libex=* | --libe=*) + libexecdir="$ac_optarg" ;; + + -localstatedir | --localstatedir | --localstatedi | --localstated \ + | --localstate | --localstat | --localsta | --localst \ + | --locals | --local | --loca | --loc | --lo) + ac_prev=localstatedir ;; + -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ + | --localstate=* | --localstat=* | --localsta=* | --localst=* \ + | --locals=* | --local=* | --loca=* | --loc=* | --lo=*) + localstatedir="$ac_optarg" ;; + + -mandir | --mandir | --mandi | --mand | --man | --ma | --m) + ac_prev=mandir ;; + -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) + mandir="$ac_optarg" ;; + + -nfp | --nfp | --nf) + # Obsolete; use --without-fp. + with_fp=no ;; + + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c) + no_create=yes ;; + + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) + no_recursion=yes ;; + + -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ + | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ + | --oldin | --oldi | --old | --ol | --o) + ac_prev=oldincludedir ;; + -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ + | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ + | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) + oldincludedir="$ac_optarg" ;; + + -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) + ac_prev=prefix ;; + -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) + prefix="$ac_optarg" ;; + + -program-prefix | --program-prefix | --program-prefi | --program-pref \ + | --program-pre | --program-pr | --program-p) + ac_prev=program_prefix ;; + -program-prefix=* | --program-prefix=* | --program-prefi=* \ + | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) + program_prefix="$ac_optarg" ;; + + -program-suffix | --program-suffix | --program-suffi | --program-suff \ + | --program-suf | --program-su | --program-s) + ac_prev=program_suffix ;; + -program-suffix=* | --program-suffix=* | --program-suffi=* \ + | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) + program_suffix="$ac_optarg" ;; + + -program-transform-name | --program-transform-name \ + | --program-transform-nam | --program-transform-na \ + | --program-transform-n | --program-transform- \ + | --program-transform | --program-transfor \ + | --program-transfo | --program-transf \ + | --program-trans | --program-tran \ + | --progr-tra | --program-tr | --program-t) + ac_prev=program_transform_name ;; + -program-transform-name=* | --program-transform-name=* \ + | --program-transform-nam=* | --program-transform-na=* \ + | --program-transform-n=* | --program-transform-=* \ + | --program-transform=* | --program-transfor=* \ + | --program-transfo=* | --program-transf=* \ + | --program-trans=* | --program-tran=* \ + | --progr-tra=* | --program-tr=* | --program-t=*) + program_transform_name="$ac_optarg" ;; + + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + silent=yes ;; + + -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) + ac_prev=sbindir ;; + -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ + | --sbi=* | --sb=*) + sbindir="$ac_optarg" ;; + + -sharedstatedir | --sharedstatedir | --sharedstatedi \ + | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ + | --sharedst | --shareds | --shared | --share | --shar \ + | --sha | --sh) + ac_prev=sharedstatedir ;; + -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ + | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ + | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ + | --sha=* | --sh=*) + sharedstatedir="$ac_optarg" ;; + + -site | --site | --sit) + ac_prev=site ;; + -site=* | --site=* | --sit=*) + site="$ac_optarg" ;; + + -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) + ac_prev=srcdir ;; + -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) + srcdir="$ac_optarg" ;; + + -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ + | --syscon | --sysco | --sysc | --sys | --sy) + ac_prev=sysconfdir ;; + -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ + | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) + sysconfdir="$ac_optarg" ;; + + -target | --target | --targe | --targ | --tar | --ta | --t) + ac_prev=target ;; + -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) + target="$ac_optarg" ;; + + -v | -verbose | --verbose | --verbos | --verbo | --verb) + verbose=yes ;; + + -version | --version | --versio | --versi | --vers) + echo "configure generated by autoconf version 2.13" + exit 0 ;; + + -with-* | --with-*) + ac_package=`echo $ac_option|sed -e 's/-*with-//' -e 's/=.*//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_package| sed 's/[-_a-zA-Z0-9]//g'`"; then + { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } + fi + ac_package=`echo $ac_package| sed 's/-/_/g'` + case "$ac_option" in + *=*) ;; + *) ac_optarg=yes ;; + esac + eval "with_${ac_package}='$ac_optarg'" ;; + + -without-* | --without-*) + ac_package=`echo $ac_option|sed -e 's/-*without-//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_package| sed 's/[-a-zA-Z0-9_]//g'`"; then + { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } + fi + ac_package=`echo $ac_package| sed 's/-/_/g'` + eval "with_${ac_package}=no" ;; + + --x) + # Obsolete; use --with-x. + with_x=yes ;; + + -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ + | --x-incl | --x-inc | --x-in | --x-i) + ac_prev=x_includes ;; + -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ + | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) + x_includes="$ac_optarg" ;; + + -x-libraries | --x-libraries | --x-librarie | --x-librari \ + | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) + ac_prev=x_libraries ;; + -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ + | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) + x_libraries="$ac_optarg" ;; + + -*) { echo "configure: error: $ac_option: invalid option; use --help to show usage" 1>&2; exit 1; } + ;; + + *) + if test -n "`echo $ac_option| sed 's/[-a-z0-9.]//g'`"; then + echo "configure: warning: $ac_option: invalid host type" 1>&2 + fi + if test "x$nonopt" != xNONE; then + { echo "configure: error: can only configure for one host and one target at a time" 1>&2; exit 1; } + fi + nonopt="$ac_option" + ;; + + esac +done + +if test -n "$ac_prev"; then + { echo "configure: error: missing argument to --`echo $ac_prev | sed 's/_/-/g'`" 1>&2; exit 1; } +fi + +trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 + +# File descriptor usage: +# 0 standard input +# 1 file creation +# 2 errors and warnings +# 3 some systems may open it to /dev/tty +# 4 used on the Kubota Titan +# 6 checking for... messages and results +# 5 compiler messages saved in config.log +if test "$silent" = yes; then + exec 6>/dev/null +else + exec 6>&1 +fi +exec 5>./config.log + +echo "\ +This file contains any messages produced by compilers while +running configure, to aid debugging if configure makes a mistake. +" 1>&5 + +# Strip out --no-create and --no-recursion so they do not pile up. +# Also quote any args containing shell metacharacters. +ac_configure_args= +for ac_arg +do + case "$ac_arg" in + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c) ;; + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) ;; + *" "*|*" "*|*[\[\]\~\#\$\^\&\*\(\)\{\}\\\|\;\<\>\?]*) + ac_configure_args="$ac_configure_args '$ac_arg'" ;; + *) ac_configure_args="$ac_configure_args $ac_arg" ;; + esac +done + +# NLS nuisances. +# Only set these to C if already set. These must not be set unconditionally +# because not all systems understand e.g. LANG=C (notably SCO). +# Fixing LC_MESSAGES prevents Solaris sh from translating var values in `set'! +# Non-C LC_CTYPE values break the ctype check. +if test "${LANG+set}" = set; then LANG=C; export LANG; fi +if test "${LC_ALL+set}" = set; then LC_ALL=C; export LC_ALL; fi +if test "${LC_MESSAGES+set}" = set; then LC_MESSAGES=C; export LC_MESSAGES; fi +if test "${LC_CTYPE+set}" = set; then LC_CTYPE=C; export LC_CTYPE; fi + +# confdefs.h avoids OS command line length limits that DEFS can exceed. +rm -rf conftest* confdefs.h +# AIX cpp loses on an empty file, so make sure it contains at least a newline. +echo > confdefs.h + +# A filename unique to this package, relative to the directory that +# configure is in, which we can look for to find out if srcdir is correct. +ac_unique_file=t_pwd.h + +# Find the source files, if location was not specified. +if test -z "$srcdir"; then + ac_srcdir_defaulted=yes + # Try the directory containing this script, then its parent. + ac_prog=$0 + ac_confdir=`echo $ac_prog|sed 's%/[^/][^/]*$%%'` + test "x$ac_confdir" = "x$ac_prog" && ac_confdir=. + srcdir=$ac_confdir + if test ! -r $srcdir/$ac_unique_file; then + srcdir=.. + fi +else + ac_srcdir_defaulted=no +fi +if test ! -r $srcdir/$ac_unique_file; then + if test "$ac_srcdir_defaulted" = yes; then + { echo "configure: error: can not find sources in $ac_confdir or .." 1>&2; exit 1; } + else + { echo "configure: error: can not find sources in $srcdir" 1>&2; exit 1; } + fi +fi +srcdir=`echo "${srcdir}" | sed 's%\([^/]\)/*$%\1%'` + +# Prefer explicitly selected file to automatically selected ones. +if test -z "$CONFIG_SITE"; then + if test "x$prefix" != xNONE; then + CONFIG_SITE="$prefix/share/config.site $prefix/etc/config.site" + else + CONFIG_SITE="$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site" + fi +fi +for ac_site_file in $CONFIG_SITE; do + if test -r "$ac_site_file"; then + echo "loading site script $ac_site_file" + . "$ac_site_file" + fi +done + +if test -r "$cache_file"; then + echo "loading cache $cache_file" + . $cache_file +else + echo "creating cache $cache_file" + > $cache_file +fi + +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest${ac_exeext} $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +ac_exeext= +ac_objext=o +if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null; then + # Stardent Vistra SVR4 grep lacks -e, says ghazi@caip.rutgers.edu. + if (echo -n testing; echo 1,2,3) | sed s/-n/xn/ | grep xn >/dev/null; then + ac_n= ac_c=' +' ac_t=' ' + else + ac_n=-n ac_c= ac_t= + fi +else + ac_n= ac_c='\c' ac_t= +fi + + + + + +ac_aux_dir= +for ac_dir in $srcdir $srcdir/.. $srcdir/../..; do + if test -f $ac_dir/install-sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install-sh -c" + break + elif test -f $ac_dir/install.sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install.sh -c" + break + fi +done +if test -z "$ac_aux_dir"; then + { echo "configure: error: can not find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../.." 1>&2; exit 1; } +fi +ac_config_guess=$ac_aux_dir/config.guess +ac_config_sub=$ac_aux_dir/config.sub +ac_configure=$ac_aux_dir/configure # This should be Cygnus configure. + +# Find a good install program. We prefer a C program (faster), +# so one script is as good as another. But avoid the broken or +# incompatible versions: +# SysV /etc/install, /usr/sbin/install +# SunOS /usr/etc/install +# IRIX /sbin/install +# AIX /bin/install +# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag +# AFS /usr/afsws/bin/install, which mishandles nonexistent args +# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" +# ./install, which can be erroneously created by make from ./install.sh. +echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6 +echo "configure:559: checking for a BSD compatible install" >&5 +if test -z "$INSTALL"; then +if eval "test \"`echo '$''{'ac_cv_path_install'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS=":" + for ac_dir in $PATH; do + # Account for people who put trailing slashes in PATH elements. + case "$ac_dir/" in + /|./|.//|/etc/*|/usr/sbin/*|/usr/etc/*|/sbin/*|/usr/afsws/bin/*|/usr/ucb/*) ;; + *) + # OSF1 and SCO ODT 3.0 have their own names for install. + # Don't use installbsd from OSF since it installs stuff as root + # by default. + for ac_prog in ginstall scoinst install; do + if test -f $ac_dir/$ac_prog; then + if test $ac_prog = install && + grep dspmsg $ac_dir/$ac_prog >/dev/null 2>&1; then + # AIX install. It has an incompatible calling convention. + : + else + ac_cv_path_install="$ac_dir/$ac_prog -c" + break 2 + fi + fi + done + ;; + esac + done + IFS="$ac_save_IFS" + +fi + if test "${ac_cv_path_install+set}" = set; then + INSTALL="$ac_cv_path_install" + else + # As a last resort, use the slow shell script. We don't cache a + # path for INSTALL within a source directory, because that will + # break other packages using the cache if that directory is + # removed, or if the path is relative. + INSTALL="$ac_install_sh" + fi +fi +echo "$ac_t""$INSTALL" 1>&6 + +# Use test -z because SunOS4 sh mishandles braces in ${var-val}. +# It thinks the first close brace ends the variable substitution. +test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' + +test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL_PROGRAM}' + +test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' + +echo $ac_n "checking whether build environment is sane""... $ac_c" 1>&6 +echo "configure:612: checking whether build environment is sane" >&5 +# Just in case +sleep 1 +echo timestamp > conftestfile +# Do `set' in a subshell so we don't clobber the current shell's +# arguments. Must try -L first in case configure is actually a +# symlink; some systems play weird games with the mod time of symlinks +# (eg FreeBSD returns the mod time of the symlink's containing +# directory). +if ( + set X `ls -Lt $srcdir/configure conftestfile 2> /dev/null` + if test "$*" = "X"; then + # -L didn't work. + set X `ls -t $srcdir/configure conftestfile` + fi + if test "$*" != "X $srcdir/configure conftestfile" \ + && test "$*" != "X conftestfile $srcdir/configure"; then + + # If neither matched, then we have a broken ls. This can happen + # if, for instance, CONFIG_SHELL is bash and it inherits a + # broken ls alias from the environment. This has actually + # happened. Such a system could not be considered "sane". + { echo "configure: error: ls -t appears to fail. Make sure there is not a broken +alias in your environment" 1>&2; exit 1; } + fi + + test "$2" = conftestfile + ) +then + # Ok. + : +else + { echo "configure: error: newly created file is older than distributed files! +Check your system clock" 1>&2; exit 1; } +fi +rm -f conftest* +echo "$ac_t""yes" 1>&6 +if test "$program_transform_name" = s,x,x,; then + program_transform_name= +else + # Double any \ or $. echo might interpret backslashes. + cat <<\EOF_SED > conftestsed +s,\\,\\\\,g; s,\$,$$,g +EOF_SED + program_transform_name="`echo $program_transform_name|sed -f conftestsed`" + rm -f conftestsed +fi +test "$program_prefix" != NONE && + program_transform_name="s,^,${program_prefix},; $program_transform_name" +# Use a double $ so make ignores it. +test "$program_suffix" != NONE && + program_transform_name="s,\$\$,${program_suffix},; $program_transform_name" + +# sed with no file args requires a program. +test "$program_transform_name" = "" && program_transform_name="s,x,x," + +echo $ac_n "checking whether ${MAKE-make} sets \${MAKE}""... $ac_c" 1>&6 +echo "configure:669: checking whether ${MAKE-make} sets \${MAKE}" >&5 +set dummy ${MAKE-make}; ac_make=`echo "$2" | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_prog_make_${ac_make}_set'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftestmake <<\EOF +all: + @echo 'ac_maketemp="${MAKE}"' +EOF +# GNU make sometimes prints "make[1]: Entering...", which would confuse us. +eval `${MAKE-make} -f conftestmake 2>/dev/null | grep temp=` +if test -n "$ac_maketemp"; then + eval ac_cv_prog_make_${ac_make}_set=yes +else + eval ac_cv_prog_make_${ac_make}_set=no +fi +rm -f conftestmake +fi +if eval "test \"`echo '$ac_cv_prog_make_'${ac_make}_set`\" = yes"; then + echo "$ac_t""yes" 1>&6 + SET_MAKE= +else + echo "$ac_t""no" 1>&6 + SET_MAKE="MAKE=${MAKE-make}" +fi + + + +PACKAGE=libtinysrp + +VERSION=0.7.5 + +if test "`cd $srcdir && pwd`" != "`pwd`" && test -f $srcdir/config.status; then + { echo "configure: error: source directory already configured; run "make distclean" there first" 1>&2; exit 1; } +fi +cat >> confdefs.h <<EOF +#define PACKAGE "$PACKAGE" +EOF + +cat >> confdefs.h <<EOF +#define VERSION "$VERSION" +EOF + + + +missing_dir=`cd $ac_aux_dir && pwd` +echo $ac_n "checking for working aclocal""... $ac_c" 1>&6 +echo "configure:716: checking for working aclocal" >&5 +# Run test in a subshell; some versions of sh will print an error if +# an executable is not found, even if stderr is redirected. +# Redirect stdin to placate older versions of autoconf. Sigh. +if (aclocal --version) < /dev/null > /dev/null 2>&1; then + ACLOCAL=aclocal + echo "$ac_t""found" 1>&6 +else + ACLOCAL="$missing_dir/missing aclocal" + echo "$ac_t""missing" 1>&6 +fi + +echo $ac_n "checking for working autoconf""... $ac_c" 1>&6 +echo "configure:729: checking for working autoconf" >&5 +# Run test in a subshell; some versions of sh will print an error if +# an executable is not found, even if stderr is redirected. +# Redirect stdin to placate older versions of autoconf. Sigh. +if (autoconf --version) < /dev/null > /dev/null 2>&1; then + AUTOCONF=autoconf + echo "$ac_t""found" 1>&6 +else + AUTOCONF="$missing_dir/missing autoconf" + echo "$ac_t""missing" 1>&6 +fi + +echo $ac_n "checking for working automake""... $ac_c" 1>&6 +echo "configure:742: checking for working automake" >&5 +# Run test in a subshell; some versions of sh will print an error if +# an executable is not found, even if stderr is redirected. +# Redirect stdin to placate older versions of autoconf. Sigh. +if (automake --version) < /dev/null > /dev/null 2>&1; then + AUTOMAKE=automake + echo "$ac_t""found" 1>&6 +else + AUTOMAKE="$missing_dir/missing automake" + echo "$ac_t""missing" 1>&6 +fi + +echo $ac_n "checking for working autoheader""... $ac_c" 1>&6 +echo "configure:755: checking for working autoheader" >&5 +# Run test in a subshell; some versions of sh will print an error if +# an executable is not found, even if stderr is redirected. +# Redirect stdin to placate older versions of autoconf. Sigh. +if (autoheader --version) < /dev/null > /dev/null 2>&1; then + AUTOHEADER=autoheader + echo "$ac_t""found" 1>&6 +else + AUTOHEADER="$missing_dir/missing autoheader" + echo "$ac_t""missing" 1>&6 +fi + +echo $ac_n "checking for working makeinfo""... $ac_c" 1>&6 +echo "configure:768: checking for working makeinfo" >&5 +# Run test in a subshell; some versions of sh will print an error if +# an executable is not found, even if stderr is redirected. +# Redirect stdin to placate older versions of autoconf. Sigh. +if (makeinfo --version) < /dev/null > /dev/null 2>&1; then + MAKEINFO=makeinfo + echo "$ac_t""found" 1>&6 +else + MAKEINFO="$missing_dir/missing makeinfo" + echo "$ac_t""missing" 1>&6 +fi + + + +test "$CFLAGS" = "" && CFLAGS="-O2" + + +# Extract the first word of "gcc", so it can be a program name with args. +set dummy gcc; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:788: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" + ac_dummy="$PATH" + for ac_dir in $ac_dummy; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_CC="gcc" + break + fi + done + IFS="$ac_save_ifs" +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +if test -z "$CC"; then + # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:818: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" + ac_prog_rejected=no + ac_dummy="$PATH" + for ac_dir in $ac_dummy; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + if test "$ac_dir/$ac_word" = "/usr/ucb/cc"; then + ac_prog_rejected=yes + continue + fi + ac_cv_prog_CC="cc" + break + fi + done + IFS="$ac_save_ifs" +if test $ac_prog_rejected = yes; then + # We found a bogon in the path, so make sure we never use it. + set dummy $ac_cv_prog_CC + shift + if test $# -gt 0; then + # We chose a different compiler from the bogus one. + # However, it has the same basename, so the bogon will be chosen + # first if we set CC to just the basename; use the full file name. + shift + set dummy "$ac_dir/$ac_word" "$@" + shift + ac_cv_prog_CC="$@" + fi +fi +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + + if test -z "$CC"; then + case "`uname -s`" in + *win32* | *WIN32*) + # Extract the first word of "cl", so it can be a program name with args. +set dummy cl; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:869: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" + ac_dummy="$PATH" + for ac_dir in $ac_dummy; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_CC="cl" + break + fi + done + IFS="$ac_save_ifs" +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + ;; + esac + fi + test -z "$CC" && { echo "configure: error: no acceptable cc found in \$PATH" 1>&2; exit 1; } +fi + +echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 +echo "configure:901: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 + +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest${ac_exeext} $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +cat > conftest.$ac_ext << EOF + +#line 912 "configure" +#include "confdefs.h" + +main(){return(0);} +EOF +if { (eval echo configure:917: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + ac_cv_prog_cc_works=yes + # If we can't run a trivial program, we are probably using a cross compiler. + if (./conftest; exit) 2>/dev/null; then + ac_cv_prog_cc_cross=no + else + ac_cv_prog_cc_cross=yes + fi +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + ac_cv_prog_cc_works=no +fi +rm -fr conftest* +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest${ac_exeext} $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +echo "$ac_t""$ac_cv_prog_cc_works" 1>&6 +if test $ac_cv_prog_cc_works = no; then + { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } +fi +echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 +echo "configure:943: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 +cross_compiling=$ac_cv_prog_cc_cross + +echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 +echo "configure:948: checking whether we are using GNU C" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_gcc'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.c <<EOF +#ifdef __GNUC__ + yes; +#endif +EOF +if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:957: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then + ac_cv_prog_gcc=yes +else + ac_cv_prog_gcc=no +fi +fi + +echo "$ac_t""$ac_cv_prog_gcc" 1>&6 + +if test $ac_cv_prog_gcc = yes; then + GCC=yes +else + GCC= +fi + +ac_test_CFLAGS="${CFLAGS+set}" +ac_save_CFLAGS="$CFLAGS" +CFLAGS= +echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 +echo "configure:976: checking whether ${CC-cc} accepts -g" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_cc_g'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + echo 'void f(){}' > conftest.c +if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then + ac_cv_prog_cc_g=yes +else + ac_cv_prog_cc_g=no +fi +rm -f conftest* + +fi + +echo "$ac_t""$ac_cv_prog_cc_g" 1>&6 +if test "$ac_test_CFLAGS" = set; then + CFLAGS="$ac_save_CFLAGS" +elif test $ac_cv_prog_cc_g = yes; then + if test "$GCC" = yes; then + CFLAGS="-g -O2" + else + CFLAGS="-g" + fi +else + if test "$GCC" = yes; then + CFLAGS="-O2" + else + CFLAGS= + fi +fi + +# Find a good install program. We prefer a C program (faster), +# so one script is as good as another. But avoid the broken or +# incompatible versions: +# SysV /etc/install, /usr/sbin/install +# SunOS /usr/etc/install +# IRIX /sbin/install +# AIX /bin/install +# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag +# AFS /usr/afsws/bin/install, which mishandles nonexistent args +# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" +# ./install, which can be erroneously created by make from ./install.sh. +echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6 +echo "configure:1019: checking for a BSD compatible install" >&5 +if test -z "$INSTALL"; then +if eval "test \"`echo '$''{'ac_cv_path_install'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + IFS="${IFS= }"; ac_save_IFS="$IFS"; IFS=":" + for ac_dir in $PATH; do + # Account for people who put trailing slashes in PATH elements. + case "$ac_dir/" in + /|./|.//|/etc/*|/usr/sbin/*|/usr/etc/*|/sbin/*|/usr/afsws/bin/*|/usr/ucb/*) ;; + *) + # OSF1 and SCO ODT 3.0 have their own names for install. + # Don't use installbsd from OSF since it installs stuff as root + # by default. + for ac_prog in ginstall scoinst install; do + if test -f $ac_dir/$ac_prog; then + if test $ac_prog = install && + grep dspmsg $ac_dir/$ac_prog >/dev/null 2>&1; then + # AIX install. It has an incompatible calling convention. + : + else + ac_cv_path_install="$ac_dir/$ac_prog -c" + break 2 + fi + fi + done + ;; + esac + done + IFS="$ac_save_IFS" + +fi + if test "${ac_cv_path_install+set}" = set; then + INSTALL="$ac_cv_path_install" + else + # As a last resort, use the slow shell script. We don't cache a + # path for INSTALL within a source directory, because that will + # break other packages using the cache if that directory is + # removed, or if the path is relative. + INSTALL="$ac_install_sh" + fi +fi +echo "$ac_t""$INSTALL" 1>&6 + +# Use test -z because SunOS4 sh mishandles braces in ${var-val}. +# It thinks the first close brace ends the variable substitution. +test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' + +test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL_PROGRAM}' + +test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' + +echo $ac_n "checking whether ln -s works""... $ac_c" 1>&6 +echo "configure:1072: checking whether ln -s works" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_LN_S'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + rm -f conftestdata +if ln -s X conftestdata 2>/dev/null +then + rm -f conftestdata + ac_cv_prog_LN_S="ln -s" +else + ac_cv_prog_LN_S=ln +fi +fi +LN_S="$ac_cv_prog_LN_S" +if test "$ac_cv_prog_LN_S" = "ln -s"; then + echo "$ac_t""yes" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +# Extract the first word of "ranlib", so it can be a program name with args. +set dummy ranlib; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1095: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_RANLIB'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$RANLIB"; then + ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS=":" + ac_dummy="$PATH" + for ac_dir in $ac_dummy; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_RANLIB="ranlib" + break + fi + done + IFS="$ac_save_ifs" + test -z "$ac_cv_prog_RANLIB" && ac_cv_prog_RANLIB=":" +fi +fi +RANLIB="$ac_cv_prog_RANLIB" +if test -n "$RANLIB"; then + echo "$ac_t""$RANLIB" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +if test "$program_transform_name" = s,x,x,; then + program_transform_name= +else + # Double any \ or $. echo might interpret backslashes. + cat <<\EOF_SED > conftestsed +s,\\,\\\\,g; s,\$,$$,g +EOF_SED + program_transform_name="`echo $program_transform_name|sed -f conftestsed`" + rm -f conftestsed +fi +test "$program_prefix" != NONE && + program_transform_name="s,^,${program_prefix},; $program_transform_name" +# Use a double $ so make ignores it. +test "$program_suffix" != NONE && + program_transform_name="s,\$\$,${program_suffix},; $program_transform_name" + +# sed with no file args requires a program. +test "$program_transform_name" = "" && program_transform_name="s,x,x," + + + +echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6 +echo "configure:1144: checking how to run the C preprocessor" >&5 +# On Suns, sometimes $CPP names a directory. +if test -n "$CPP" && test -d "$CPP"; then + CPP= +fi +if test -z "$CPP"; then +if eval "test \"`echo '$''{'ac_cv_prog_CPP'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + # This must be in double quotes, not single quotes, because CPP may get + # substituted into the Makefile and "${CC-cc}" will confuse make. + CPP="${CC-cc} -E" + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. + cat > conftest.$ac_ext <<EOF +#line 1159 "configure" +#include "confdefs.h" +#include <assert.h> +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1165: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP="${CC-cc} -E -traditional-cpp" + cat > conftest.$ac_ext <<EOF +#line 1176 "configure" +#include "confdefs.h" +#include <assert.h> +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1182: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP="${CC-cc} -nologo -E" + cat > conftest.$ac_ext <<EOF +#line 1193 "configure" +#include "confdefs.h" +#include <assert.h> +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1199: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP=/lib/cpp +fi +rm -f conftest* +fi +rm -f conftest* +fi +rm -f conftest* + ac_cv_prog_CPP="$CPP" +fi + CPP="$ac_cv_prog_CPP" +else + ac_cv_prog_CPP="$CPP" +fi +echo "$ac_t""$CPP" 1>&6 + +echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 +echo "configure:1224: checking for ANSI C header files" >&5 +if eval "test \"`echo '$''{'ac_cv_header_stdc'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1229 "configure" +#include "confdefs.h" +#include <stdlib.h> +#include <stdarg.h> +#include <string.h> +#include <float.h> +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1237: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + rm -rf conftest* + ac_cv_header_stdc=yes +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +if test $ac_cv_header_stdc = yes; then + # SunOS 4.x string.h does not declare mem*, contrary to ANSI. +cat > conftest.$ac_ext <<EOF +#line 1254 "configure" +#include "confdefs.h" +#include <string.h> +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "memchr" >/dev/null 2>&1; then + : +else + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. +cat > conftest.$ac_ext <<EOF +#line 1272 "configure" +#include "confdefs.h" +#include <stdlib.h> +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "free" >/dev/null 2>&1; then + : +else + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. +if test "$cross_compiling" = yes; then + : +else + cat > conftest.$ac_ext <<EOF +#line 1293 "configure" +#include "confdefs.h" +#include <ctype.h> +#define ISLOWER(c) ('a' <= (c) && (c) <= 'z') +#define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) +#define XOR(e, f) (((e) && !(f)) || (!(e) && (f))) +int main () { int i; for (i = 0; i < 256; i++) +if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) exit(2); +exit (0); } + +EOF +if { (eval echo configure:1304: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + : +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_header_stdc=no +fi +rm -fr conftest* +fi + +fi +fi + +echo "$ac_t""$ac_cv_header_stdc" 1>&6 +if test $ac_cv_header_stdc = yes; then + cat >> confdefs.h <<\EOF +#define STDC_HEADERS 1 +EOF + +fi + +for ac_hdr in sgtty.h sys/ioctl.h sys/time.h termio.h termios.h unistd.h +do +ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 +echo "configure:1331: checking for $ac_hdr" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1336 "configure" +#include "confdefs.h" +#include <$ac_hdr> +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1341: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` + cat >> confdefs.h <<EOF +#define $ac_tr_hdr 1 +EOF + +else + echo "$ac_t""no" 1>&6 +fi +done + + + +echo $ac_n "checking for working const""... $ac_c" 1>&6 +echo "configure:1370: checking for working const" >&5 +if eval "test \"`echo '$''{'ac_cv_c_const'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1375 "configure" +#include "confdefs.h" + +int main() { + +/* Ultrix mips cc rejects this. */ +typedef int charset[2]; const charset x; +/* SunOS 4.1.1 cc rejects this. */ +char const *const *ccp; +char **p; +/* NEC SVR4.0.2 mips cc rejects this. */ +struct point {int x, y;}; +static struct point const zero = {0,0}; +/* AIX XL C 1.02.0.0 rejects this. + It does not let you subtract one const X* pointer from another in an arm + of an if-expression whose if-part is not a constant expression */ +const char *g = "string"; +ccp = &g + (g ? g-g : 0); +/* HPUX 7.0 cc rejects these. */ +++ccp; +p = (char**) ccp; +ccp = (char const *const *) p; +{ /* SCO 3.2v4 cc rejects this. */ + char *t; + char const *s = 0 ? (char *) 0 : (char const *) 0; + + *t++ = 0; +} +{ /* Someone thinks the Sun supposedly-ANSI compiler will reject this. */ + int x[] = {25, 17}; + const int *foo = &x[0]; + ++foo; +} +{ /* Sun SC1.0 ANSI compiler rejects this -- but not the above. */ + typedef const int *iptr; + iptr p = 0; + ++p; +} +{ /* AIX XL C 1.02.0.0 rejects this saying + "k.c", line 2.27: 1506-025 (S) Operand must be a modifiable lvalue. */ + struct s { int j; const int *ap[3]; }; + struct s *b; b->j = 5; +} +{ /* ULTRIX-32 V3.1 (Rev 9) vcc rejects this */ + const int foo = 10; +} + +; return 0; } +EOF +if { (eval echo configure:1424: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_c_const=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_c_const=no +fi +rm -f conftest* +fi + +echo "$ac_t""$ac_cv_c_const" 1>&6 +if test $ac_cv_c_const = no; then + cat >> confdefs.h <<\EOF +#define const +EOF + +fi + +echo $ac_n "checking for inline""... $ac_c" 1>&6 +echo "configure:1445: checking for inline" >&5 +if eval "test \"`echo '$''{'ac_cv_c_inline'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_cv_c_inline=no +for ac_kw in inline __inline__ __inline; do + cat > conftest.$ac_ext <<EOF +#line 1452 "configure" +#include "confdefs.h" + +int main() { +} $ac_kw foo() { +; return 0; } +EOF +if { (eval echo configure:1459: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_c_inline=$ac_kw; break +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 +fi +rm -f conftest* +done + +fi + +echo "$ac_t""$ac_cv_c_inline" 1>&6 +case "$ac_cv_c_inline" in + inline | yes) ;; + no) cat >> confdefs.h <<\EOF +#define inline +EOF + ;; + *) cat >> confdefs.h <<EOF +#define inline $ac_cv_c_inline +EOF + ;; +esac + +echo $ac_n "checking whether time.h and sys/time.h may both be included""... $ac_c" 1>&6 +echo "configure:1485: checking whether time.h and sys/time.h may both be included" >&5 +if eval "test \"`echo '$''{'ac_cv_header_time'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1490 "configure" +#include "confdefs.h" +#include <sys/types.h> +#include <sys/time.h> +#include <time.h> +int main() { +struct tm *tp; +; return 0; } +EOF +if { (eval echo configure:1499: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_header_time=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_header_time=no +fi +rm -f conftest* +fi + +echo "$ac_t""$ac_cv_header_time" 1>&6 +if test $ac_cv_header_time = yes; then + cat >> confdefs.h <<\EOF +#define TIME_WITH_SYS_TIME 1 +EOF + +fi + +echo $ac_n "checking whether byte ordering is bigendian""... $ac_c" 1>&6 +echo "configure:1520: checking whether byte ordering is bigendian" >&5 +if eval "test \"`echo '$''{'ac_cv_c_bigendian'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_cv_c_bigendian=unknown +# See if sys/param.h defines the BYTE_ORDER macro. +cat > conftest.$ac_ext <<EOF +#line 1527 "configure" +#include "confdefs.h" +#include <sys/types.h> +#include <sys/param.h> +int main() { + +#if !BYTE_ORDER || !BIG_ENDIAN || !LITTLE_ENDIAN + bogus endian macros +#endif +; return 0; } +EOF +if { (eval echo configure:1538: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + # It does; now see whether it defined to BIG_ENDIAN or not. +cat > conftest.$ac_ext <<EOF +#line 1542 "configure" +#include "confdefs.h" +#include <sys/types.h> +#include <sys/param.h> +int main() { + +#if BYTE_ORDER != BIG_ENDIAN + not big endian +#endif +; return 0; } +EOF +if { (eval echo configure:1553: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_c_bigendian=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_c_bigendian=no +fi +rm -f conftest* +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 +fi +rm -f conftest* +if test $ac_cv_c_bigendian = unknown; then +if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext <<EOF +#line 1573 "configure" +#include "confdefs.h" +main () { + /* Are we little or big endian? From Harbison&Steele. */ + union + { + long l; + char c[sizeof (long)]; + } u; + u.l = 1; + exit (u.c[sizeof (long) - 1] == 1); +} +EOF +if { (eval echo configure:1586: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + ac_cv_c_bigendian=no +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_c_bigendian=yes +fi +rm -fr conftest* +fi + +fi +fi + +echo "$ac_t""$ac_cv_c_bigendian" 1>&6 +if test $ac_cv_c_bigendian = yes; then + cat >> confdefs.h <<\EOF +#define WORDS_BIGENDIAN 1 +EOF + +fi + +echo $ac_n "checking size of short""... $ac_c" 1>&6 +echo "configure:1610: checking size of short" >&5 +if eval "test \"`echo '$''{'ac_cv_sizeof_short'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext <<EOF +#line 1618 "configure" +#include "confdefs.h" +#include <stdio.h> +main() +{ + FILE *f=fopen("conftestval", "w"); + if (!f) exit(1); + fprintf(f, "%d\n", sizeof(short)); + exit(0); +} +EOF +if { (eval echo configure:1629: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + ac_cv_sizeof_short=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sizeof_short=0 +fi +rm -fr conftest* +fi + +fi +echo "$ac_t""$ac_cv_sizeof_short" 1>&6 +cat >> confdefs.h <<EOF +#define SIZEOF_SHORT $ac_cv_sizeof_short +EOF + + +echo $ac_n "checking size of int""... $ac_c" 1>&6 +echo "configure:1649: checking size of int" >&5 +if eval "test \"`echo '$''{'ac_cv_sizeof_int'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext <<EOF +#line 1657 "configure" +#include "confdefs.h" +#include <stdio.h> +main() +{ + FILE *f=fopen("conftestval", "w"); + if (!f) exit(1); + fprintf(f, "%d\n", sizeof(int)); + exit(0); +} +EOF +if { (eval echo configure:1668: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + ac_cv_sizeof_int=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sizeof_int=0 +fi +rm -fr conftest* +fi + +fi +echo "$ac_t""$ac_cv_sizeof_int" 1>&6 +cat >> confdefs.h <<EOF +#define SIZEOF_INT $ac_cv_sizeof_int +EOF + + +echo $ac_n "checking size of long""... $ac_c" 1>&6 +echo "configure:1688: checking size of long" >&5 +if eval "test \"`echo '$''{'ac_cv_sizeof_long'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext <<EOF +#line 1696 "configure" +#include "confdefs.h" +#include <stdio.h> +main() +{ + FILE *f=fopen("conftestval", "w"); + if (!f) exit(1); + fprintf(f, "%d\n", sizeof(long)); + exit(0); +} +EOF +if { (eval echo configure:1707: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + ac_cv_sizeof_long=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sizeof_long=0 +fi +rm -fr conftest* +fi + +fi +echo "$ac_t""$ac_cv_sizeof_long" 1>&6 +cat >> confdefs.h <<EOF +#define SIZEOF_LONG $ac_cv_sizeof_long +EOF + + +echo $ac_n "checking size of long long""... $ac_c" 1>&6 +echo "configure:1727: checking size of long long" >&5 +if eval "test \"`echo '$''{'ac_cv_sizeof_long_long'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext <<EOF +#line 1735 "configure" +#include "confdefs.h" +#include <stdio.h> +main() +{ + FILE *f=fopen("conftestval", "w"); + if (!f) exit(1); + fprintf(f, "%d\n", sizeof(long long)); + exit(0); +} +EOF +if { (eval echo configure:1746: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + ac_cv_sizeof_long_long=`cat conftestval` +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_sizeof_long_long=0 +fi +rm -fr conftest* +fi + +fi +echo "$ac_t""$ac_cv_sizeof_long_long" 1>&6 +cat >> confdefs.h <<EOF +#define SIZEOF_LONG_LONG $ac_cv_sizeof_long_long +EOF + + +cat > conftest.$ac_ext <<EOF +#line 1766 "configure" +#include "confdefs.h" + +int main() { +volatile int i; +; return 0; } +EOF +if { (eval echo configure:1773: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + : +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + cat >> confdefs.h <<\EOF +#define volatile +EOF + +fi +rm -f conftest* +echo $ac_n "checking whether char is unsigned""... $ac_c" 1>&6 +echo "configure:1786: checking whether char is unsigned" >&5 +if eval "test \"`echo '$''{'ac_cv_c_char_unsigned'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test "$GCC" = yes; then + # GCC predefines this symbol on systems where it applies. +cat > conftest.$ac_ext <<EOF +#line 1793 "configure" +#include "confdefs.h" +#ifdef __CHAR_UNSIGNED__ + yes +#endif + +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "yes" >/dev/null 2>&1; then + rm -rf conftest* + ac_cv_c_char_unsigned=yes +else + rm -rf conftest* + ac_cv_c_char_unsigned=no +fi +rm -f conftest* + +else +if test "$cross_compiling" = yes; then + { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } +else + cat > conftest.$ac_ext <<EOF +#line 1815 "configure" +#include "confdefs.h" +/* volatile prevents gcc2 from optimizing the test away on sparcs. */ +#if !defined(__STDC__) || __STDC__ != 1 +#define volatile +#endif +main() { + volatile char c = 255; exit(c < 0); +} +EOF +if { (eval echo configure:1825: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +then + ac_cv_c_char_unsigned=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_c_char_unsigned=no +fi +rm -fr conftest* +fi + +fi +fi + +echo "$ac_t""$ac_cv_c_char_unsigned" 1>&6 +if test $ac_cv_c_char_unsigned = yes && test "$GCC" != yes; then + cat >> confdefs.h <<\EOF +#define __CHAR_UNSIGNED__ 1 +EOF + +fi + + +if test "$ac_cv_c_char_unsigned" = "yes"; then + signed=-signed +fi + + +for ac_func in sigaction strchr memcpy +do +echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 +echo "configure:1857: checking for $ac_func" >&5 +if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1862 "configure" +#include "confdefs.h" +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func(); below. */ +#include <assert.h> +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +$ac_func(); +#endif + +; return 0; } +EOF +if { (eval echo configure:1885: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_func_$ac_func=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_$ac_func=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'$ac_func`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_func=HAVE_`echo $ac_func | tr 'abcdefghijklmnopqrstuvwxyz' 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'` + cat >> confdefs.h <<EOF +#define $ac_tr_func 1 +EOF + +else + echo "$ac_t""no" 1>&6 +fi +done + + +echo $ac_n "checking POSIX signal handlers""... $ac_c" 1>&6 +echo "configure:1911: checking POSIX signal handlers" >&5 +if eval "test \"`echo '$''{'ac_cv_has_posix_signals'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1916 "configure" +#include "confdefs.h" +#include <sys/types.h> +#include <signal.h> +#ifdef signal +#undef signal +#endif +extern void (*signal ()) (); +int main() { + +; return 0; } +EOF +if { (eval echo configure:1928: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then + rm -rf conftest* + ac_cv_has_posix_signals=yes +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_has_posix_signals=no +fi +rm -f conftest* +fi + +echo "$ac_t""$ac_cv_has_posix_signals" 1>&6 +if test $ac_cv_has_posix_signals = yes; then + cat >> confdefs.h <<\EOF +#define RETSIGTYPE void +EOF + cat >> confdefs.h <<\EOF +#define POSIX_SIGTYPE 1 +EOF + +else + if test $ac_cv_type_signal = void; then + cat >> confdefs.h <<\EOF +#define RETSIGTYPE void +EOF + + else + cat >> confdefs.h <<\EOF +#define RETSIGTYPE int +EOF + + fi +fi +ac_safe=`echo "termios.h" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for termios.h""... $ac_c" 1>&6 +echo "configure:1964: checking for termios.h" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1969 "configure" +#include "confdefs.h" +#include <termios.h> +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1974: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + echo $ac_n "checking for cfsetispeed""... $ac_c" 1>&6 +echo "configure:1991: checking for cfsetispeed" >&5 +if eval "test \"`echo '$''{'ac_cv_func_cfsetispeed'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext <<EOF +#line 1996 "configure" +#include "confdefs.h" +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char cfsetispeed(); below. */ +#include <assert.h> +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char cfsetispeed(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_cfsetispeed) || defined (__stub___cfsetispeed) +choke me +#else +cfsetispeed(); +#endif + +; return 0; } +EOF +if { (eval echo configure:2019: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_func_cfsetispeed=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_cfsetispeed=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'cfsetispeed`\" = yes"; then + echo "$ac_t""yes" 1>&6 + cat >> confdefs.h <<\EOF +#define POSIX_TERMIOS 1 +EOF + +else + echo "$ac_t""no" 1>&6 +fi + +else + echo "$ac_t""no" 1>&6 +fi + + + + +cat >> confdefs.h <<\EOF +#define SHA1HANDSOFF 1 +EOF + + +trap '' 1 2 15 +cat > confcache <<\EOF +# This file is a shell script that caches the results of configure +# tests run on this system so they can be shared between configure +# scripts and configure runs. It is not useful on other systems. +# If it contains results you don't want to keep, you may remove or edit it. +# +# By default, configure uses ./config.cache as the cache file, +# creating it if it does not exist already. You can give configure +# the --cache-file=FILE option to use a different cache file; that is +# what configure does when it calls configure scripts in +# subdirectories, so they share the cache. +# Giving --cache-file=/dev/null disables caching, for debugging configure. +# config.status only pays attention to the cache file if you give it the +# --recheck option to rerun configure. +# +EOF +# The following way of writing the cache mishandles newlines in values, +# but we know of no workaround that is simple, portable, and efficient. +# So, don't put newlines in cache variables' values. +# Ultrix sh set writes to stderr and can't be redirected directly, +# and sets the high bit in the cache file unless we assign to the vars. +(set) 2>&1 | + case `(ac_space=' '; set | grep ac_space) 2>&1` in + *ac_space=\ *) + # `set' does not quote correctly, so add quotes (double-quote substitution + # turns \\\\ into \\, and sed turns \\ into \). + sed -n \ + -e "s/'/'\\\\''/g" \ + -e "s/^\\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\\)=\\(.*\\)/\\1=\${\\1='\\2'}/p" + ;; + *) + # `set' quotes correctly as required by POSIX, so do not add quotes. + sed -n -e 's/^\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\)=\(.*\)/\1=${\1=\2}/p' + ;; + esac >> confcache +if cmp -s $cache_file confcache; then + : +else + if test -w $cache_file; then + echo "updating cache $cache_file" + cat confcache > $cache_file + else + echo "not updating unwritable cache $cache_file" + fi +fi +rm -f confcache + +trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 + +test "x$prefix" = xNONE && prefix=$ac_default_prefix +# Let make expand exec_prefix. +test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' + +# Any assignment to VPATH causes Sun make to only execute +# the first set of double-colon rules, so remove it if not needed. +# If there is a colon in the path, we need to keep it. +if test "x$srcdir" = x.; then + ac_vpsub='/^[ ]*VPATH[ ]*=[^:]*$/d' +fi + +trap 'rm -f $CONFIG_STATUS conftest*; exit 1' 1 2 15 + +DEFS=-DHAVE_CONFIG_H + +# Without the "./", some shells look in PATH for config.status. +: ${CONFIG_STATUS=./config.status} + +echo creating $CONFIG_STATUS +rm -f $CONFIG_STATUS +cat > $CONFIG_STATUS <<EOF +#! /bin/sh +# Generated automatically by configure. +# Run this file to recreate the current configuration. +# This directory was configured as follows, +# on host `(hostname || uname -n) 2>/dev/null | sed 1q`: +# +# $0 $ac_configure_args +# +# Compiler output produced by configure, useful for debugging +# configure, is in ./config.log if it exists. + +ac_cs_usage="Usage: $CONFIG_STATUS [--recheck] [--version] [--help]" +for ac_option +do + case "\$ac_option" in + -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) + echo "running \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion" + exec \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion ;; + -version | --version | --versio | --versi | --vers | --ver | --ve | --v) + echo "$CONFIG_STATUS generated by autoconf version 2.13" + exit 0 ;; + -help | --help | --hel | --he | --h) + echo "\$ac_cs_usage"; exit 0 ;; + *) echo "\$ac_cs_usage"; exit 1 ;; + esac +done + +ac_given_srcdir=$srcdir +ac_given_INSTALL="$INSTALL" + +trap 'rm -fr `echo "Makefile config.h" | sed "s/:[^ ]*//g"` conftest*; exit 1' 1 2 15 +EOF +cat >> $CONFIG_STATUS <<EOF + +# Protect against being on the right side of a sed subst in config.status. +sed 's/%@/@@/; s/@%/@@/; s/%g\$/@g/; /@g\$/s/[\\\\&%]/\\\\&/g; + s/@@/%@/; s/@@/@%/; s/@g\$/%g/' > conftest.subs <<\\CEOF +$ac_vpsub +$extrasub +s%@SHELL@%$SHELL%g +s%@CFLAGS@%$CFLAGS%g +s%@CPPFLAGS@%$CPPFLAGS%g +s%@CXXFLAGS@%$CXXFLAGS%g +s%@FFLAGS@%$FFLAGS%g +s%@DEFS@%$DEFS%g +s%@LDFLAGS@%$LDFLAGS%g +s%@LIBS@%$LIBS%g +s%@exec_prefix@%$exec_prefix%g +s%@prefix@%$prefix%g +s%@program_transform_name@%$program_transform_name%g +s%@bindir@%$bindir%g +s%@sbindir@%$sbindir%g +s%@libexecdir@%$libexecdir%g +s%@datadir@%$datadir%g +s%@sysconfdir@%$sysconfdir%g +s%@sharedstatedir@%$sharedstatedir%g +s%@localstatedir@%$localstatedir%g +s%@libdir@%$libdir%g +s%@includedir@%$includedir%g +s%@oldincludedir@%$oldincludedir%g +s%@infodir@%$infodir%g +s%@mandir@%$mandir%g +s%@INSTALL_PROGRAM@%$INSTALL_PROGRAM%g +s%@INSTALL_SCRIPT@%$INSTALL_SCRIPT%g +s%@INSTALL_DATA@%$INSTALL_DATA%g +s%@PACKAGE@%$PACKAGE%g +s%@VERSION@%$VERSION%g +s%@ACLOCAL@%$ACLOCAL%g +s%@AUTOCONF@%$AUTOCONF%g +s%@AUTOMAKE@%$AUTOMAKE%g +s%@AUTOHEADER@%$AUTOHEADER%g +s%@MAKEINFO@%$MAKEINFO%g +s%@SET_MAKE@%$SET_MAKE%g +s%@CC@%$CC%g +s%@LN_S@%$LN_S%g +s%@RANLIB@%$RANLIB%g +s%@CPP@%$CPP%g +s%@signed@%$signed%g + +CEOF +EOF + +cat >> $CONFIG_STATUS <<\EOF + +# Split the substitutions into bite-sized pieces for seds with +# small command number limits, like on Digital OSF/1 and HP-UX. +ac_max_sed_cmds=90 # Maximum number of lines to put in a sed script. +ac_file=1 # Number of current file. +ac_beg=1 # First line for current file. +ac_end=$ac_max_sed_cmds # Line after last line for current file. +ac_more_lines=: +ac_sed_cmds="" +while $ac_more_lines; do + if test $ac_beg -gt 1; then + sed "1,${ac_beg}d; ${ac_end}q" conftest.subs > conftest.s$ac_file + else + sed "${ac_end}q" conftest.subs > conftest.s$ac_file + fi + if test ! -s conftest.s$ac_file; then + ac_more_lines=false + rm -f conftest.s$ac_file + else + if test -z "$ac_sed_cmds"; then + ac_sed_cmds="sed -f conftest.s$ac_file" + else + ac_sed_cmds="$ac_sed_cmds | sed -f conftest.s$ac_file" + fi + ac_file=`expr $ac_file + 1` + ac_beg=$ac_end + ac_end=`expr $ac_end + $ac_max_sed_cmds` + fi +done +if test -z "$ac_sed_cmds"; then + ac_sed_cmds=cat +fi +EOF + +cat >> $CONFIG_STATUS <<EOF + +CONFIG_FILES=\${CONFIG_FILES-"Makefile"} +EOF +cat >> $CONFIG_STATUS <<\EOF +for ac_file in .. $CONFIG_FILES; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + # Adjust a relative srcdir, top_srcdir, and INSTALL for subdirectories. + + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + ac_dir_suffix="/`echo $ac_dir|sed 's%^\./%%'`" + # A "../" for each directory in $ac_dir_suffix. + ac_dots=`echo $ac_dir_suffix|sed 's%/[^/]*%../%g'` + else + ac_dir_suffix= ac_dots= + fi + + case "$ac_given_srcdir" in + .) srcdir=. + if test -z "$ac_dots"; then top_srcdir=. + else top_srcdir=`echo $ac_dots|sed 's%/$%%'`; fi ;; + /*) srcdir="$ac_given_srcdir$ac_dir_suffix"; top_srcdir="$ac_given_srcdir" ;; + *) # Relative path. + srcdir="$ac_dots$ac_given_srcdir$ac_dir_suffix" + top_srcdir="$ac_dots$ac_given_srcdir" ;; + esac + + case "$ac_given_INSTALL" in + [/$]*) INSTALL="$ac_given_INSTALL" ;; + *) INSTALL="$ac_dots$ac_given_INSTALL" ;; + esac + + echo creating "$ac_file" + rm -f "$ac_file" + configure_input="Generated automatically from `echo $ac_file_in|sed 's%.*/%%'` by configure." + case "$ac_file" in + *Makefile*) ac_comsub="1i\\ +# $configure_input" ;; + *) ac_comsub= ;; + esac + + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + sed -e "$ac_comsub +s%@configure_input@%$configure_input%g +s%@srcdir@%$srcdir%g +s%@top_srcdir@%$top_srcdir%g +s%@INSTALL@%$INSTALL%g +" $ac_file_inputs | (eval "$ac_sed_cmds") > $ac_file +fi; done +rm -f conftest.s* + +# These sed commands are passed to sed as "A NAME B NAME C VALUE D", where +# NAME is the cpp macro being defined and VALUE is the value it is being given. +# +# ac_d sets the value in "#define NAME VALUE" lines. +ac_dA='s%^\([ ]*\)#\([ ]*define[ ][ ]*\)' +ac_dB='\([ ][ ]*\)[^ ]*%\1#\2' +ac_dC='\3' +ac_dD='%g' +# ac_u turns "#undef NAME" with trailing blanks into "#define NAME VALUE". +ac_uA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_uB='\([ ]\)%\1#\2define\3' +ac_uC=' ' +ac_uD='\4%g' +# ac_e turns "#undef NAME" without trailing blanks into "#define NAME VALUE". +ac_eA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_eB='$%\1#\2define\3' +ac_eC=' ' +ac_eD='%g' + +if test "${CONFIG_HEADERS+set}" != set; then +EOF +cat >> $CONFIG_STATUS <<EOF + CONFIG_HEADERS="config.h" +EOF +cat >> $CONFIG_STATUS <<\EOF +fi +for ac_file in .. $CONFIG_HEADERS; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + echo creating $ac_file + + rm -f conftest.frag conftest.in conftest.out + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + cat $ac_file_inputs > conftest.in + +EOF + +# Transform confdefs.h into a sed script conftest.vals that substitutes +# the proper values into config.h.in to produce config.h. And first: +# Protect against being on the right side of a sed subst in config.status. +# Protect against being in an unquoted here document in config.status. +rm -f conftest.vals +cat > conftest.hdr <<\EOF +s/[\\&%]/\\&/g +s%[\\$`]%\\&%g +s%#define \([A-Za-z_][A-Za-z0-9_]*\) *\(.*\)%${ac_dA}\1${ac_dB}\1${ac_dC}\2${ac_dD}%gp +s%ac_d%ac_u%gp +s%ac_u%ac_e%gp +EOF +sed -n -f conftest.hdr confdefs.h > conftest.vals +rm -f conftest.hdr + +# This sed command replaces #undef with comments. This is necessary, for +# example, in the case of _POSIX_SOURCE, which is predefined and required +# on some systems where configure will not decide to define it. +cat >> conftest.vals <<\EOF +s%^[ ]*#[ ]*undef[ ][ ]*[a-zA-Z_][a-zA-Z_0-9]*%/* & */% +EOF + +# Break up conftest.vals because some shells have a limit on +# the size of here documents, and old seds have small limits too. + +rm -f conftest.tail +while : +do + ac_lines=`grep -c . conftest.vals` + # grep -c gives empty output for an empty file on some AIX systems. + if test -z "$ac_lines" || test "$ac_lines" -eq 0; then break; fi + # Write a limited-size here document to conftest.frag. + echo ' cat > conftest.frag <<CEOF' >> $CONFIG_STATUS + sed ${ac_max_here_lines}q conftest.vals >> $CONFIG_STATUS + echo 'CEOF + sed -f conftest.frag conftest.in > conftest.out + rm -f conftest.in + mv conftest.out conftest.in +' >> $CONFIG_STATUS + sed 1,${ac_max_here_lines}d conftest.vals > conftest.tail + rm -f conftest.vals + mv conftest.tail conftest.vals +done +rm -f conftest.vals + +cat >> $CONFIG_STATUS <<\EOF + rm -f conftest.frag conftest.h + echo "/* $ac_file. Generated automatically by configure. */" > conftest.h + cat conftest.in >> conftest.h + rm -f conftest.in + if cmp -s $ac_file conftest.h 2>/dev/null; then + echo "$ac_file is unchanged" + rm -f conftest.h + else + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + fi + rm -f $ac_file + mv conftest.h $ac_file + fi +fi; done + +EOF +cat >> $CONFIG_STATUS <<EOF + + +EOF +cat >> $CONFIG_STATUS <<\EOF +test -z "$CONFIG_HEADERS" || echo timestamp > stamp-h + +exit 0 +EOF +chmod +x $CONFIG_STATUS +rm -fr confdefs* $ac_clean_files +test "$no_create" = yes || ${CONFIG_SHELL-/bin/sh} $CONFIG_STATUS || exit 1 + diff --git a/package/network/services/ead/src/tinysrp/configure.in b/package/network/services/ead/src/tinysrp/configure.in new file mode 100644 index 0000000000..627d15a8c7 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/configure.in @@ -0,0 +1,52 @@ +dnl Process this file with autoconf to produce a configure script. + +AC_INIT(t_pwd.h) +AM_CONFIG_HEADER(config.h) +AM_INIT_AUTOMAKE(libtinysrp, 0.7.5) + +test "$CFLAGS" = "" && CFLAGS="-O2" + +dnl Checks for programs. + +AC_PROG_CC +AC_PROG_INSTALL +AC_PROG_LN_S +AC_PROG_RANLIB +AC_ARG_PROGRAM + +dnl Checks for header files. + +AC_HEADER_STDC +AC_CHECK_HEADERS(sgtty.h sys/ioctl.h sys/time.h termio.h termios.h unistd.h) + +dnl Checks for typedefs, structures, and compiler characteristics. + +AC_C_CONST +AC_C_INLINE +AC_HEADER_TIME +AC_C_BIGENDIAN +AC_CHECK_SIZEOF(short) +AC_CHECK_SIZEOF(int) +AC_CHECK_SIZEOF(long) +AC_CHECK_SIZEOF(long long) +AC_TRY_COMPILE(, [volatile int i;], , AC_DEFINE(volatile, )) +AC_C_CHAR_UNSIGNED + +AC_SUBST(signed)dnl +if test "$ac_cv_c_char_unsigned" = "yes"; then + signed=-signed +fi + +dnl Checks for library functions. + +AC_CHECK_FUNCS(sigaction strchr memcpy) +TYPE_SIGNAL +AC_HEADER_CHECK(termios.h,AC_FUNC_CHECK(cfsetispeed,AC_DEFINE(POSIX_TERMIOS))) + +dnl User options + +dnl Some defines for now. + +AC_DEFINE(SHA1HANDSOFF) + +AC_OUTPUT(Makefile) diff --git a/package/network/services/ead/src/tinysrp/install-sh b/package/network/services/ead/src/tinysrp/install-sh new file mode 100755 index 0000000000..e8436696c1 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/install-sh @@ -0,0 +1,250 @@ +#!/bin/sh +# +# install - install a program, script, or datafile +# This comes from X11R5 (mit/util/scripts/install.sh). +# +# Copyright 1991 by the Massachusetts Institute of Technology +# +# Permission to use, copy, modify, distribute, and sell this software and its +# documentation for any purpose is hereby granted without fee, provided that +# the above copyright notice appear in all copies and that both that +# copyright notice and this permission notice appear in supporting +# documentation, and that the name of M.I.T. not be used in advertising or +# publicity pertaining to distribution of the software without specific, +# written prior permission. M.I.T. makes no representations about the +# suitability of this software for any purpose. It is provided "as is" +# without express or implied warranty. +# +# Calling this script install-sh is preferred over install.sh, to prevent +# `make' implicit rules from creating a file called install from it +# when there is no Makefile. +# +# This script is compatible with the BSD install script, but was written +# from scratch. It can only install one file at a time, a restriction +# shared with many OS's install programs. + + +# set DOITPROG to echo to test this script + +# Don't use :- since 4.3BSD and earlier shells don't like it. +doit="${DOITPROG-}" + + +# put in absolute paths if you don't have them in your path; or use env. vars. + +mvprog="${MVPROG-mv}" +cpprog="${CPPROG-cp}" +chmodprog="${CHMODPROG-chmod}" +chownprog="${CHOWNPROG-chown}" +chgrpprog="${CHGRPPROG-chgrp}" +stripprog="${STRIPPROG-strip}" +rmprog="${RMPROG-rm}" +mkdirprog="${MKDIRPROG-mkdir}" + +transformbasename="" +transform_arg="" +instcmd="$mvprog" +chmodcmd="$chmodprog 0755" +chowncmd="" +chgrpcmd="" +stripcmd="" +rmcmd="$rmprog -f" +mvcmd="$mvprog" +src="" +dst="" +dir_arg="" + +while [ x"$1" != x ]; do + case $1 in + -c) instcmd="$cpprog" + shift + continue;; + + -d) dir_arg=true + shift + continue;; + + -m) chmodcmd="$chmodprog $2" + shift + shift + continue;; + + -o) chowncmd="$chownprog $2" + shift + shift + continue;; + + -g) chgrpcmd="$chgrpprog $2" + shift + shift + continue;; + + -s) stripcmd="$stripprog" + shift + continue;; + + -t=*) transformarg=`echo $1 | sed 's/-t=//'` + shift + continue;; + + -b=*) transformbasename=`echo $1 | sed 's/-b=//'` + shift + continue;; + + *) if [ x"$src" = x ] + then + src=$1 + else + # this colon is to work around a 386BSD /bin/sh bug + : + dst=$1 + fi + shift + continue;; + esac +done + +if [ x"$src" = x ] +then + echo "install: no input file specified" + exit 1 +else + true +fi + +if [ x"$dir_arg" != x ]; then + dst=$src + src="" + + if [ -d $dst ]; then + instcmd=: + else + instcmd=mkdir + fi +else + +# Waiting for this to be detected by the "$instcmd $src $dsttmp" command +# might cause directories to be created, which would be especially bad +# if $src (and thus $dsttmp) contains '*'. + + if [ -f $src -o -d $src ] + then + true + else + echo "install: $src does not exist" + exit 1 + fi + + if [ x"$dst" = x ] + then + echo "install: no destination specified" + exit 1 + else + true + fi + +# If destination is a directory, append the input filename; if your system +# does not like double slashes in filenames, you may need to add some logic + + if [ -d $dst ] + then + dst="$dst"/`basename $src` + else + true + fi +fi + +## this sed command emulates the dirname command +dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` + +# Make sure that the destination directory exists. +# this part is taken from Noah Friedman's mkinstalldirs script + +# Skip lots of stat calls in the usual case. +if [ ! -d "$dstdir" ]; then +defaultIFS=' +' +IFS="${IFS-${defaultIFS}}" + +oIFS="${IFS}" +# Some sh's can't handle IFS=/ for some reason. +IFS='%' +set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'` +IFS="${oIFS}" + +pathcomp='' + +while [ $# -ne 0 ] ; do + pathcomp="${pathcomp}${1}" + shift + + if [ ! -d "${pathcomp}" ] ; + then + $mkdirprog "${pathcomp}" + else + true + fi + + pathcomp="${pathcomp}/" +done +fi + +if [ x"$dir_arg" != x ] +then + $doit $instcmd $dst && + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi +else + +# If we're going to rename the final executable, determine the name now. + + if [ x"$transformarg" = x ] + then + dstfile=`basename $dst` + else + dstfile=`basename $dst $transformbasename | + sed $transformarg`$transformbasename + fi + +# don't allow the sed command to completely eliminate the filename + + if [ x"$dstfile" = x ] + then + dstfile=`basename $dst` + else + true + fi + +# Make a temp file name in the proper directory. + + dsttmp=$dstdir/#inst.$$# + +# Move or copy the file name to the temp name + + $doit $instcmd $src $dsttmp && + + trap "rm -f ${dsttmp}" 0 && + +# and set any options; do chmod last to preserve setuid bits + +# If any of these fail, we abort the whole thing. If we want to +# ignore errors from any of these, just make sure not to ignore +# errors from the above "$doit $instcmd $src $dsttmp" command. + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi && + +# Now rename the file to the real destination. + + $doit $rmcmd -f $dstdir/$dstfile && + $doit $mvcmd $dsttmp $dstdir/$dstfile + +fi && + + +exit 0 diff --git a/package/network/services/ead/src/tinysrp/missing b/package/network/services/ead/src/tinysrp/missing new file mode 100755 index 0000000000..a6abd06980 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/missing @@ -0,0 +1,134 @@ +#! /bin/sh +# Common stub for a few missing GNU programs while installing. +# Copyright (C) 1996, 1997 Free Software Foundation, Inc. +# Franc,ois Pinard <pinard@iro.umontreal.ca>, 1996. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2, or (at your option) +# any later version. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. + +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA +# 02111-1307, USA. + +if test $# -eq 0; then + echo 1>&2 "Try \`$0 --help' for more information" + exit 1 +fi + +case "$1" in + + -h|--h|--he|--hel|--help) + echo "\ +$0 [OPTION]... PROGRAM [ARGUMENT]... + +Handle \`PROGRAM [ARGUMENT]...' for when PROGRAM is missing, or return an +error status if there is no known handling for PROGRAM. + +Options: + -h, --help display this help and exit + -v, --version output version information and exit + +Supported PROGRAM values: + aclocal touch file \`aclocal.m4' + autoconf touch file \`configure' + autoheader touch file \`config.h.in' + automake touch all \`Makefile.in' files + bison touch file \`y.tab.c' + makeinfo touch the output file + yacc touch file \`y.tab.c'" + ;; + + -v|--v|--ve|--ver|--vers|--versi|--versio|--version) + echo "missing - GNU libit 0.0" + ;; + + -*) + echo 1>&2 "$0: Unknown \`$1' option" + echo 1>&2 "Try \`$0 --help' for more information" + exit 1 + ;; + + aclocal) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`acinclude.m4' or \`configure.in'. You might want + to install the \`Automake' and \`Perl' packages. Grab them from + any GNU archive site." + touch aclocal.m4 + ;; + + autoconf) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`configure.in'. You might want to install the + \`Autoconf' and \`GNU m4' packages. Grab them from any GNU + archive site." + touch configure + ;; + + autoheader) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`acconfig.h' or \`configure.in'. You might want + to install the \`Autoconf' and \`GNU m4' packages. Grab them + from any GNU archive site." + touch config.h.in + ;; + + automake) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`Makefile.am', \`acinclude.m4' or \`configure.in'. + You might want to install the \`Automake' and \`Perl' packages. + Grab them from any GNU archive site." + find . -type f -name Makefile.am -print \ + | sed 's/^\(.*\).am$/touch \1.in/' \ + | sh + ;; + + bison|yacc) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.y' file. You may need the \`Bison' package + in order for those modifications to take effect. You can get + \`Bison' from any GNU archive site." + touch y.tab.c + ;; + + makeinfo) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.texi' or \`.texinfo' file, or any other file + indirectly affecting the aspect of the manual. The spurious + call might also be the consequence of using a buggy \`make' (AIX, + DU, IRIX). You might want to install the \`Texinfo' package or + the \`GNU make' package. Grab either from any GNU archive site." + file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'` + if test -z "$file"; then + file=`echo "$*" | sed 's/.* \([^ ]*\) *$/\1/'` + file=`sed -n '/^@setfilename/ { s/.* \([^ ]*\) *$/\1/; p; q; }' $file` + fi + touch $file + ;; + + *) + echo 1>&2 "\ +WARNING: \`$1' is needed, and you do not seem to have it handy on your + system. You might have modified some files without having the + proper tools for further handling them. Check the \`README' file, + it often tells you about the needed prerequirements for installing + this package. You may also peek at any GNU archive site, in case + some other package would contain this missing \`$1' program." + exit 1 + ;; +esac + +exit 0 diff --git a/package/network/services/ead/src/tinysrp/mkinstalldirs b/package/network/services/ead/src/tinysrp/mkinstalldirs new file mode 100755 index 0000000000..3bc183603e --- /dev/null +++ b/package/network/services/ead/src/tinysrp/mkinstalldirs @@ -0,0 +1,39 @@ +#! /bin/sh +# mkinstalldirs --- make directory hierarchy +# Author: Noah Friedman <friedman@prep.ai.mit.edu> +# Created: 1993-05-16 +# Public domain + + +errstatus=0 + +for file +do + set fnord `echo ":$file" | sed -ne 's/^:\//#/;s/^://;s/\// /g;s/^#/\//;p'` + shift + + pathcomp= + for d + do + pathcomp="$pathcomp$d" + case "$pathcomp" in + -* ) pathcomp=./$pathcomp ;; + esac + + if test ! -d "$pathcomp"; then + echo "mkdir $pathcomp" 1>&2 + + mkdir "$pathcomp" || lasterr=$? + + if test ! -d "$pathcomp"; then + errstatus=$lasterr + fi + fi + + pathcomp="$pathcomp/" + done +done + +exit $errstatus + +# mkinstalldirs ends here diff --git a/package/network/services/ead/src/tinysrp/srvtest.c b/package/network/services/ead/src/tinysrp/srvtest.c new file mode 100644 index 0000000000..e09d501ad3 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/srvtest.c @@ -0,0 +1,111 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> +#include "t_defines.h" +#include "t_pwd.h" +#include "t_server.h" + +int +main(argc, argv) + int argc; + char * argv[]; +{ + struct t_server * ts; + struct t_pw * tpw; + struct t_conf * tcnf; + struct t_num * B; + char username[MAXUSERLEN]; + char hexbuf[MAXHEXPARAMLEN]; + char buf[MAXPARAMLEN]; + struct t_num A; + unsigned char * skey; + unsigned char cbuf[20]; + FILE * fp; + FILE * fp2; + char confname[256]; + + printf("Enter username: "); + fgets(username, sizeof(username), stdin); + username[strlen(username) - 1] = '\0'; + ts = t_serveropen(username); + + if(ts == NULL) { + fprintf(stderr, "User %s not found\n", username); + exit(1); + } + +#if 0 + printf("n: %s\n", t_tob64(hexbuf, ts->n.data, ts->n.len)); + printf("g: %s\n", t_tob64(hexbuf, ts->g.data, ts->g.len)); +#endif + printf("index (to client): %d\n", ts->index); + printf("salt (to client): %s\n", t_tob64(hexbuf, ts->s.data, ts->s.len)); + + B = t_servergenexp(ts); + printf("Enter A (from client): "); + fgets(hexbuf, sizeof(hexbuf), stdin); + A.data = buf; + A.len = t_fromb64(A.data, hexbuf); + + printf("B (to client): %s\n", t_tob64(hexbuf, B->data, B->len)); + + skey = t_servergetkey(ts, &A); + printf("Session key: %s\n", t_tohex(hexbuf, skey, 40)); + + /* printf("[Expected response: %s]\n", t_tohex(hexbuf, cbuf, 16)); */ + + printf("Enter response (from client): "); + fgets(hexbuf, sizeof(hexbuf), stdin); + hexbuf[strlen(hexbuf) - 1] = '\0'; + t_fromhex(cbuf, hexbuf); + + if(t_serververify(ts, cbuf) == 0) { + printf("Authentication successful.\n"); + printf("Response (to client): %s\n", + t_tohex(hexbuf, t_serverresponse(ts), RESPONSE_LEN)); + } else + printf("Authentication failed.\n"); + + t_serverclose(ts); + + return 0; +} diff --git a/package/network/services/ead/src/tinysrp/stamp-h.in b/package/network/services/ead/src/tinysrp/stamp-h.in new file mode 100644 index 0000000000..9788f70238 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/stamp-h.in @@ -0,0 +1 @@ +timestamp diff --git a/package/network/services/ead/src/tinysrp/t_client.c b/package/network/services/ead/src/tinysrp/t_client.c new file mode 100644 index 0000000000..ebdd203af5 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_client.c @@ -0,0 +1,287 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> +#include "t_defines.h" +#include "t_pwd.h" +#include "t_client.h" +#include "t_sha.h" + +_TYPE( struct t_client * ) +t_clientopen(u, n, g, s) + const char * u; + struct t_num * n; + struct t_num * g; + struct t_num * s; +{ + struct t_client * tc; + unsigned char buf1[SHA_DIGESTSIZE], buf2[SHA_DIGESTSIZE]; + SHA1_CTX ctxt; + int i, validated; + struct t_preconf * tpc; + + BigInteger nn, gg, n12, r; + + validated = 0; + if(n->len < MIN_MOD_BYTES) + return 0; + for(i = 0; i < t_getprecount(); ++i) { + tpc = t_getpreparam(i); + if(tpc->modulus.len == n->len && tpc->generator.len == g->len && + memcmp(tpc->modulus.data, n->data, n->len) == 0 && + memcmp(tpc->generator.data, g->data, g->len) == 0) { + validated = 1; /* Match found, done */ + break; + } + } + + if(validated == 0) + return 0; + + if((tc = malloc(sizeof(struct t_client))) == 0) + return 0; + + strncpy(tc->username, u, MAXUSERLEN); + + SHA1Init(&tc->hash); + + tc->n.len = n->len; + tc->n.data = tc->nbuf; + memcpy(tc->n.data, n->data, tc->n.len); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, tc->n.data, tc->n.len); + SHA1Final(buf1, &ctxt); + + tc->g.len = g->len; + tc->g.data = tc->gbuf; + memcpy(tc->g.data, g->data, tc->g.len); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, tc->g.data, tc->g.len); + SHA1Final(buf2, &ctxt); + + for(i = 0; i < sizeof(buf1); ++i) + buf1[i] ^= buf2[i]; + + SHA1Update(&tc->hash, buf1, sizeof(buf1)); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, tc->username, strlen(tc->username)); + SHA1Final(buf1, &ctxt); + + SHA1Update(&tc->hash, buf1, sizeof(buf1)); + + tc->s.len = s->len; + tc->s.data = tc->sbuf; + memcpy(tc->s.data, s->data, tc->s.len); + + SHA1Update(&tc->hash, tc->s.data, tc->s.len); + + tc->a.data = tc->abuf; + tc->A.data = tc->Abuf; + tc->p.data = tc->pbuf; + tc->v.data = tc->vbuf; + + SHA1Init(&tc->ckhash); + + return tc; +} + +_TYPE( struct t_num * ) +t_clientgenexp(tc) + struct t_client * tc; +{ + BigInteger a, A, n, g; + + if(tc->n.len < ALEN) + tc->a.len = tc->n.len; + else + tc->a.len = ALEN; + + t_random(tc->a.data, tc->a.len); + a = BigIntegerFromBytes(tc->a.data, tc->a.len); + n = BigIntegerFromBytes(tc->n.data, tc->n.len); + g = BigIntegerFromBytes(tc->g.data, tc->g.len); + A = BigIntegerFromInt(0); + BigIntegerModExp(A, g, a, n); + tc->A.len = BigIntegerToBytes(A, tc->A.data); + + BigIntegerFree(A); + BigIntegerFree(a); + BigIntegerFree(g); + BigIntegerFree(n); + + SHA1Update(&tc->hash, tc->A.data, tc->A.len); + SHA1Update(&tc->ckhash, tc->A.data, tc->A.len); + + return &tc->A; +} + +_TYPE( void ) +t_clientpasswd(tc, password) + struct t_client * tc; + char * password; +{ + BigInteger n, g, p, v; + SHA1_CTX ctxt; + unsigned char dig[SHA_DIGESTSIZE]; + + n = BigIntegerFromBytes(tc->n.data, tc->n.len); + g = BigIntegerFromBytes(tc->g.data, tc->g.len); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, tc->username, strlen(tc->username)); + SHA1Update(&ctxt, ":", 1); + SHA1Update(&ctxt, password, strlen(password)); + SHA1Final(dig, &ctxt); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, tc->s.data, tc->s.len); + SHA1Update(&ctxt, dig, sizeof(dig)); + SHA1Final(dig, &ctxt); + + p = BigIntegerFromBytes(dig, sizeof(dig)); + + v = BigIntegerFromInt(0); + BigIntegerModExp(v, g, p, n); + + tc->p.len = BigIntegerToBytes(p, tc->p.data); + BigIntegerFree(p); + + tc->v.len = BigIntegerToBytes(v, tc->v.data); + BigIntegerFree(v); +} + +_TYPE( unsigned char * ) +t_clientgetkey(tc, serverval) + struct t_client * tc; + struct t_num * serverval; +{ + BigInteger n, B, v, p, a, sum, S; + unsigned char sbuf[MAXPARAMLEN]; + unsigned char dig[SHA_DIGESTSIZE]; + unsigned slen; + unsigned int u; + SHA1_CTX ctxt; + + SHA1Init(&ctxt); + SHA1Update(&ctxt, serverval->data, serverval->len); + SHA1Final(dig, &ctxt); + u = (dig[0] << 24) | (dig[1] << 16) | (dig[2] << 8) | dig[3]; + if(u == 0) + return NULL; + + SHA1Update(&tc->hash, serverval->data, serverval->len); + + B = BigIntegerFromBytes(serverval->data, serverval->len); + n = BigIntegerFromBytes(tc->n.data, tc->n.len); + + if(BigIntegerCmp(B, n) >= 0 || BigIntegerCmpInt(B, 0) == 0) { + BigIntegerFree(B); + BigIntegerFree(n); + return NULL; + } + v = BigIntegerFromBytes(tc->v.data, tc->v.len); + if(BigIntegerCmp(B, v) < 0) + BigIntegerAdd(B, B, n); + BigIntegerSub(B, B, v); + BigIntegerFree(v); + + a = BigIntegerFromBytes(tc->a.data, tc->a.len); + p = BigIntegerFromBytes(tc->p.data, tc->p.len); + + sum = BigIntegerFromInt(0); + BigIntegerMulInt(sum, p, u); + BigIntegerAdd(sum, sum, a); + + BigIntegerFree(p); + BigIntegerFree(a); + + S = BigIntegerFromInt(0); + BigIntegerModExp(S, B, sum, n); + slen = BigIntegerToBytes(S, sbuf); + + BigIntegerFree(S); + BigIntegerFree(sum); + BigIntegerFree(B); + BigIntegerFree(n); + + t_sessionkey(tc->session_key, sbuf, slen); + memset(sbuf, 0, slen); + + SHA1Update(&tc->hash, tc->session_key, sizeof(tc->session_key)); + + SHA1Final(tc->session_response, &tc->hash); + SHA1Update(&tc->ckhash, tc->session_response, sizeof(tc->session_response)); + SHA1Update(&tc->ckhash, tc->session_key, sizeof(tc->session_key)); + + return tc->session_key; +} + +_TYPE( int ) +t_clientverify(tc, resp) + struct t_client * tc; + unsigned char * resp; +{ + unsigned char expected[SHA_DIGESTSIZE]; + + SHA1Final(expected, &tc->ckhash); + return memcmp(expected, resp, sizeof(expected)); +} + +_TYPE( unsigned char * ) +t_clientresponse(tc) + struct t_client * tc; +{ + return tc->session_response; +} + +_TYPE( void ) +t_clientclose(tc) + struct t_client * tc; +{ + memset(tc->abuf, 0, sizeof(tc->abuf)); + memset(tc->pbuf, 0, sizeof(tc->pbuf)); + memset(tc->vbuf, 0, sizeof(tc->vbuf)); + memset(tc->session_key, 0, sizeof(tc->session_key)); + free(tc); +} diff --git a/package/network/services/ead/src/tinysrp/t_client.h b/package/network/services/ead/src/tinysrp/t_client.h new file mode 100644 index 0000000000..42922aff1b --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_client.h @@ -0,0 +1,148 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#ifndef T_CLIENT_H +#define T_CLIENT_H + +#include "t_sha.h" + +#if !defined(P) +#ifdef __STDC__ +#define P(x) x +#else +#define P(x) () +#endif +#endif + +/* For building dynamic link libraries under windows, windows NT + * using MSVC1.5 or MSVC2.0 + */ + +#ifndef _DLLDECL +#define _DLLDECL + +#ifdef MSVC15 /* MSVC1.5 support for 16 bit apps */ +#define _MSVC15EXPORT _export +#define _MSVC20EXPORT +#define _DLLAPI _export _pascal +#define _TYPE(a) a _MSVC15EXPORT +#define DLLEXPORT 1 + +#elif MSVC20 +#define _MSVC15EXPORT +#define _MSVC20EXPORT _declspec(dllexport) +#define _DLLAPI +#define _TYPE(a) _MSVC20EXPORT a +#define DLLEXPORT 1 + +#else /* Default, non-dll. Use this for Unix or DOS */ +#define _MSVC15DEXPORT +#define _MSVC20EXPORT +#define _DLLAPI +#define _TYPE(a) a +#endif +#endif + +#define ALEN 32 +#define MIN_MOD_BYTES 64 /* 512 bits */ + +struct t_client { + struct t_num n; + struct t_num g; + struct t_num s; + + struct t_num a; + struct t_num A; + + struct t_num p; + struct t_num v; + + SHA1_CTX hash, ckhash; + + char username[MAXUSERLEN]; + unsigned char session_key[SESSION_KEY_LEN]; + unsigned char session_response[RESPONSE_LEN]; + + unsigned char nbuf[MAXPARAMLEN], gbuf[MAXPARAMLEN], sbuf[MAXSALTLEN]; + unsigned char pbuf[MAXPARAMLEN], vbuf[MAXPARAMLEN]; + unsigned char abuf[ALEN], Abuf[MAXPARAMLEN]; +}; + +/* + * SRP client-side negotiation + * + * This code negotiates the client side of an SRP exchange. + * "t_clientopen" accepts a username, and N, g, and s parameters, + * which are usually sent by the server in the first round. + * The client should then call... + * "t_clientgenexp" will generate a random 256-bit exponent and + * raise g to that power, returning the result. This result + * should be sent to the server as w(p). + * "t_clientpasswd" accepts the user's password, which should be + * entered locally and updates the client's state. + * "t_clientgetkey" accepts the exponential y(p), which should + * be sent by the server in the next round and computes the + * 256-bit session key. This data should be saved before the + * session is closed. + * "t_clientresponse" computes the session key proof as SHA(y(p), K). + * "t_clientclose" closes the session and frees its memory. + * + * Note that authentication is not performed per se; it is up + * to either/both sides of the protocol to now verify securely + * that their session keys agree in order to establish authenticity. + * One possible way is through "oracle hashing"; one side sends + * r, the other replies with H(r,K), where H() is a hash function. + * + * t_clientresponse and t_clientverify now implement a version of + * the session-key verification described above. + */ +_TYPE( struct t_client * ) + t_clientopen P((const char *, struct t_num *, struct t_num *, + struct t_num *)); +_TYPE( struct t_num * ) t_clientgenexp P((struct t_client *)); +_TYPE( void ) t_clientpasswd P((struct t_client *, char *)); +_TYPE( unsigned char * ) + t_clientgetkey P((struct t_client *, struct t_num *)); +_TYPE( int ) t_clientverify P((struct t_client *, unsigned char *)); +_TYPE( unsigned char * ) t_clientresponse P((struct t_client *)); +_TYPE( void ) t_clientclose P((struct t_client *)); + +#endif diff --git a/package/network/services/ead/src/tinysrp/t_conf.c b/package/network/services/ead/src/tinysrp/t_conf.c new file mode 100644 index 0000000000..fbe6f410e2 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_conf.c @@ -0,0 +1,1080 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> + +#include "t_defines.h" +#include "t_pwd.h" +#include "t_read.h" +#include "bn.h" +#include "bn_lcl.h" +#include "bn_prime.h" + +#define TABLE_SIZE 32 + +static int witness(BIGNUM *w, const BIGNUM *a, const BIGNUM *a1, + const BIGNUM *a1_odd, int k, BN_CTX *ctx, BN_MONT_CTX *mont); + +/* + * This is the safe prime generation logic. + * To generate a safe prime p (where p = 2q+1 and q is prime), we start + * with a random odd q that is one bit shorter than the desired length + * of p. We use a simple 30-element sieve to filter the values of q + * and consider only those that are 11, 23, or 29 (mod 30). (If q were + * anything else, either q or p would be divisible by 2, 3, or 5). + * For the values of q that are left, we apply the following tests in + * this order: + * + * trial divide q + * let p = 2q + 1 + * trial divide p + * apply Fermat test to q (2^q == 2 (mod q)) + * apply Fermat test to p (2^p == 2 (mod p)) + * apply real probablistic primality test to q + * apply real probablistic primality test to p + * + * A number that passes all these tests is considered a safe prime for + * our purposes. The tests are ordered this way for efficiency; the + * slower tests are run rarely if ever at all. + */ + +static int +trialdiv(x) + const BigInteger x; +{ + static int primes[] = { /* All odd primes < 256 */ + 3, 5, 7, 11, 13, 17, 19, 23, 29, + 31, 37, 41, 43, 47, 53, 59, 61, 67, + 71, 73, 79, 83, 89, 97, 101, 103, + 107, 109, 113, 127, 131, 137, 139, 149, 151, + 157, 163, 167, 173, 179, 181, 191, 193, 197, + 199, 211, 223, 227, 229, 233, 239, 241, 251 + }; + static int nprimes = sizeof(primes) / sizeof(int); + int i; + + for(i = 0; i < nprimes; ++i) { + if(BigIntegerModInt(x, primes[i]) == 0) + return primes[i]; + } + return 1; +} + +/* x + sieve30[x%30] == 11, 23, or 29 (mod 30) */ + +static int sieve30[] = +{ 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, + 1, 12, 11, 10, 9, 8, 7, 6, 5, 4, + 3, 2, 1, 6, 5, 4, 3, 2, 1, 12 +}; + +/* Find a Sophie-Germain prime between "lo" and "hi". NOTE: this is not + a "safe prime", but the smaller prime. Take 2q+1 to get the safe prime. */ + +static void +sophie_germain(q, lo, hi) + BigInteger q; /* assumed initialized */ + const BigInteger lo; + const BigInteger hi; +{ + BigInteger m, p, r; + char parambuf[MAXPARAMLEN]; + int foundprime = 0; + int i, mod30; + + m = BigIntegerFromInt(0); + BigIntegerSub(m, hi, lo); + i = (BigIntegerBitLen(m) + 7) / 8; + t_random(parambuf, i); + r = BigIntegerFromBytes(parambuf, i); + BigIntegerMod(r, r, m); + + BigIntegerAdd(q, r, lo); + if(BigIntegerModInt(q, 2) == 0) + BigIntegerAddInt(q, q, 1); /* make q odd */ + + mod30 = BigIntegerModInt(q, 30); /* mod30 = q % 30 */ + + BigIntegerFree(m); + m = BigIntegerFromInt(2); /* m = 2 */ + p = BigIntegerFromInt(0); + + while(BigIntegerCmp(q, hi) < 0) { + if(trialdiv(q) < 2) { + BigIntegerMulInt(p, q, 2); /* p = 2 * q */ + BigIntegerAddInt(p, p, 1); /* p += 1 */ + if(trialdiv(p) < 2) { + BigIntegerModExp(r, m, q, q); /* r = 2^q % q */ + if(BigIntegerCmpInt(r, 2) == 0) { /* if(r == 2) */ + BigIntegerModExp(r, m, p, p); /* r = 2^p % p */ + if(BigIntegerCmpInt(r, 2) == 0) { /* if(r == 2) */ + if(BigIntegerCheckPrime(q) && BigIntegerCheckPrime(p)) { + ++foundprime; + break; + } + } + } + } + } + + i = sieve30[mod30]; + BigIntegerAddInt(q, q, i); /* q += i */ + mod30 = (mod30 + i) % 30; + } + + /* should wrap around on failure */ + if(!foundprime) { + fprintf(stderr, "Prime generation failed!\n"); + exit(1); + } + + BigIntegerFree(r); + BigIntegerFree(m); + BigIntegerFree(p); +} + +_TYPE( struct t_confent * ) +t_makeconfent(tc, nsize) + struct t_conf * tc; + int nsize; +{ + BigInteger n, g, q, t, u; + + t = BigIntegerFromInt(0); + u = BigIntegerFromInt(1); /* u = 1 */ + BigIntegerLShift(t, u, nsize - 2); /* t = 2^(nsize-2) */ + BigIntegerMulInt(u, t, 2); /* u = 2^(nsize-1) */ + + q = BigIntegerFromInt(0); + sophie_germain(q, t, u); + + n = BigIntegerFromInt(0); + BigIntegerMulInt(n, q, 2); + BigIntegerAddInt(n, n, 1); + + /* Look for a generator mod n */ + g = BigIntegerFromInt(2); + while(1) { + BigIntegerModExp(t, g, q, n); /* t = g^q % n */ + if(BigIntegerCmpInt(t, 1) == 0) /* if(t == 1) */ + BigIntegerAddInt(g, g, 1); /* ++g */ + else + break; + } + BigIntegerFree(t); + BigIntegerFree(u); + BigIntegerFree(q); + + tc->tcbuf.modulus.data = tc->modbuf; + tc->tcbuf.modulus.len = BigIntegerToBytes(n, tc->tcbuf.modulus.data); + BigIntegerFree(n); + + tc->tcbuf.generator.data = tc->genbuf; + tc->tcbuf.generator.len = BigIntegerToBytes(g, tc->tcbuf.generator.data); + BigIntegerFree(g); + + tc->tcbuf.index = 1; + return &tc->tcbuf; +} + +_TYPE( struct t_confent * ) +t_makeconfent_c(tc, nsize) + struct t_conf * tc; + int nsize; +{ + BigInteger g, n, p, q, j, k, t, u; + int psize, qsize; + + psize = nsize / 2; + qsize = nsize - psize; + + t = BigIntegerFromInt(1); /* t = 1 */ + u = BigIntegerFromInt(0); + BigIntegerLShift(u, t, psize - 3); /* u = t*2^(psize-3) = 2^(psize-3) */ + BigIntegerMulInt(t, u, 3); /* t = 3*u = 1.5*2^(psize-2) */ + BigIntegerAdd(u, u, t); /* u += t [u = 2^(psize-1)] */ + j = BigIntegerFromInt(0); + sophie_germain(j, t, u); + + k = BigIntegerFromInt(0); + if(qsize != psize) { + BigIntegerFree(t); + t = BigIntegerFromInt(1); /* t = 1 */ + BigIntegerLShift(u, t, qsize - 3); /* u = t*2^(qsize-3) = 2^(qsize-3) */ + BigIntegerMulInt(t, u, 3); /* t = 3*u = 1.5*2^(qsize-2) */ + BigIntegerAdd(u, u, t); /* u += t [u = 2^(qsize-1)] */ + } + sophie_germain(k, t, u); + + p = BigIntegerFromInt(0); + BigIntegerMulInt(p, j, 2); /* p = 2 * j */ + BigIntegerAddInt(p, p, 1); /* p += 1 */ + + q = BigIntegerFromInt(0); + BigIntegerMulInt(q, k, 2); /* q = 2 * k */ + BigIntegerAddInt(q, q, 1); /* q += 1 */ + + n = BigIntegerFromInt(0); + BigIntegerMul(n, p, q); /* n = p * q */ + BigIntegerMul(u, j, k); /* u = j * k */ + + BigIntegerFree(p); + BigIntegerFree(q); + BigIntegerFree(j); + BigIntegerFree(k); + + g = BigIntegerFromInt(2); /* g = 2 */ + + /* Look for a generator mod n */ + while(1) { + BigIntegerModExp(t, g, u, n); /* t = g^u % n */ + if(BigIntegerCmpInt(t, 1) == 0) + BigIntegerAddInt(g, g, 1); /* ++g */ + else + break; + } + + BigIntegerFree(u); + BigIntegerFree(t); + + tc->tcbuf.modulus.data = tc->modbuf; + tc->tcbuf.modulus.len = BigIntegerToBytes(n, tc->tcbuf.modulus.data); + BigIntegerFree(n); + + tc->tcbuf.generator.data = tc->genbuf; + tc->tcbuf.generator.len = BigIntegerToBytes(g, tc->tcbuf.generator.data); + BigIntegerFree(g); + + tc->tcbuf.index = 1; + return &tc->tcbuf; +} + +_TYPE( struct t_confent * ) +t_newconfent(tc) + struct t_conf * tc; +{ + tc->tcbuf.index = 0; + tc->tcbuf.modulus.data = tc->modbuf; + tc->tcbuf.modulus.len = 0; + tc->tcbuf.generator.data = tc->genbuf; + tc->tcbuf.generator.len = 0; + return &tc->tcbuf; +} + +_TYPE( void ) +t_putconfent(ent, fp) + const struct t_confent * ent; + FILE * fp; +{ + char strbuf[MAXB64PARAMLEN]; + + fprintf(fp, "%d:%s:", ent->index, + t_tob64(strbuf, ent->modulus.data, ent->modulus.len)); + fprintf(fp, "%s\n", + t_tob64(strbuf, ent->generator.data, ent->generator.len)); +} + +int +BigIntegerBitLen(b) + BigInteger b; +{ + return BN_num_bits(b); +} + +int +BigIntegerCheckPrime(n) + BigInteger n; +{ + BN_CTX * ctx = BN_CTX_new(); + int rv = BN_is_prime(n, 25, NULL, ctx, NULL); + BN_CTX_free(ctx); + return rv; +} + +unsigned int +BigIntegerModInt(d, m) + BigInteger d; + unsigned int m; +{ + return BN_mod_word(d, m); +} + +void +BigIntegerMod(result, d, m) + BigInteger result, d, m; +{ + BN_CTX * ctx = BN_CTX_new(); + BN_mod(result, d, m, ctx); + BN_CTX_free(ctx); +} + +void +BigIntegerMul(result, m1, m2) + BigInteger result, m1, m2; +{ + BN_CTX * ctx = BN_CTX_new(); + BN_mul(result, m1, m2, ctx); + BN_CTX_free(ctx); +} + +void +BigIntegerLShift(result, x, bits) + BigInteger result, x; + unsigned int bits; +{ + BN_lshift(result, x, bits); +} + +int BN_is_prime(const BIGNUM *a, int checks, void (*callback)(int,int,void *), + BN_CTX *ctx_passed, void *cb_arg) + { + return BN_is_prime_fasttest(a, checks, callback, ctx_passed, cb_arg, 0); + } + +int BN_is_prime_fasttest(const BIGNUM *a, int checks, + void (*callback)(int,int,void *), + BN_CTX *ctx_passed, void *cb_arg, + int do_trial_division) + { + int i, j, ret = -1; + int k; + BN_CTX *ctx = NULL; + BIGNUM *A1, *A1_odd, *check; /* taken from ctx */ + BN_MONT_CTX *mont = NULL; + const BIGNUM *A = NULL; + + if (checks == BN_prime_checks) + checks = BN_prime_checks_for_size(BN_num_bits(a)); + + /* first look for small factors */ + if (!BN_is_odd(a)) + return(0); + if (do_trial_division) + { + for (i = 1; i < NUMPRIMES; i++) + if (BN_mod_word(a, primes[i]) == 0) + return 0; + if (callback != NULL) callback(1, -1, cb_arg); + } + + if (ctx_passed != NULL) + ctx = ctx_passed; + else + if ((ctx=BN_CTX_new()) == NULL) + goto err; + BN_CTX_start(ctx); + + /* A := abs(a) */ + if (a->neg) + { + BIGNUM *t; + if ((t = BN_CTX_get(ctx)) == NULL) goto err; + BN_copy(t, a); + t->neg = 0; + A = t; + } + else + A = a; + A1 = BN_CTX_get(ctx); + A1_odd = BN_CTX_get(ctx); + check = BN_CTX_get(ctx); + if (check == NULL) goto err; + + /* compute A1 := A - 1 */ + if (!BN_copy(A1, A)) + goto err; + if (!BN_sub_word(A1, 1)) + goto err; + if (BN_is_zero(A1)) + { + ret = 0; + goto err; + } + + /* write A1 as A1_odd * 2^k */ + k = 1; + while (!BN_is_bit_set(A1, k)) + k++; + if (!BN_rshift(A1_odd, A1, k)) + goto err; + + /* Montgomery setup for computations mod A */ + mont = BN_MONT_CTX_new(); + if (mont == NULL) + goto err; + if (!BN_MONT_CTX_set(mont, A, ctx)) + goto err; + + for (i = 0; i < checks; i++) + { + if (!BN_pseudo_rand(check, BN_num_bits(A1), 0, 0)) + goto err; + if (BN_cmp(check, A1) >= 0) + if (!BN_sub(check, check, A1)) + goto err; + if (!BN_add_word(check, 1)) + goto err; + /* now 1 <= check < A */ + + j = witness(check, A, A1, A1_odd, k, ctx, mont); + if (j == -1) goto err; + if (j) + { + ret=0; + goto err; + } + if (callback != NULL) callback(1,i,cb_arg); + } + ret=1; +err: + if (ctx != NULL) + { + BN_CTX_end(ctx); + if (ctx_passed == NULL) + BN_CTX_free(ctx); + } + if (mont != NULL) + BN_MONT_CTX_free(mont); + + return(ret); + } + +static int witness(BIGNUM *w, const BIGNUM *a, const BIGNUM *a1, + const BIGNUM *a1_odd, int k, BN_CTX *ctx, BN_MONT_CTX *mont) + { + if (!BN_mod_exp_mont(w, w, a1_odd, a, ctx, mont)) /* w := w^a1_odd mod a */ + return -1; + if (BN_is_one(w)) + return 0; /* probably prime */ + if (BN_cmp(w, a1) == 0) + return 0; /* w == -1 (mod a), 'a' is probably prime */ + while (--k) + { + if (!BN_mod_mul(w, w, w, a, ctx)) /* w := w^2 mod a */ + return -1; + if (BN_is_one(w)) + return 1; /* 'a' is composite, otherwise a previous 'w' would + * have been == -1 (mod 'a') */ + if (BN_cmp(w, a1) == 0) + return 0; /* w == -1 (mod a), 'a' is probably prime */ + } + /* If we get here, 'w' is the (a-1)/2-th power of the original 'w', + * and it is neither -1 nor +1 -- so 'a' cannot be prime */ + return 1; + } + +int BN_mod_exp_mont(BIGNUM *rr, BIGNUM *a, const BIGNUM *p, + const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *in_mont) + { + int i,j,bits,ret=0,wstart,wend,window,wvalue; + int start=1,ts=0; + BIGNUM *d,*r; + BIGNUM *aa; + BIGNUM val[TABLE_SIZE]; + BN_MONT_CTX *mont=NULL; + + bn_check_top(a); + bn_check_top(p); + bn_check_top(m); + + if (!(m->d[0] & 1)) + { + return(0); + } + bits=BN_num_bits(p); + if (bits == 0) + { + BN_one(rr); + return(1); + } + BN_CTX_start(ctx); + d = BN_CTX_get(ctx); + r = BN_CTX_get(ctx); + if (d == NULL || r == NULL) goto err; + + /* If this is not done, things will break in the montgomery + * part */ + + if (in_mont != NULL) + mont=in_mont; + else + { + if ((mont=BN_MONT_CTX_new()) == NULL) goto err; + if (!BN_MONT_CTX_set(mont,m,ctx)) goto err; + } + + BN_init(&val[0]); + ts=1; + if (BN_ucmp(a,m) >= 0) + { + if (!BN_mod(&(val[0]),a,m,ctx)) + goto err; + aa= &(val[0]); + } + else + aa=a; + if (!BN_to_montgomery(&(val[0]),aa,mont,ctx)) goto err; /* 1 */ + + window = BN_window_bits_for_exponent_size(bits); + if (window > 1) + { + if (!BN_mod_mul_montgomery(d,&(val[0]),&(val[0]),mont,ctx)) goto err; /* 2 */ + j=1<<(window-1); + for (i=1; i<j; i++) + { + BN_init(&(val[i])); + if (!BN_mod_mul_montgomery(&(val[i]),&(val[i-1]),d,mont,ctx)) + goto err; + } + ts=i; + } + + start=1; /* This is used to avoid multiplication etc + * when there is only the value '1' in the + * buffer. */ + wvalue=0; /* The 'value' of the window */ + wstart=bits-1; /* The top bit of the window */ + wend=0; /* The bottom bit of the window */ + + if (!BN_to_montgomery(r,BN_value_one(),mont,ctx)) goto err; + for (;;) + { + if (BN_is_bit_set(p,wstart) == 0) + { + if (!start) + { + if (!BN_mod_mul_montgomery(r,r,r,mont,ctx)) + goto err; + } + if (wstart == 0) break; + wstart--; + continue; + } + /* We now have wstart on a 'set' bit, we now need to work out + * how bit a window to do. To do this we need to scan + * forward until the last set bit before the end of the + * window */ + j=wstart; + wvalue=1; + wend=0; + for (i=1; i<window; i++) + { + if (wstart-i < 0) break; + if (BN_is_bit_set(p,wstart-i)) + { + wvalue<<=(i-wend); + wvalue|=1; + wend=i; + } + } + + /* wend is the size of the current window */ + j=wend+1; + /* add the 'bytes above' */ + if (!start) + for (i=0; i<j; i++) + { + if (!BN_mod_mul_montgomery(r,r,r,mont,ctx)) + goto err; + } + + /* wvalue will be an odd number < 2^window */ + if (!BN_mod_mul_montgomery(r,r,&(val[wvalue>>1]),mont,ctx)) + goto err; + + /* move the 'window' down further */ + wstart-=wend+1; + wvalue=0; + start=0; + if (wstart < 0) break; + } + if (!BN_from_montgomery(rr,r,mont,ctx)) goto err; + ret=1; +err: + if ((in_mont == NULL) && (mont != NULL)) BN_MONT_CTX_free(mont); + BN_CTX_end(ctx); + for (i=0; i<ts; i++) + BN_clear_free(&(val[i])); + return(ret); + } + +BN_ULONG BN_mod_word(const BIGNUM *a, BN_ULONG w) + { +#ifndef BN_LLONG + BN_ULONG ret=0; +#else + BN_ULLONG ret=0; +#endif + int i; + + w&=BN_MASK2; + for (i=a->top-1; i>=0; i--) + { +#ifndef BN_LLONG + ret=((ret<<BN_BITS4)|((a->d[i]>>BN_BITS4)&BN_MASK2l))%w; + ret=((ret<<BN_BITS4)|(a->d[i]&BN_MASK2l))%w; +#else + ret=(BN_ULLONG)(((ret<<(BN_ULLONG)BN_BITS2)|a->d[i])% + (BN_ULLONG)w); +#endif + } + return((BN_ULONG)ret); + } + +static int bnrand(int pseudorand, BIGNUM *rnd, int bits, int top, int bottom) + { + unsigned char *buf=NULL; + int ret=0,bit,bytes,mask; + + if (bits == 0) + { + BN_zero(rnd); + return 1; + } + + bytes=(bits+7)/8; + bit=(bits-1)%8; + mask=0xff<<bit; + + buf=(unsigned char *)malloc(bytes); + if (buf == NULL) + { + goto err; + } + + /* make a random number and set the top and bottom bits */ + /* this ignores the pseudorand flag */ + + t_random(buf, bytes); + + if (top) + { + if (bit == 0) + { + buf[0]=1; + buf[1]|=0x80; + } + else + { + buf[0]|=(3<<(bit-1)); + buf[0]&= ~(mask<<1); + } + } + else + { + buf[0]|=(1<<bit); + buf[0]&= ~(mask<<1); + } + if (bottom) /* set bottom bits to whatever odd is */ + buf[bytes-1]|=1; + if (!BN_bin2bn(buf,bytes,rnd)) goto err; + ret=1; +err: + if (buf != NULL) + { + memset(buf,0,bytes); + free(buf); + } + return(ret); + } + +/* BN_pseudo_rand is the same as BN_rand, now. */ + +int BN_pseudo_rand(BIGNUM *rnd, int bits, int top, int bottom) + { + return bnrand(1, rnd, bits, top, bottom); + } + +#define MONT_WORD /* use the faster word-based algorithm */ + +int BN_mod_mul_montgomery(BIGNUM *r, BIGNUM *a, BIGNUM *b, + BN_MONT_CTX *mont, BN_CTX *ctx) + { + BIGNUM *tmp,*tmp2; + int ret=0; + + BN_CTX_start(ctx); + tmp = BN_CTX_get(ctx); + tmp2 = BN_CTX_get(ctx); + if (tmp == NULL || tmp2 == NULL) goto err; + + bn_check_top(tmp); + bn_check_top(tmp2); + + if (a == b) + { + if (!BN_sqr(tmp,a,ctx)) goto err; + } + else + { + if (!BN_mul(tmp,a,b,ctx)) goto err; + } + /* reduce from aRR to aR */ + if (!BN_from_montgomery(r,tmp,mont,ctx)) goto err; + ret=1; +err: + BN_CTX_end(ctx); + return(ret); + } + +int BN_from_montgomery(BIGNUM *ret, BIGNUM *a, BN_MONT_CTX *mont, + BN_CTX *ctx) + { + int retn=0; + +#ifdef MONT_WORD + BIGNUM *n,*r; + BN_ULONG *ap,*np,*rp,n0,v,*nrp; + int al,nl,max,i,x,ri; + + BN_CTX_start(ctx); + if ((r = BN_CTX_get(ctx)) == NULL) goto err; + + if (!BN_copy(r,a)) goto err; + n= &(mont->N); + + ap=a->d; + /* mont->ri is the size of mont->N in bits (rounded up + to the word size) */ + al=ri=mont->ri/BN_BITS2; + + nl=n->top; + if ((al == 0) || (nl == 0)) { r->top=0; return(1); } + + max=(nl+al+1); /* allow for overflow (no?) XXX */ + if (bn_wexpand(r,max) == NULL) goto err; + if (bn_wexpand(ret,max) == NULL) goto err; + + r->neg=a->neg^n->neg; + np=n->d; + rp=r->d; + nrp= &(r->d[nl]); + + /* clear the top words of T */ +#if 1 + for (i=r->top; i<max; i++) /* memset? XXX */ + r->d[i]=0; +#else + memset(&(r->d[r->top]),0,(max-r->top)*sizeof(BN_ULONG)); +#endif + + r->top=max; + n0=mont->n0; + +#ifdef BN_COUNT + printf("word BN_from_montgomery %d * %d\n",nl,nl); +#endif + for (i=0; i<nl; i++) + { +#ifdef __TANDEM + { + long long t1; + long long t2; + long long t3; + t1 = rp[0] * (n0 & 0177777); + t2 = 037777600000l; + t2 = n0 & t2; + t3 = rp[0] & 0177777; + t2 = (t3 * t2) & BN_MASK2; + t1 = t1 + t2; + v=bn_mul_add_words(rp,np,nl,(BN_ULONG) t1); + } +#else + v=bn_mul_add_words(rp,np,nl,(rp[0]*n0)&BN_MASK2); +#endif + nrp++; + rp++; + if (((nrp[-1]+=v)&BN_MASK2) >= v) + continue; + else + { + if (((++nrp[0])&BN_MASK2) != 0) continue; + if (((++nrp[1])&BN_MASK2) != 0) continue; + for (x=2; (((++nrp[x])&BN_MASK2) == 0); x++) ; + } + } + bn_fix_top(r); + + /* mont->ri will be a multiple of the word size */ +#if 0 + BN_rshift(ret,r,mont->ri); +#else + ret->neg = r->neg; + x=ri; + rp=ret->d; + ap= &(r->d[x]); + if (r->top < x) + al=0; + else + al=r->top-x; + ret->top=al; + al-=4; + for (i=0; i<al; i+=4) + { + BN_ULONG t1,t2,t3,t4; + + t1=ap[i+0]; + t2=ap[i+1]; + t3=ap[i+2]; + t4=ap[i+3]; + rp[i+0]=t1; + rp[i+1]=t2; + rp[i+2]=t3; + rp[i+3]=t4; + } + al+=4; + for (; i<al; i++) + rp[i]=ap[i]; +#endif +#else /* !MONT_WORD */ + BIGNUM *t1,*t2; + + BN_CTX_start(ctx); + t1 = BN_CTX_get(ctx); + t2 = BN_CTX_get(ctx); + if (t1 == NULL || t2 == NULL) goto err; + + if (!BN_copy(t1,a)) goto err; + BN_mask_bits(t1,mont->ri); + + if (!BN_mul(t2,t1,&mont->Ni,ctx)) goto err; + BN_mask_bits(t2,mont->ri); + + if (!BN_mul(t1,t2,&mont->N,ctx)) goto err; + if (!BN_add(t2,a,t1)) goto err; + BN_rshift(ret,t2,mont->ri); +#endif /* MONT_WORD */ + + if (BN_ucmp(ret, &(mont->N)) >= 0) + { + BN_usub(ret,ret,&(mont->N)); + } + retn=1; + err: + BN_CTX_end(ctx); + return(retn); + } + +void BN_MONT_CTX_init(BN_MONT_CTX *ctx) + { + ctx->ri=0; + BN_init(&(ctx->RR)); + BN_init(&(ctx->N)); + BN_init(&(ctx->Ni)); + ctx->flags=0; + } + +BN_MONT_CTX *BN_MONT_CTX_new(void) + { + BN_MONT_CTX *ret; + + if ((ret=(BN_MONT_CTX *)malloc(sizeof(BN_MONT_CTX))) == NULL) + return(NULL); + + BN_MONT_CTX_init(ret); + ret->flags=BN_FLG_MALLOCED; + return(ret); + } + +void BN_MONT_CTX_free(BN_MONT_CTX *mont) + { + if(mont == NULL) + return; + + BN_free(&(mont->RR)); + BN_free(&(mont->N)); + BN_free(&(mont->Ni)); + if (mont->flags & BN_FLG_MALLOCED) + free(mont); + } + +int BN_MONT_CTX_set(BN_MONT_CTX *mont, const BIGNUM *mod, BN_CTX *ctx) + { + BIGNUM Ri,*R; + + BN_init(&Ri); + R= &(mont->RR); /* grab RR as a temp */ + BN_copy(&(mont->N),mod); /* Set N */ + +#ifdef MONT_WORD + { + BIGNUM tmod; + BN_ULONG buf[2]; + + mont->ri=(BN_num_bits(mod)+(BN_BITS2-1))/BN_BITS2*BN_BITS2; + BN_zero(R); + BN_set_bit(R,BN_BITS2); /* R */ + + buf[0]=mod->d[0]; /* tmod = N mod word size */ + buf[1]=0; + tmod.d=buf; + tmod.top=1; + tmod.dmax=2; + tmod.neg=mod->neg; + /* Ri = R^-1 mod N*/ + if ((BN_mod_inverse(&Ri,R,&tmod,ctx)) == NULL) + goto err; + BN_lshift(&Ri,&Ri,BN_BITS2); /* R*Ri */ + if (!BN_is_zero(&Ri)) + BN_sub_word(&Ri,1); + else /* if N mod word size == 1 */ + BN_set_word(&Ri,BN_MASK2); /* Ri-- (mod word size) */ + BN_div(&Ri,NULL,&Ri,&tmod,ctx); /* Ni = (R*Ri-1)/N, + * keep only least significant word: */ + mont->n0=Ri.d[0]; + BN_free(&Ri); + } +#else /* !MONT_WORD */ + { /* bignum version */ + mont->ri=BN_num_bits(mod); + BN_zero(R); + BN_set_bit(R,mont->ri); /* R = 2^ri */ + /* Ri = R^-1 mod N*/ + if ((BN_mod_inverse(&Ri,R,mod,ctx)) == NULL) + goto err; + BN_lshift(&Ri,&Ri,mont->ri); /* R*Ri */ + BN_sub_word(&Ri,1); + /* Ni = (R*Ri-1) / N */ + BN_div(&(mont->Ni),NULL,&Ri,mod,ctx); + BN_free(&Ri); + } +#endif + + /* setup RR for conversions */ + BN_zero(&(mont->RR)); + BN_set_bit(&(mont->RR),mont->ri*2); + BN_mod(&(mont->RR),&(mont->RR),&(mont->N),ctx); + + return(1); +err: + return(0); + } + +BIGNUM *BN_value_one(void) + { + static BN_ULONG data_one=1L; + static BIGNUM const_one={&data_one,1,1,0}; + + return(&const_one); + } + +/* solves ax == 1 (mod n) */ +BIGNUM *BN_mod_inverse(BIGNUM *in, BIGNUM *a, const BIGNUM *n, BN_CTX *ctx) + { + BIGNUM *A,*B,*X,*Y,*M,*D,*R=NULL; + BIGNUM *T,*ret=NULL; + int sign; + + bn_check_top(a); + bn_check_top(n); + + BN_CTX_start(ctx); + A = BN_CTX_get(ctx); + B = BN_CTX_get(ctx); + X = BN_CTX_get(ctx); + D = BN_CTX_get(ctx); + M = BN_CTX_get(ctx); + Y = BN_CTX_get(ctx); + if (Y == NULL) goto err; + + if (in == NULL) + R=BN_new(); + else + R=in; + if (R == NULL) goto err; + + BN_zero(X); + BN_one(Y); + if (BN_copy(A,a) == NULL) goto err; + if (BN_copy(B,n) == NULL) goto err; + sign=1; + + while (!BN_is_zero(B)) + { + if (!BN_div(D,M,A,B,ctx)) goto err; + T=A; + A=B; + B=M; + /* T has a struct, M does not */ + + if (!BN_mul(T,D,X,ctx)) goto err; + if (!BN_add(T,T,Y)) goto err; + M=Y; + Y=X; + X=T; + sign= -sign; + } + if (sign < 0) + { + if (!BN_sub(Y,n,Y)) goto err; + } + + if (BN_is_one(A)) + { if (!BN_mod(R,Y,n,ctx)) goto err; } + else + { + goto err; + } + ret=R; +err: + if ((ret == NULL) && (in == NULL)) BN_free(R); + BN_CTX_end(ctx); + return(ret); + } + +int BN_set_bit(BIGNUM *a, int n) + { + int i,j,k; + + i=n/BN_BITS2; + j=n%BN_BITS2; + if (a->top <= i) + { + if (bn_wexpand(a,i+1) == NULL) return(0); + for(k=a->top; k<i+1; k++) + a->d[k]=0; + a->top=i+1; + } + + a->d[i]|=(((BN_ULONG)1)<<j); + return(1); + } + diff --git a/package/network/services/ead/src/tinysrp/t_conv.c b/package/network/services/ead/src/tinysrp/t_conv.c new file mode 100644 index 0000000000..d3fe246c41 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_conv.c @@ -0,0 +1,226 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +/*#define _POSIX_SOURCE*/ +#include <stdio.h> +#include "t_defines.h" + +static int +hexDigitToInt(c) + char c; +{ + if(c >= '0' && c <= '9') + return c - '0'; + else if(c >= 'a' && c <= 'f') + return c - 'a' + 10; + else if(c >= 'A' && c <= 'F') + return c - 'A' + 10; + else + return 0; +} + +/* + * Convert a hex string to a string of bytes; return size of dst + */ +_TYPE( int ) +t_fromhex(dst, src) + register char *dst, *src; +{ + register char *chp = dst; + register unsigned size = strlen(src); + + /* FIXME: handle whitespace and non-hex digits by setting size and src + appropriately. */ + + if(size % 2 == 1) { + *chp++ = hexDigitToInt(*src++); + --size; + } + while(size > 0) { + *chp++ = (hexDigitToInt(*src) << 4) | hexDigitToInt(*(src + 1)); + src += 2; + size -= 2; + } + return chp - dst; +} + +/* + * Convert a string of bytes to their hex representation + */ +_TYPE( char * ) +t_tohex(dst, src, size) + register char *dst, *src; + register unsigned size; +{ + int notleading = 0; + + register char *chp = dst; + if (size != 0) do { + if(notleading || *src != '\0') { + notleading = 1; + sprintf(chp, "%.2x", * (unsigned char *) src); + chp += 2; + } + ++src; + } while (--size != 0); + return dst; +} + +static char b64table[] = + "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz./"; + +/* + * Convert a base64 string into raw byte array representation. + */ +_TYPE( int ) +t_fromb64(dst, src) + register char *dst, *src; +{ + unsigned char *a; + char *loc; + int i, j; + unsigned int size; + + while(*src && (*src == ' ' || *src == '\t' || *src == '\n')) + ++src; + size = strlen(src); + + a = malloc((size + 1) * sizeof(unsigned char)); + if(a == (unsigned char *) 0) + return -1; + + i = 0; + while(i < size) { + loc = strchr(b64table, src[i]); + if(loc == (char *) 0) + break; + else + a[i] = loc - b64table; + ++i; + } + size = i; + + i = size - 1; + j = size; + while(1) { + a[j] = a[i]; + if(--i < 0) + break; + a[j] |= (a[i] & 3) << 6; + --j; + a[j] = (unsigned char) ((a[i] & 0x3c) >> 2); + if(--i < 0) + break; + a[j] |= (a[i] & 0xf) << 4; + --j; + a[j] = (unsigned char) ((a[i] & 0x30) >> 4); + if(--i < 0) + break; + a[j] |= (a[i] << 2); + + a[--j] = 0; + if(--i < 0) + break; + } + + while(a[j] == 0 && j <= size) + ++j; + + memcpy(dst, a + j, size - j + 1); + free(a); + return size - j + 1; +} + +/* + * Convert a raw byte string into a null-terminated base64 ASCII string. + */ +_TYPE( char * ) +t_tob64(dst, src, size) + register char *dst, *src; + register unsigned size; +{ + int c, pos = size % 3; + unsigned char b0 = 0, b1 = 0, b2 = 0, notleading = 0; + char *olddst = dst; + + switch(pos) { + case 1: + b2 = src[0]; + break; + case 2: + b1 = src[0]; + b2 = src[1]; + break; + } + + while(1) { + c = (b0 & 0xfc) >> 2; + if(notleading || c != 0) { + *dst++ = b64table[c]; + notleading = 1; + } + c = ((b0 & 3) << 4) | ((b1 & 0xf0) >> 4); + if(notleading || c != 0) { + *dst++ = b64table[c]; + notleading = 1; + } + c = ((b1 & 0xf) << 2) | ((b2 & 0xc0) >> 6); + if(notleading || c != 0) { + *dst++ = b64table[c]; + notleading = 1; + } + c = b2 & 0x3f; + if(notleading || c != 0) { + *dst++ = b64table[c]; + notleading = 1; + } + if(pos >= size) + break; + else { + b0 = src[pos++]; + b1 = src[pos++]; + b2 = src[pos++]; + } + } + + *dst++ = '\0'; + return olddst; +} diff --git a/package/network/services/ead/src/tinysrp/t_defines.h b/package/network/services/ead/src/tinysrp/t_defines.h new file mode 100644 index 0000000000..4128093f60 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_defines.h @@ -0,0 +1,169 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#ifndef T_DEFINES_H +#define T_DEFINES_H + +#ifndef P +#if defined(__STDC__) || defined(__cplusplus) +#define P(x) x +#else +#define P(x) () +#endif +#endif + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif /* HAVE_CONFIG_H */ + +#ifndef _DLLDECL +#define _DLLDECL + +#ifdef MSVC15 /* MSVC1.5 support for 16 bit apps */ +#define _MSVC15EXPORT _export +#define _MSVC20EXPORT +#define _DLLAPI _export _pascal +#define _TYPE(a) a _MSVC15EXPORT +#define DLLEXPORT 1 + +#elif MSVC20 +#define _MSVC15EXPORT +#define _MSVC20EXPORT _declspec(dllexport) +#define _DLLAPI +#define _TYPE(a) _MSVC20EXPORT a +#define DLLEXPORT 1 + +#else /* Default, non-dll. Use this for Unix or DOS */ +#define _MSVC15DEXPORT +#define _MSVC20EXPORT +#define _DLLAPI +#define _TYPE(a) a +#endif +#endif + +#if STDC_HEADERS +#include <stdlib.h> +#include <string.h> +#else /* not STDC_HEADERS */ +#ifndef HAVE_STRCHR +#define strchr index +#define strrchr rindex +#endif +char *strchr(), *strrchr(), *strtok(); +#ifndef HAVE_MEMCPY +#define memcpy(d, s, n) bcopy((s), (d), (n)) +#endif +#endif /* not STDC_HEADERS */ + +#include <sys/types.h> + +#if TIME_WITH_SYS_TIME +#include <sys/time.h> +#include <time.h> +#else /* not TIME_WITH_SYS_TIME */ +#if HAVE_SYS_TIME_H +#include <sys/time.h> +#else +#include <time.h> +#endif +#endif /* not TIME_WITH_SYS_TIME */ + +#if HAVE_TERMIOS_H +#include <termios.h> +#define STTY(fd, termio) tcsetattr(fd, TCSANOW, termio) +#define GTTY(fd, termio) tcgetattr(fd, termio) +#define TERMIO struct termios +#define USE_TERMIOS +#elif HAVE_TERMIO_H +#include <sys/ioctl.h> +#include <termio.h> +#define STTY(fd, termio) ioctl(fd, TCSETA, termio) +#define GTTY(fd, termio) ioctl(fd, TCGETA, termio) +#define TEMRIO struct termio +#define USE_TERMIO +#elif HAVE_SGTTY_H +#include <sgtty.h> +#define STTY(fd, termio) stty(fd, termio) +#define GTTY(fd, termio) gtty(fd, termio) +#define TERMIO struct sgttyb +#define USE_SGTTY +#endif + +#ifdef USE_FTIME +#include <sys/timeb.h> +#endif + +#ifndef MATH_PRIV +typedef void * BigInteger; +#endif + +_TYPE( BigInteger ) BigIntegerFromInt P((unsigned int number)); +_TYPE( BigInteger ) BigIntegerFromBytes P((unsigned char * bytes, int length)); +_TYPE( int ) BigIntegerToBytes P((BigInteger src, unsigned char * dest)); +_TYPE( int ) BigIntegerBitLen P((BigInteger b)); +_TYPE( int ) BigIntegerCmp P((BigInteger c1, BigInteger c2)); +_TYPE( int ) BigIntegerCmpInt P((BigInteger c1, unsigned int c2)); +_TYPE( void ) BigIntegerLShift P((BigInteger result, BigInteger x, + unsigned int bits)); +_TYPE( void ) BigIntegerAdd P((BigInteger result, BigInteger a1, BigInteger a2)); +_TYPE( void ) BigIntegerAddInt P((BigInteger result, + BigInteger a1, unsigned int a2)); +_TYPE( void ) BigIntegerSub P((BigInteger result, BigInteger s1, BigInteger s2)); +_TYPE( void ) BigIntegerSubInt P((BigInteger result, + BigInteger s1, unsigned int s2)); +/* For BigIntegerMul{,Int}: result != m1, m2 */ +_TYPE( void ) BigIntegerMul P((BigInteger result, BigInteger m1, BigInteger m2)); +_TYPE( void ) BigIntegerMulInt P((BigInteger result, + BigInteger m1, unsigned int m2)); +_TYPE( void ) BigIntegerDivInt P((BigInteger result, + BigInteger d, unsigned int m)); +_TYPE( void ) BigIntegerMod P((BigInteger result, BigInteger d, BigInteger m)); +_TYPE( unsigned int ) BigIntegerModInt P((BigInteger d, unsigned int m)); +_TYPE( void ) BigIntegerModMul P((BigInteger result, + BigInteger m1, BigInteger m2, BigInteger m)); +_TYPE( void ) BigIntegerModExp P((BigInteger result, BigInteger base, + BigInteger expt, BigInteger modulus)); +_TYPE( void ) BigIntegerModExpInt P((BigInteger result, BigInteger base, + unsigned int expt, BigInteger modulus)); +_TYPE( int ) BigIntegerCheckPrime P((BigInteger n)); +_TYPE( void ) BigIntegerFree P((BigInteger b)); + +#endif diff --git a/package/network/services/ead/src/tinysrp/t_getconf.c b/package/network/services/ead/src/tinysrp/t_getconf.c new file mode 100644 index 0000000000..db6de6171f --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_getconf.c @@ -0,0 +1,118 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> + +#include "t_defines.h" +#include "t_pwd.h" +#include "t_read.h" + +/* Master builtin parameter storage object. The default that tphrase +uses is the last one. */ + +static struct pre_struct { + struct t_preconf preconf; + int state; /* 0 == uninitialized/first time */ + unsigned char modbuf[MAXPARAMLEN]; + unsigned char genbuf[MAXPARAMLEN]; +} pre_params[] = { + { { "2iQzj1CagQc/5ctbuJYLWlhtAsPHc7xWVyCPAKFRLWKADpASkqe9djWPFWTNTdeJtL8nAhImCn3Sr/IAdQ1FrGw0WvQUstPx3FO9KNcXOwisOQ1VlL.gheAHYfbYyBaxXL.NcJx9TUwgWDT0hRzFzqSrdGGTN3FgSTA1v4QnHtEygNj3eZ.u0MThqWUaDiP87nqha7XnT66bkTCkQ8.7T8L4KZjIImrNrUftedTTBi.WCi.zlrBxDuOM0da0JbUkQlXqvp0yvJAPpC11nxmmZOAbQOywZGmu9nhZNuwTlxjfIro0FOdthaDTuZRL9VL7MRPUDo/DQEyW.d4H.UIlzp", + "2", + NULL }, 0 }, + { { "dUyyhxav9tgnyIg65wHxkzkb7VIPh4o0lkwfOKiPp4rVJrzLRYVBtb76gKlaO7ef5LYGEw3G.4E0jbMxcYBetDy2YdpiP/3GWJInoBbvYHIRO9uBuxgsFKTKWu7RnR7yTau/IrFTdQ4LY/q.AvoCzMxV0PKvD9Odso/LFIItn8PbTov3VMn/ZEH2SqhtpBUkWtmcIkEflhX/YY/fkBKfBbe27/zUaKUUZEUYZ2H2nlCL60.JIPeZJSzsu/xHDVcx", + "2", + NULL }, 0 }, + { { "3NUKQ2Re4P5BEK0TLg2dX3gETNNNECPoe92h4OVMaDn3Xo/0QdjgG/EvM.hiVV1BdIGklSI14HA38Mpe5k04juR5/EXMU0r1WtsLhNXwKBlf2zEfoOh0zVmDvqInpU695f29Iy7sNW3U5RIogcs740oUp2Kdv5wuITwnIx84cnO.e467/IV1lPnvMCr0pd1dgS0a.RV5eBJr03Q65Xy61R", + "2", + NULL }, 0 }, + { { "F//////////oG/QeY5emZJ4ncABWDmSqIa2JWYAPynq0Wk.fZiJco9HIWXvZZG4tU.L6RFDEaCRC2iARV9V53TFuJLjRL72HUI5jNPYNdx6z4n2wQOtxMiB/rosz0QtxUuuQ/jQYP.bhfya4NnB7.P9A6PHxEPJWV//////////", + "5", + "oakley prime 2" }, 0 }, + { { "Ewl2hcjiutMd3Fu2lgFnUXWSc67TVyy2vwYCKoS9MLsrdJVT9RgWTCuEqWJrfB6uE3LsE9GkOlaZabS7M29sj5TnzUqOLJMjiwEzArfiLr9WbMRANlF68N5AVLcPWvNx6Zjl3m5Scp0BzJBz9TkgfhzKJZ.WtP3Mv/67I/0wmRZ", + "2", + NULL }, 0 }, +}; + +_TYPE( int ) +t_getprecount() +{ + return (sizeof(pre_params) / sizeof(struct pre_struct)); +} + +static struct t_confent sysconf; + +/* id is index origin 1 */ + +_TYPE( struct t_confent * ) +gettcid +(id) + int id; +{ + struct t_preconf *tcp; + + if (id <= 0 || id > t_getprecount()) { + return NULL; + } + tcp = t_getpreparam(id - 1); + sysconf.index = id; + sysconf.modulus = tcp->modulus; + sysconf.generator = tcp->generator; + + return &sysconf; +} + +_TYPE( struct t_preconf * ) +t_getpreparam(idx) + int idx; +{ + if(pre_params[idx].state == 0) { + /* Wire up storage */ + pre_params[idx].preconf.modulus.data = pre_params[idx].modbuf; + pre_params[idx].preconf.generator.data = pre_params[idx].genbuf; + + /* Convert from b64 to t_num */ + pre_params[idx].preconf.modulus.len = t_fromb64(pre_params[idx].preconf.modulus.data, pre_params[idx].preconf.mod_b64); + pre_params[idx].preconf.generator.len = t_fromb64(pre_params[idx].preconf.generator.data, pre_params[idx].preconf.gen_b64); + + pre_params[idx].state = 1; + } + return &(pre_params[idx].preconf); +} diff --git a/package/network/services/ead/src/tinysrp/t_getpass.c b/package/network/services/ead/src/tinysrp/t_getpass.c new file mode 100644 index 0000000000..6ae7fca4de --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_getpass.c @@ -0,0 +1,191 @@ +/* + * Copyright 1990 - 1995, Julianne Frances Haugh + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Julianne F. Haugh nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY JULIE HAUGH AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL JULIE HAUGH OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include "t_defines.h" +#ifdef _WIN32 +#include <windows.h> +#include <io.h> +#endif /* _WIN32 */ +#ifdef HAVE_UNISTD_H +#include <unistd.h> +#endif /* HAVE_UNISTD_H */ +#include <signal.h> +#include <stdio.h> + +static int sig_caught; +#ifdef HAVE_SIGACTION +static struct sigaction sigact; +#endif + +/*ARGSUSED*/ +static RETSIGTYPE +sig_catch (sig) +int sig; +{ + sig_caught = 1; +} + +_TYPE( int ) +t_getpass (buf, maxlen, prompt) + char *buf; + unsigned maxlen; + const char *prompt; +{ + char *cp; +#ifdef _WIN32 + HANDLE handle = (HANDLE) _get_osfhandle(_fileno(stdin)); + DWORD mode; + + GetConsoleMode( handle, &mode ); + SetConsoleMode( handle, mode & ~ENABLE_ECHO_INPUT ); + + if(fputs(prompt, stdout) == EOF || + fgets(buf, maxlen, stdin) == NULL) { + SetConsoleMode(handle,mode); + return -1; + } + cp = buf + strlen(buf) - 1; + if ( *cp == 0x0a ) + *cp = '\0'; + printf("\n"); + SetConsoleMode(handle,mode); +#else + FILE *fp; + int tty_opened = 0; + +#ifdef HAVE_SIGACTION + struct sigaction old_sigact; +#else + RETSIGTYPE (*old_signal)(); +#endif + TERMIO new_modes; + TERMIO old_modes; + + /* + * set a flag so the SIGINT signal can be re-sent if it + * is caught + */ + + sig_caught = 0; + + /* + * if /dev/tty can't be opened, getpass() needs to read + * from stdin instead. + */ + + if ((fp = fopen ("/dev/tty", "r")) == 0) { + fp = stdin; + setbuf (fp, (char *) 0); + } else { + tty_opened = 1; + } + + /* + * the current tty modes must be saved so they can be + * restored later on. echo will be turned off, except + * for the newline character (BSD has to punt on this) + */ + + if (GTTY (fileno (fp), &new_modes)) + return -1; + + old_modes = new_modes; + +#ifdef HAVE_SIGACTION + sigact.sa_handler = sig_catch; + (void) sigaction (SIGINT, &sigact, &old_sigact); +#else + old_signal = signal (SIGINT, sig_catch); +#endif + +#ifdef USE_SGTTY + new_modes.sg_flags &= ~ECHO; +#else + new_modes.c_iflag &= ~IGNCR; + new_modes.c_iflag |= ICRNL; + new_modes.c_oflag |= OPOST|ONLCR; + new_modes.c_lflag &= ~(ECHO|ECHOE|ECHOK); + new_modes.c_lflag |= ICANON|ECHONL; +#endif + + if (STTY (fileno (fp), &new_modes)) + goto out; + + /* + * the prompt is output, and the response read without + * echoing. the trailing newline must be removed. if + * the fgets() returns an error, a NULL pointer is + * returned. + */ + + if (fputs (prompt, stdout) == EOF) + goto out; + + (void) fflush (stdout); + + if (fgets (buf, maxlen, fp) == buf) { + if ((cp = strchr (buf, '\n'))) + *cp = '\0'; + else + buf[maxlen - 1] = '\0'; + +#ifdef USE_SGTTY + putc ('\n', stdout); +#endif + } + else buf[0] = '\0'; +out: + /* + * the old SIGINT handler is restored after the tty + * modes. then /dev/tty is closed if it was opened in + * the beginning. finally, if a signal was caught it + * is sent to this process for normal processing. + */ + + if (STTY (fileno (fp), &old_modes)) + { memset (buf, 0, maxlen); return -1; } + +#ifdef HAVE_SIGACTION + (void) sigaction (SIGINT, &old_sigact, NULL); +#else + (void) signal (SIGINT, old_signal); +#endif + + if (tty_opened) + (void) fclose (fp); + + if (sig_caught) { + kill (getpid (), SIGINT); + memset (buf, 0, maxlen); + return -1; + } +#endif + + return 0; +} diff --git a/package/network/services/ead/src/tinysrp/t_math.c b/package/network/services/ead/src/tinysrp/t_math.c new file mode 100644 index 0000000000..20161a0112 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_math.c @@ -0,0 +1,177 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> +#include <sys/types.h> + +#include "config.h" + +#include "bn.h" +typedef BIGNUM * BigInteger; +#define MATH_PRIV + +#include "t_defines.h" +#include "t_pwd.h" + +/* Math library interface stubs */ + +BigInteger +BigIntegerFromInt(n) + unsigned int n; +{ + BIGNUM * a = BN_new(); + BN_set_word(a, n); + return a; +} + +BigInteger +BigIntegerFromBytes(bytes, length) + unsigned char * bytes; + int length; +{ + BIGNUM * a = BN_new(); + BN_bin2bn(bytes, length, a); + return a; +} + +int +BigIntegerToBytes(src, dest) + BigInteger src; + unsigned char * dest; +{ + return BN_bn2bin(src, dest); +} + +int +BigIntegerCmp(c1, c2) + BigInteger c1, c2; +{ + return BN_cmp(c1, c2); +} + +int +BigIntegerCmpInt(c1, c2) + BigInteger c1; + unsigned int c2; +{ + BIGNUM * a = BN_new(); + int rv; + BN_set_word(a, c2); + rv = BN_cmp(c1, a); + BN_free(a); + return rv; +} + +void +BigIntegerAdd(result, a1, a2) + BigInteger result, a1, a2; +{ + BN_add(result, a1, a2); +} + +void +BigIntegerAddInt(result, a1, a2) + BigInteger result, a1; + unsigned int a2; +{ + BIGNUM * a = BN_new(); + BN_set_word(a, a2); + BN_add(result, a1, a); + BN_free(a); +} + +void +BigIntegerSub(result, s1, s2) + BigInteger result, s1, s2; +{ + BN_sub(result, s1, s2); +} + +void +BigIntegerMulInt(result, m1, m2) + BigInteger result, m1; + unsigned int m2; +{ + BN_CTX * ctx = BN_CTX_new(); + BIGNUM * m = BN_new(); + BN_set_word(m, m2); + BN_mul(result, m1, m, ctx); + BN_CTX_free(ctx); +} + +void +BigIntegerModMul(r, m1, m2, modulus) + BigInteger r, m1, m2, modulus; +{ + BN_CTX * ctx = BN_CTX_new(); + BN_mod_mul(r, m1, m2, modulus, ctx); + BN_CTX_free(ctx); +} + +void +BigIntegerModExp(r, b, e, m) + BigInteger r, b, e, m; +{ + BN_CTX * ctx = BN_CTX_new(); + BN_mod_exp(r, b, e, m, ctx); + BN_CTX_free(ctx); +} + +void +BigIntegerModExpInt(r, b, e, m) + BigInteger r, b; + unsigned int e; + BigInteger m; +{ + BN_CTX * ctx = BN_CTX_new(); + BIGNUM * p = BN_new(); + BN_set_word(p, e); + BN_mod_exp(r, b, p, m, ctx); + BN_free(p); + BN_CTX_free(ctx); +} + +void +BigIntegerFree(b) + BigInteger b; +{ + BN_free(b); +} diff --git a/package/network/services/ead/src/tinysrp/t_misc.c b/package/network/services/ead/src/tinysrp/t_misc.c new file mode 100644 index 0000000000..a23986f90f --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_misc.c @@ -0,0 +1,338 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include "t_defines.h" + +#ifdef HAVE_UNISTD_H +#include <unistd.h> +#endif /* HAVE_UNISTD_H */ + +#include <stdio.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <fcntl.h> + +#include "t_sha.h" + +#ifndef NULL +#define NULL 0 +#endif + +static unsigned char randpool[SHA_DIGESTSIZE], randout[SHA_DIGESTSIZE]; +static unsigned long randcnt = 0; +static unsigned int outpos = 0; +SHA1_CTX randctxt; + +/* + * t_envhash - Generate a 160-bit SHA hash of the environment + * + * This routine performs an SHA hash of all the "name=value" pairs + * in the environment concatenated together and dumps them in the + * output. While it is true that anyone on the system can see + * your environment, someone not on the system will have a very + * difficult time guessing it, especially since some systems play + * tricks with variable ordering and sometimes define quirky + * environment variables like $WINDOWID or $_. + */ +extern char ** environ; + +static void +t_envhash(out) + unsigned char * out; +{ + char ** ptr; + char ebuf[256]; + SHA1_CTX ctxt; + + SHA1Init(&ctxt); + for(ptr = environ; *ptr; ++ptr) { + strncpy(ebuf, *ptr, 255); + ebuf[255] = '\0'; + SHA1Update(&ctxt, ebuf, strlen(ebuf)); + } + SHA1Final(out, &ctxt); +} + +/* + * t_fshash - Generate a 160-bit SHA hash from the file system + * + * This routine climbs up the directory tree from the current + * directory, running stat() on each directory until it hits the + * root directory. This information is sensitive to the last + * access/modification times of all the directories above you, + * so someone who lists one of those directories injects some + * entropy into the system. Obviously, this hash is very sensitive + * to your current directory when the program is run. + * + * For good measure, it also performs an fstat on the standard input, + * usually your tty, throws that into the buffer, creates a file in + * /tmp (the inode is unpredictable on a busy system), and runs stat() + * on that before deleting it. + * + * The entire buffer is run once through SHA to obtain the final result. + */ +static void +t_fshash(out) + unsigned char * out; +{ + char dotpath[128]; + struct stat st; + SHA1_CTX ctxt; + int i, pinode; + dev_t pdev; + + SHA1Init(&ctxt); + if(stat(".", &st) >= 0) { + SHA1Update(&ctxt, (unsigned char *) &st, sizeof(st)); + pinode = st.st_ino; + pdev = st.st_dev; + strcpy(dotpath, ".."); + for(i = 0; i < 40; ++i) { + if(stat(dotpath, &st) < 0) + break; + if(st.st_ino == pinode && st.st_dev == pdev) + break; + SHA1Update(&ctxt, (unsigned char *) &st, sizeof(st)); + pinode = st.st_ino; + pdev = st.st_dev; + strcat(dotpath, "/.."); + } + } + + if(fstat(0, &st) >= 0) + SHA1Update(&ctxt, (unsigned char *) &st, sizeof(st)); + + sprintf(dotpath, "/tmp/rnd.%d", getpid()); + if(creat(dotpath, 0600) >= 0 && stat(dotpath, &st) >= 0) + SHA1Update(&ctxt, (unsigned char *) &st, sizeof(st)); + unlink(dotpath); + + SHA1Final(out, &ctxt); +} + +/* + * Generate a high-entropy seed for the strong random number generator. + * This uses a wide variety of quickly gathered and somewhat unpredictable + * system information. The 'preseed' structure is assembled from: + * + * The system time in seconds + * The system time in microseconds + * The current process ID + * The parent process ID + * A hash of the user's environment + * A hash gathered from the file system + * Input from a random device, if available + * Timings of system interrupts + * + * The entire structure (60 bytes on most systems) is fed to SHA to produce + * a 160-bit seed for the strong random number generator. It is believed + * that in the worst case (on a quiet system with no random device versus + * an attacker who has access to the system already), the seed contains at + * least about 80 bits of entropy. Versus an attacker who does not have + * access to the system, the entropy should be slightly over 128 bits. + */ +static char initialized = 0; + +static struct { + unsigned int trand1; + time_t sec; + time_t usec; + short pid; + short ppid; + unsigned char envh[SHA_DIGESTSIZE]; + unsigned char fsh[SHA_DIGESTSIZE]; + unsigned char devrand[20]; + unsigned int trand2; +} preseed; + +unsigned long raw_truerand(); + +void +t_initrand() +{ + SHA1_CTX ctxt; +#ifdef USE_FTIME + struct timeb t; +#else + struct timeval t; +#endif + int i, r=0; + + if(initialized) + return; + + initialized = 1; + + i = open("/dev/urandom", O_RDONLY); + if(i > 0) { + r += read(i, preseed.devrand, sizeof(preseed.devrand)); + close(i); + } + + /* Resort to truerand only if desperate for some Real entropy */ + if(r == 0) + preseed.trand1 = raw_truerand(); + +#ifdef USE_FTIME + ftime(&t); +#else + gettimeofday(&t, NULL); +#endif + +#ifdef USE_FTIME + preseed.sec = t.time; + preseed.usec = t.millitm; +#else + preseed.sec = t.tv_sec; + preseed.usec = t.tv_usec; +#endif + preseed.pid = getpid(); + preseed.ppid = getppid(); + t_envhash(preseed.envh); + t_fshash(preseed.fsh); + + if(r == 0) + preseed.trand2 = raw_truerand(); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, (unsigned char *) &preseed, sizeof(preseed)); + SHA1Final(randpool, &ctxt); + outpos = 0; + memset((unsigned char *) &preseed, 0, sizeof(preseed)); + memset((unsigned char *) &ctxt, 0, sizeof(ctxt)); +} + +#define NUM_RANDOMS 12 + +/* + * The strong random number generator. This uses a 160-bit seed + * and uses SHA-1 in a feedback configuration to generate successive + * outputs. If S[0] is set to the initial seed, then: + * + * S[i+1] = SHA-1(i || S[i]) + * A[i] = SHA-1(S[i]) + * + * where the A[i] are the output blocks starting with i=0. + * Each cycle generates 20 bytes of new output. + */ +_TYPE( void ) +t_random(data, size) + unsigned char * data; + unsigned size; +{ + if(!initialized) + t_initrand(); + + if(size <= 0) /* t_random(NULL, 0) forces seed initialization */ + return; + + while(size > outpos) { + if(outpos > 0) { + memcpy(data, randout + (sizeof(randout) - outpos), outpos); + data += outpos; + size -= outpos; + } + + /* Recycle */ + SHA1Init(&randctxt); + SHA1Update(&randctxt, randpool, sizeof(randpool)); + SHA1Final(randout, &randctxt); + SHA1Init(&randctxt); + SHA1Update(&randctxt, (unsigned char *) &randcnt, sizeof(randcnt)); + SHA1Update(&randctxt, randpool, sizeof(randpool)); + SHA1Final(randpool, &randctxt); + ++randcnt; + outpos = sizeof(randout); + } + + if(size > 0) { + memcpy(data, randout + (sizeof(randout) - outpos), size); + outpos -= size; + } +} + +/* + * The interleaved session-key hash. This separates the even and the odd + * bytes of the input (ignoring the first byte if the input length is odd), + * hashes them separately, and re-interleaves the two outputs to form a + * single 320-bit value. + */ +_TYPE( unsigned char * ) +t_sessionkey(key, sk, sklen) + unsigned char * key; + unsigned char * sk; + unsigned sklen; +{ + unsigned i, klen; + unsigned char * hbuf; + unsigned char hout[SHA_DIGESTSIZE]; + SHA1_CTX ctxt; + + while(sklen > 0 && *sk == 0) { /* Skip leading 0's */ + --sklen; + ++sk; + } + + klen = sklen / 2; + if((hbuf = malloc(klen * sizeof(char))) == 0) + return 0; + + for(i = 0; i < klen; ++i) + hbuf[i] = sk[sklen - 2 * i - 1]; + SHA1Init(&ctxt); + SHA1Update(&ctxt, hbuf, klen); + SHA1Final(hout, &ctxt); + for(i = 0; i < sizeof(hout); ++i) + key[2 * i] = hout[i]; + + for(i = 0; i < klen; ++i) + hbuf[i] = sk[sklen - 2 * i - 2]; + SHA1Init(&ctxt); + SHA1Update(&ctxt, hbuf, klen); + SHA1Final(hout, &ctxt); + for(i = 0; i < sizeof(hout); ++i) + key[2 * i + 1] = hout[i]; + + memset(hout, 0, sizeof(hout)); + memset(hbuf, 0, klen); + free(hbuf); + return key; +} diff --git a/package/network/services/ead/src/tinysrp/t_pw.c b/package/network/services/ead/src/tinysrp/t_pw.c new file mode 100644 index 0000000000..18e929bb79 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_pw.c @@ -0,0 +1,262 @@ +/* + * Copyright (c) 1997-2000 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include "t_defines.h" + +#ifdef HAVE_UNISTD_H +#include <unistd.h> +#endif /* HAVE_UNISTD_H */ + +#include <stdio.h> +#include <sys/types.h> +#include <sys/stat.h> +#ifdef USE_HOMEDIR +#include <pwd.h> +#endif +#ifdef WIN32 +#include <io.h> +#endif + +#include "t_pwd.h" +#include "t_read.h" +#include "t_sha.h" +#include "t_server.h" + +static struct t_pw * syspw = NULL; +static struct t_passwd tpass; + +_TYPE( struct t_server * ) +t_serveropen(username) + const char * username; +{ + struct t_passwd * p; + p = gettpnam(username); + if(p == NULL) { + return NULL; + } else { + return t_serveropenraw(&p->tp, &p->tc); + } +} + + +/* t_openpw(NULL) is deprecated - use settpent()/gettpnam() instead */ + +_TYPE( struct t_pw * ) +t_openpw(fp) + FILE * fp; +{ + struct t_pw * tpw; + char close_flag = 0; + + if(fp == NULL) { /* Deprecated */ + if((fp = fopen(DEFAULT_PASSWD, "r")) == NULL) + return NULL; + close_flag = 1; + } + else + close_flag = 0; + + if((tpw = malloc(sizeof(struct t_pw))) == NULL) + return NULL; + tpw->instream = fp; + tpw->close_on_exit = close_flag; + tpw->state = FILE_ONLY; + + return tpw; +} + +_TYPE( struct t_pw * ) +t_openpwbyname(pwname) + const char * pwname; +{ + FILE * fp; + struct t_pw * t; + + if(pwname == NULL) /* Deprecated */ + return t_openpw(NULL); + + if((fp = fopen(pwname, "r")) == NULL) + return NULL; + + t = t_openpw(fp); + t->close_on_exit = 1; + return t; +} + +_TYPE( void ) +t_closepw(tpw) + struct t_pw * tpw; +{ + if(tpw->close_on_exit) + fclose(tpw->instream); + free(tpw); +} + +_TYPE( void ) +t_rewindpw(tpw) + struct t_pw * tpw; +{ +#ifdef ENABLE_YP + if(tpw->state == IN_NIS) + tpw->state = FILE_NIS; +#endif + rewind(tpw->instream); +} + +#ifdef ENABLE_YP +static void +savepwent(tpw, pwent) + struct t_pw * tpw; + struct t_pwent *pwent; +{ + tpw->pebuf.name = tpw->userbuf; + tpw->pebuf.password.data = tpw->pwbuf; + tpw->pebuf.salt.data = tpw->saltbuf; + strcpy(tpw->pebuf.name, pwent->name); + tpw->pebuf.password.len = pwent->password.len; + memcpy(tpw->pebuf.password.data, pwent->password.data, pwent->password.len); + tpw->pebuf.salt.len = pwent->salt.len; + memcpy(tpw->pebuf.salt.data, pwent->salt.data, pwent->salt.len); + tpw->pebuf.index = pwent->index; +} +#endif /* ENABLE_YP */ + +_TYPE( struct t_pwent * ) +t_getpwbyname(tpw, user) + struct t_pw * tpw; + const char * user; +{ + char indexbuf[16]; + char passbuf[MAXB64PARAMLEN]; + char saltstr[MAXB64SALTLEN]; + char username[MAXUSERLEN]; +#ifdef ENABLE_YP + struct t_passwd * nisent; +#endif + + t_rewindpw(tpw); + + while(t_nextfield(tpw->instream, username, MAXUSERLEN) > 0) { +#ifdef ENABLE_YP + if(tpw->state == FILE_NIS && *username == '+') { + if(strlen(username) == 1 || strcmp(user, username+1) == 0) { + nisent = _yp_gettpnam(user); /* Entry is +username or + */ + if(nisent != NULL) { + savepwent(tpw, &nisent->tp); + return &tpw->pebuf; + } + } + } +#endif + if(strcmp(user, username) == 0) + if(t_nextfield(tpw->instream, passbuf, MAXB64PARAMLEN) > 0 && + (tpw->pebuf.password.len = t_fromb64(tpw->pwbuf, passbuf)) > 0 && + t_nextfield(tpw->instream, saltstr, MAXB64SALTLEN) > 0 && + (tpw->pebuf.salt.len = t_fromb64(tpw->saltbuf, saltstr)) > 0 && + t_nextfield(tpw->instream, indexbuf, 16) > 0 && + (tpw->pebuf.index = atoi(indexbuf)) > 0) { + strcpy(tpw->userbuf, username); + tpw->pebuf.name = tpw->userbuf; + tpw->pebuf.password.data = tpw->pwbuf; + tpw->pebuf.salt.data = tpw->saltbuf; + t_nextline(tpw->instream); + return &tpw->pebuf; + } + if(t_nextline(tpw->instream) < 0) + return NULL; + } + return NULL; +} + +/* System password file accessors */ + +static int +pwinit() +{ + if(syspw == NULL) { + if((syspw = t_openpwbyname(DEFAULT_PASSWD)) == NULL) + return -1; + syspw->state = FILE_NIS; + } + return 0; +} + +static void +pwsetup(out, tpwd, tcnf) + struct t_passwd * out; + struct t_pwent * tpwd; + struct t_confent * tcnf; +{ + out->tp.name = tpwd->name; + out->tp.password.len = tpwd->password.len; + out->tp.password.data = tpwd->password.data; + out->tp.salt.len = tpwd->salt.len; + out->tp.salt.data = tpwd->salt.data; + out->tp.index = tpwd->index; + + out->tc.index = tcnf->index; + out->tc.modulus.len = tcnf->modulus.len; + out->tc.modulus.data = tcnf->modulus.data; + out->tc.generator.len = tcnf->generator.len; + out->tc.generator.data = tcnf->generator.data; +} + +_TYPE( struct t_passwd * ) +gettpnam +(user) + const char * user; +{ + struct t_pwent * tpptr; + struct t_confent * tcptr; + + if(pwinit() < 0) + return NULL; + tpptr = t_getpwbyname(syspw, user); + if(tpptr == NULL) + return NULL; + tcptr = + gettcid + (tpptr->index); + if(tcptr == NULL) + return NULL; + pwsetup(&tpass, tpptr, tcptr); + return &tpass; +} diff --git a/package/network/services/ead/src/tinysrp/t_pwd.h b/package/network/services/ead/src/tinysrp/t_pwd.h new file mode 100644 index 0000000000..73697bef3e --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_pwd.h @@ -0,0 +1,310 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#ifndef T_PWD_H +#define T_PWD_H + +#ifndef P +#if defined (__STDC__) || defined (__cplusplus) +#define P(x) x +#else +#define P(x) () +#endif +#endif + +/* For building dynamic link libraries under windows, windows NT + * using MSVC1.5 or MSVC2.0 + */ + +#ifndef _DLLDECL +#define _DLLDECL + +#ifdef MSVC15 /* MSVC1.5 support for 16 bit apps */ +#define _MSVC15EXPORT _export +#define _MSVC20EXPORT +#define _DLLAPI _export _pascal +#define _TYPE(a) a _MSVC15EXPORT +#define DLLEXPORT 1 + +#elif MSVC20 +#define _MSVC15EXPORT +#define _MSVC20EXPORT _declspec(dllexport) +#define _DLLAPI +#define _TYPE(a) _MSVC20EXPORT a +#define DLLEXPORT 1 + +#else /* Default, non-dll. Use this for Unix or DOS */ +#define _MSVC15DEXPORT +#define _MSVC20EXPORT +#define _DLLAPI +#define _TYPE(a) a +#endif +#endif + +#define MAXPARAMBITS 2048 +#define MAXPARAMLEN ((MAXPARAMBITS + 7) / 8) +#define MAXB64PARAMLEN ((MAXPARAMBITS + 5) / 6 + 1) +#define MAXHEXPARAMLEN ((MAXPARAMBITS + 3) / 4 + 1) +#define MAXOCTPARAMLEN ((MAXPARAMBITS + 2) / 3 + 1) + +#define MAXUSERLEN 32 +#define MAXSALTLEN 32 +#define MAXB64SALTLEN 44 /* 256 bits in b64 + null */ +#define SALTLEN 10 /* Normally 80 bits */ + +#define RESPONSE_LEN 20 /* 160-bit proof hashes */ +#define SESSION_KEY_LEN (2 * RESPONSE_LEN) /* 320-bit session key */ + +#define DEFAULT_PASSWD "tpasswd" + +struct t_num { /* Standard byte-oriented integer representation */ + int len; + unsigned char * data; +}; + +struct t_preconf { /* Structure returned by t_getpreparam() */ + char * mod_b64; + char * gen_b64; + char * comment; + + struct t_num modulus; + struct t_num generator; +}; + +/* + * The built-in (known good) parameters access routines + * + * "t_getprecount" returns the number of precompiled parameter sets. + * "t_getpreparam" returns the indicated parameter set. + * Memory is statically allocated - callers need not perform any memory mgmt. + */ +_TYPE( int ) t_getprecount(); +_TYPE( struct t_preconf * ) t_getpreparam P((int)); + +struct t_confent { /* One configuration file entry (index, N, g) */ + int index; + struct t_num modulus; + struct t_num generator; +}; + +struct t_conf { /* An open configuration file */ + FILE * instream; + char close_on_exit; + unsigned char modbuf[MAXPARAMLEN]; + unsigned char genbuf[MAXPARAMLEN]; + struct t_confent tcbuf; +}; + +/* + * The configuration file routines are designed along the lines of the + * "getpw" functions in the standard C library. + * + * "t_openconf" accepts a stdio stream and interprets it as a config file. + * "t_openconfbyname" accepts a filename and does the same thing. + * "t_closeconf" closes the config file. + * "t_getconfent" fetches the next sequential configuration entry. + * "t_getconfbyindex" fetches the configuration entry whose index + * matches the one supplied, or NULL if one can't be found. + * "t_getconflast" fetches the last configuration entry in the file. + * "t_makeconfent" generates a set of configuration entry parameters + * randomly. + * "t_newconfent" returns an empty configuration entry. + * "t_cmpconfent" compares two configuration entries a la strcmp. + * "t_checkconfent" verifies that a set of configuration parameters + * are suitable. N must be prime and should be a safe prime. + * "t_putconfent" writes a configuration entry to a stream. + */ +_TYPE( struct t_conf * ) t_openconf P((FILE *)); +_TYPE( struct t_conf * ) t_openconfbyname P((const char *)); +_TYPE( void ) t_closeconf P((struct t_conf *)); +_TYPE( void ) t_rewindconf P((struct t_conf *)); +_TYPE( struct t_confent * ) t_getconfent P((struct t_conf *)); +_TYPE( struct t_confent * ) t_getconfbyindex P((struct t_conf *, int)); +_TYPE( struct t_confent * ) t_getconflast P((struct t_conf *)); +_TYPE( struct t_confent * ) t_makeconfent P((struct t_conf *, int)); +_TYPE( struct t_confent * ) t_makeconfent_c P((struct t_conf *, int)); +_TYPE( struct t_confent * ) t_newconfent P((struct t_conf *)); +_TYPE( int ) t_cmpconfent P((const struct t_confent *, const struct t_confent *)); +_TYPE( int ) t_checkconfent P((const struct t_confent *)); +_TYPE( void ) t_putconfent P((const struct t_confent *, FILE *)); + +/* libc-style system conf file access */ +_TYPE( struct t_confent *) gettcent(); +_TYPE( struct t_confent *) gettcid P((int)); +_TYPE( void ) settcent(); +_TYPE( void ) endtcent(); + +#ifdef ENABLE_NSW +extern struct t_confent * _gettcent(); +extern struct t_confent * _gettcid P((int)); +extern void _settcent(); +extern void _endtcent(); +#endif + +/* A hack to support '+'-style entries in the passwd file */ + +typedef enum fstate { + FILE_ONLY, /* Ordinary file, don't consult NIS ever */ + FILE_NIS, /* Currently accessing file, use NIS if encountered */ + IN_NIS, /* Currently in a '+' entry; use NIS for getXXent */ +} FILE_STATE; + +struct t_pwent { /* A single password file entry */ + char * name; + struct t_num password; + struct t_num salt; + int index; +}; + +struct t_pw { /* An open password file */ + FILE * instream; + char close_on_exit; + FILE_STATE state; + char userbuf[MAXUSERLEN]; + unsigned char pwbuf[MAXPARAMLEN]; + unsigned char saltbuf[SALTLEN]; + struct t_pwent pebuf; +}; + +/* + * The password manipulation routines are patterned after the getpw* + * standard C library function calls. + * + * "t_openpw" reads a stream as if it were a password file. + * "t_openpwbyname" opens the named file as a password file. + * "t_closepw" closes an open password file. + * "t_rewindpw" starts the internal file pointer from the beginning + * of the password file. + * "t_getpwent" retrieves the next sequential password entry. + * "t_getpwbyname" looks up the password entry corresponding to the + * specified user. + * "t_makepwent" constructs a password entry from a username, password, + * numeric salt, and configuration entry. + * "t_putpwent" writes a password entry to a stream. + */ +_TYPE( struct t_pw * ) t_openpw P((FILE *)); +_TYPE( struct t_pw * ) t_openpwbyname P((const char *)); +_TYPE( void ) t_closepw P((struct t_pw *)); +_TYPE( void ) t_rewindpw P((struct t_pw *)); +_TYPE( struct t_pwent * ) t_getpwent P((struct t_pw *)); +_TYPE( struct t_pwent * ) t_getpwbyname P((struct t_pw *, const char *)); +_TYPE( struct t_pwent * ) t_makepwent P((struct t_pw *, const char *, + const char *, const struct t_num *, + const struct t_confent *)); +_TYPE( void ) t_putpwent P((const struct t_pwent *, FILE *)); + +struct t_passwd { + struct t_pwent tp; + struct t_confent tc; +}; + +/* libc-style system password file access */ +_TYPE( struct t_passwd * ) gettpent(); +_TYPE( struct t_passwd * ) gettpnam P((const char *)); +_TYPE( void ) settpent(); +_TYPE( void ) endtpent(); + +#ifdef ENABLE_NSW +extern struct t_passwd * _gettpent(); +extern struct t_passwd * _gettpnam P((const char *)); +extern void _settpent(); +extern void _endtpent(); +#endif + +/* + * Utility functions + * + * "t_verifypw" accepts a username and password, and checks against the + * system password file to see if the password for that user is correct. + * Returns > 0 if it is correct, 0 if not, and -1 if some error occurred + * (i.e. the user doesn't exist on the system). This is intended ONLY + * for local authentication; for remote authentication, look at the + * t_client and t_server source. (That's the whole point of SRP!) + * "t_changepw" modifies the specified file, substituting the given password + * entry for the one already in the file. If no matching entry is found, + * the new entry is simply appended to the file. + * "t_deletepw" removes the specified user from the specified file. + */ +_TYPE( int ) t_verifypw P((const char *, const char *)); +_TYPE( int ) t_changepw P((const char *, const struct t_pwent *)); +_TYPE( int ) t_deletepw P((const char *, const char *)); + +/* Conversion utilities */ + +/* + * All these calls accept output as the first parameter. In the case of + * t_tohex and t_tob64, the last argument is the length of the byte-string + * input. + */ +_TYPE( char * t_tohex ) P((char *, char *, unsigned)); +_TYPE( int ) t_fromhex P((char *, char *)); +_TYPE( char * ) t_tob64 P((char *, char *, unsigned)); +_TYPE( int ) t_fromb64 P((char *, char *)); + +/* Miscellaneous utilities */ + +/* + * "t_random" is a cryptographic random number generator, which is seeded + * from various high-entropy sources and uses a one-way hash function + * in a feedback configuration. + * "t_sessionkey" is the interleaved hash used to generate session keys + * from a large integer. + * "t_getpass" reads a password from the terminal without echoing. + */ +_TYPE( void ) t_random P((unsigned char *, unsigned)); +_TYPE( void ) t_stronginitrand(); +_TYPE( unsigned char * ) + t_sessionkey P((unsigned char *, unsigned char *, unsigned)); +_TYPE( int ) t_getpass P((char *, unsigned, const char *)); + +/* + * Return value of t_checkprime: + * < 0 : not prime + * = 0 : prime, but not safe + * > 0 : safe + */ +#define NUM_NOTPRIME -1 +#define NUM_NOTSAFE 0 +#define NUM_SAFE 1 + +_TYPE( int ) t_checkprime P((const struct t_num *)); + +#endif diff --git a/package/network/services/ead/src/tinysrp/t_read.c b/package/network/services/ead/src/tinysrp/t_read.c new file mode 100644 index 0000000000..087b7d55b8 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_read.c @@ -0,0 +1,81 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> +#include "config.h" + +#define FSEPARATOR ':' + +int +t_nextfield(fp, s, max) +FILE * fp; +char * s; +unsigned max; +{ + int c, count = 0; + + while((c = getc(fp)) != EOF) { + if(c == '\n') { + ungetc(c, fp); + break; + } + else if(c == FSEPARATOR) + break; + if(count < max - 1) { + *s++ = c; + ++count; + } + } + *s++ = '\0'; + return count; +} + +int +t_nextline(fp) +FILE * fp; +{ + int c; + + while((c = getc(fp)) != '\n') + if(c == EOF) + return -1; + return 0; +} diff --git a/package/network/services/ead/src/tinysrp/t_read.h b/package/network/services/ead/src/tinysrp/t_read.h new file mode 100644 index 0000000000..e621f793ad --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_read.h @@ -0,0 +1,55 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#ifndef _T_READ_H_ +#define _T_READ_H_ + +#if !defined(P) +#ifdef __STDC__ +#define P(x) x +#else +#define P(x) () +#endif +#endif + +extern int t_nextfield P((FILE *, char *, unsigned)); +extern int t_nextline P((FILE *)); +#endif diff --git a/package/network/services/ead/src/tinysrp/t_server.c b/package/network/services/ead/src/tinysrp/t_server.c new file mode 100644 index 0000000000..6ab501bcb8 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_server.c @@ -0,0 +1,259 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <stdio.h> +#include "t_defines.h" +#include "t_pwd.h" +#include "t_server.h" + +_TYPE( struct t_server * ) +t_serveropenraw(ent, tce) + struct t_pwent * ent; + struct t_confent * tce; +{ + struct t_server * ts; + unsigned char buf1[SHA_DIGESTSIZE], buf2[SHA_DIGESTSIZE]; + SHA1_CTX ctxt; + int i; + + if((ts = malloc(sizeof(struct t_server))) == 0) + return 0; + + SHA1Init(&ts->ckhash); + + ts->index = ent->index; + ts->n.len = tce->modulus.len; + ts->n.data = ts->nbuf; + memcpy(ts->n.data, tce->modulus.data, ts->n.len); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, ts->n.data, ts->n.len); + SHA1Final(buf1, &ctxt); + + ts->g.len = tce->generator.len; + ts->g.data = ts->gbuf; + memcpy(ts->g.data, tce->generator.data, ts->g.len); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, ts->g.data, ts->g.len); + SHA1Final(buf2, &ctxt); + + for(i = 0; i < sizeof(buf1); ++i) + buf1[i] ^= buf2[i]; + + SHA1Update(&ts->ckhash, buf1, sizeof(buf1)); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, ent->name, strlen(ent->name)); + SHA1Final(buf1, &ctxt); + + SHA1Update(&ts->ckhash, buf1, sizeof(buf1)); + + ts->v.len = ent->password.len; + ts->v.data = ts->vbuf; + memcpy(ts->v.data, ent->password.data, ts->v.len); + + ts->s.len = ent->salt.len; + ts->s.data = ts->saltbuf; + memcpy(ts->s.data, ent->salt.data, ts->s.len); + + SHA1Update(&ts->ckhash, ts->s.data, ts->s.len); + + ts->b.data = ts->bbuf; + ts->B.data = ts->Bbuf; + + SHA1Init(&ts->hash); + SHA1Init(&ts->oldhash); + SHA1Init(&ts->oldckhash); + + return ts; +} + +_TYPE( struct t_num * ) +t_servergenexp(ts) + struct t_server * ts; +{ + BigInteger b, B, v, n, g; + + if(ts->n.len < BLEN) + ts->b.len = ts->n.len; + else + ts->b.len = BLEN; + + t_random(ts->b.data, ts->b.len); + b = BigIntegerFromBytes(ts->b.data, ts->b.len); + n = BigIntegerFromBytes(ts->n.data, ts->n.len); + g = BigIntegerFromBytes(ts->g.data, ts->g.len); + B = BigIntegerFromInt(0); + BigIntegerModExp(B, g, b, n); + + v = BigIntegerFromBytes(ts->v.data, ts->v.len); + BigIntegerAdd(B, B, v); + if(BigIntegerCmp(B, n) > 0) + BigIntegerSub(B, B, n); + + ts->B.len = BigIntegerToBytes(B, ts->B.data); + + BigIntegerFree(v); + BigIntegerFree(B); + BigIntegerFree(b); + BigIntegerFree(g); + BigIntegerFree(n); + + SHA1Update(&ts->oldckhash, ts->B.data, ts->B.len); + + return &ts->B; +} + +_TYPE( unsigned char * ) +t_servergetkey(ts, clientval) + struct t_server * ts; + struct t_num * clientval; +{ + BigInteger n, v, A, b, prod, res, S; + SHA1_CTX ctxt; + unsigned char sbuf[MAXPARAMLEN]; + unsigned char dig[SHA_DIGESTSIZE]; + unsigned slen; + unsigned int u; + + SHA1Update(&ts->ckhash, clientval->data, clientval->len); + SHA1Update(&ts->ckhash, ts->B.data, ts->B.len); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, ts->B.data, ts->B.len); + SHA1Final(dig, &ctxt); + u = (dig[0] << 24) | (dig[1] << 16) | (dig[2] << 8) | dig[3]; + + SHA1Update(&ts->oldhash, clientval->data, clientval->len); + SHA1Update(&ts->hash, clientval->data, clientval->len); + + n = BigIntegerFromBytes(ts->n.data, ts->n.len); + b = BigIntegerFromBytes(ts->b.data, ts->b.len); + v = BigIntegerFromBytes(ts->v.data, ts->v.len); + A = BigIntegerFromBytes(clientval->data, clientval->len); + + prod = BigIntegerFromInt(0); + BigIntegerModExpInt(prod, v, u, n); + res = BigIntegerFromInt(0); + BigIntegerModMul(res, prod, A, n); + + BigIntegerFree(A); + BigIntegerFree(v); + BigIntegerFree(prod); + + if(BigIntegerCmpInt(res, 1) <= 0) { /* Check for Av^u == 1 (mod n) */ + BigIntegerFree(res); + BigIntegerFree(b); + BigIntegerFree(n); + return NULL; + } + + S = BigIntegerFromInt(0); + + BigIntegerAddInt(S, res, 1); + if(BigIntegerCmp(S, n) == 0) { /* Check for Av^u == -1 (mod n) */ + BigIntegerFree(res); + BigIntegerFree(b); + BigIntegerFree(n); + BigIntegerFree(S); + return NULL; + } + + BigIntegerModExp(S, res, b, n); + slen = BigIntegerToBytes(S, sbuf); + + BigIntegerFree(S); + BigIntegerFree(res); + BigIntegerFree(b); + BigIntegerFree(n); + + t_sessionkey(ts->session_key, sbuf, slen); + memset(sbuf, 0, slen); + + SHA1Update(&ts->oldhash, ts->session_key, sizeof(ts->session_key)); + SHA1Update(&ts->oldckhash, ts->session_key, sizeof(ts->session_key)); + SHA1Update(&ts->ckhash, ts->session_key, sizeof(ts->session_key)); + + return ts->session_key; +} + +_TYPE( int ) +t_serververify(ts, resp) + struct t_server * ts; + unsigned char * resp; +{ + unsigned char expected[SHA_DIGESTSIZE]; + int i; + + SHA1Final(expected, &ts->oldckhash); + i = memcmp(expected, resp, sizeof(expected)); + if(i == 0) { + SHA1Final(ts->session_response, &ts->oldhash); + return 0; + } + SHA1Final(expected, &ts->ckhash); + i = memcmp(expected, resp, sizeof(expected)); + if(i == 0) { + SHA1Update(&ts->hash, expected, sizeof(expected)); + SHA1Update(&ts->hash, ts->session_key, sizeof(ts->session_key)); + SHA1Final(ts->session_response, &ts->hash); + } + return i; +} + +_TYPE( unsigned char * ) +t_serverresponse(ts) + struct t_server * ts; +{ + return ts->session_response; +} + +_TYPE( void ) +t_serverclose(ts) + struct t_server * ts; +{ + memset(ts->bbuf, 0, sizeof(ts->bbuf)); + memset(ts->vbuf, 0, sizeof(ts->vbuf)); + memset(ts->saltbuf, 0, sizeof(ts->saltbuf)); + memset(ts->session_key, 0, sizeof(ts->session_key)); + free(ts); +} diff --git a/package/network/services/ead/src/tinysrp/t_server.h b/package/network/services/ead/src/tinysrp/t_server.h new file mode 100644 index 0000000000..20970ffe06 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_server.h @@ -0,0 +1,138 @@ +/* + * Copyright (c) 1997-1999 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#ifndef T_SERVER_H +#define T_SERVER_H + +#include "t_sha.h" + +#if !defined(P) +#ifdef __STDC__ +#define P(x) x +#else +#define P(x) () +#endif +#endif + +#ifndef _DLLDECL +#define _DLLDECL + +#ifdef MSVC15 /* MSVC1.5 support for 16 bit apps */ +#define _MSVC15EXPORT _export +#define _MSVC20EXPORT +#define _DLLAPI _export _pascal +#define _TYPE(a) a _MSVC15EXPORT +#define DLLEXPORT 1 + +#elif MSVC20 +#define _MSVC15EXPORT +#define _MSVC20EXPORT _declspec(dllexport) +#define _DLLAPI +#define _TYPE(a) _MSVC20EXPORT a +#define DLLEXPORT 1 + +#else /* Default, non-dll. Use this for Unix or DOS */ +#define _MSVC15DEXPORT +#define _MSVC20EXPORT +#define _DLLAPI +#define _TYPE(a) a +#endif +#endif + +#define BLEN 32 + +struct t_server { + int index; + struct t_num n; + struct t_num g; + struct t_num v; + struct t_num s; + + struct t_num b; + struct t_num B; + + SHA1_CTX oldhash, hash, oldckhash, ckhash; + + unsigned char session_key[SESSION_KEY_LEN]; + unsigned char session_response[RESPONSE_LEN]; + + unsigned char nbuf[MAXPARAMLEN], gbuf[MAXPARAMLEN], vbuf[MAXPARAMLEN]; + unsigned char saltbuf[MAXSALTLEN], bbuf[BLEN], Bbuf[MAXPARAMLEN]; +}; + +/* + * SRP server-side negotiation + * + * This code negotiates the server side of an SRP exchange. + * "t_serveropen" accepts a username (sent by the client), a pointer + * to an open password file, and a pointer to an open configuration + * file. The server should then call... + * "t_servergenexp" will generate a random 256-bit exponent and + * raise g (from the configuration file) to that power, returning + * the result. This result should be sent to the client as y(p). + * "t_servergetkey" accepts the exponential w(p), which should be + * sent by the client, and computes the 256-bit session key. + * This data should be saved before the session is closed. + * "t_serverresponse" computes the session key proof as SHA(w(p), K). + * "t_serverclose" closes the session and frees its memory. + * + * Note that authentication is not performed per se; it is up + * to either/both sides of the protocol to now verify securely + * that their session keys agree in order to establish authenticity. + * One possible way is through "oracle hashing"; one side sends + * r, the other replies with H(r,K), where H() is a hash function. + * + * t_serverresponse and t_serververify now implement a version of + * the session-key verification described above. + */ +_TYPE( struct t_server * ) + t_serveropen P((const char *)); +_TYPE( struct t_server * ) + t_serveropenfromfiles P((const char *, struct t_pw *, struct t_conf *)); +_TYPE( struct t_server * ) + t_serveropenraw P((struct t_pwent *, struct t_confent *)); +_TYPE( struct t_num * ) t_servergenexp P((struct t_server *)); +_TYPE( unsigned char * ) t_servergetkey P((struct t_server *, struct t_num *)); +_TYPE( int ) t_serververify P((struct t_server *, unsigned char *)); +_TYPE( unsigned char * ) t_serverresponse P((struct t_server *)); +_TYPE( void ) t_serverclose P((struct t_server *)); + +#endif diff --git a/package/network/services/ead/src/tinysrp/t_sha.c b/package/network/services/ead/src/tinysrp/t_sha.c new file mode 100644 index 0000000000..cc41d6487c --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_sha.c @@ -0,0 +1,166 @@ +#include "t_defines.h" +#include "t_sha.h" + +/* +SHA-1 in C +By Steve Reid <steve@edmweb.com> +100% Public Domain + +Test Vectors (from FIPS PUB 180-1) +"abc" + A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D +"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" + 84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1 +A million repetitions of "a" + 34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F +*/ + +/* #define WORDS_BIGENDIAN * This should be #define'd if true. */ +/* #define SHA1HANDSOFF * Copies data before messing with it. */ + +#include <stdio.h> +#include <string.h> + +static void SHA1Transform(uint32 state[5], const unsigned char buffer[64]); + +#define rol(value, bits) (((value) << (bits)) | ((value) >> (32 - (bits)))) + +/* blk0() and blk() perform the initial expand. */ +/* I got the idea of expanding during the round function from SSLeay */ +#ifndef WORDS_BIGENDIAN +#define blk0(i) (block->l[i] = (rol(block->l[i],24)&0xFF00FF00) \ + |(rol(block->l[i],8)&0x00FF00FF)) +#else +#define blk0(i) block->l[i] +#endif +#define blk(i) (block->l[i&15] = rol(block->l[(i+13)&15]^block->l[(i+8)&15] \ + ^block->l[(i+2)&15]^block->l[i&15],1)) + +/* (R0+R1), R2, R3, R4 are the different operations used in SHA1 */ +#define R0(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk0(i)+0x5A827999+rol(v,5);w=rol(w,30); +#define R1(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk(i)+0x5A827999+rol(v,5);w=rol(w,30); +#define R2(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0x6ED9EBA1+rol(v,5);w=rol(w,30); +#define R3(v,w,x,y,z,i) z+=(((w|x)&y)|(w&x))+blk(i)+0x8F1BBCDC+rol(v,5);w=rol(w,30); +#define R4(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0xCA62C1D6+rol(v,5);w=rol(w,30); + +/* Hash a single 512-bit block. This is the core of the algorithm. */ + +static void SHA1Transform(uint32 state[5], const unsigned char buffer[64]) +{ +uint32 a, b, c, d, e; +typedef union { + unsigned char c[64]; + uint32 l[16]; +} CHAR64LONG16; +CHAR64LONG16* block; +#ifdef SHA1HANDSOFF +static unsigned char workspace[64]; + block = (CHAR64LONG16*)workspace; + memcpy(block, buffer, 64); +#else + block = (CHAR64LONG16*)buffer; +#endif + /* Copy context->state[] to working vars */ + a = state[0]; + b = state[1]; + c = state[2]; + d = state[3]; + e = state[4]; + /* 4 rounds of 20 operations each. Loop unrolled. */ + R0(a,b,c,d,e, 0); R0(e,a,b,c,d, 1); R0(d,e,a,b,c, 2); R0(c,d,e,a,b, 3); + R0(b,c,d,e,a, 4); R0(a,b,c,d,e, 5); R0(e,a,b,c,d, 6); R0(d,e,a,b,c, 7); + R0(c,d,e,a,b, 8); R0(b,c,d,e,a, 9); R0(a,b,c,d,e,10); R0(e,a,b,c,d,11); + R0(d,e,a,b,c,12); R0(c,d,e,a,b,13); R0(b,c,d,e,a,14); R0(a,b,c,d,e,15); + R1(e,a,b,c,d,16); R1(d,e,a,b,c,17); R1(c,d,e,a,b,18); R1(b,c,d,e,a,19); + R2(a,b,c,d,e,20); R2(e,a,b,c,d,21); R2(d,e,a,b,c,22); R2(c,d,e,a,b,23); + R2(b,c,d,e,a,24); R2(a,b,c,d,e,25); R2(e,a,b,c,d,26); R2(d,e,a,b,c,27); + R2(c,d,e,a,b,28); R2(b,c,d,e,a,29); R2(a,b,c,d,e,30); R2(e,a,b,c,d,31); + R2(d,e,a,b,c,32); R2(c,d,e,a,b,33); R2(b,c,d,e,a,34); R2(a,b,c,d,e,35); + R2(e,a,b,c,d,36); R2(d,e,a,b,c,37); R2(c,d,e,a,b,38); R2(b,c,d,e,a,39); + R3(a,b,c,d,e,40); R3(e,a,b,c,d,41); R3(d,e,a,b,c,42); R3(c,d,e,a,b,43); + R3(b,c,d,e,a,44); R3(a,b,c,d,e,45); R3(e,a,b,c,d,46); R3(d,e,a,b,c,47); + R3(c,d,e,a,b,48); R3(b,c,d,e,a,49); R3(a,b,c,d,e,50); R3(e,a,b,c,d,51); + R3(d,e,a,b,c,52); R3(c,d,e,a,b,53); R3(b,c,d,e,a,54); R3(a,b,c,d,e,55); + R3(e,a,b,c,d,56); R3(d,e,a,b,c,57); R3(c,d,e,a,b,58); R3(b,c,d,e,a,59); + R4(a,b,c,d,e,60); R4(e,a,b,c,d,61); R4(d,e,a,b,c,62); R4(c,d,e,a,b,63); + R4(b,c,d,e,a,64); R4(a,b,c,d,e,65); R4(e,a,b,c,d,66); R4(d,e,a,b,c,67); + R4(c,d,e,a,b,68); R4(b,c,d,e,a,69); R4(a,b,c,d,e,70); R4(e,a,b,c,d,71); + R4(d,e,a,b,c,72); R4(c,d,e,a,b,73); R4(b,c,d,e,a,74); R4(a,b,c,d,e,75); + R4(e,a,b,c,d,76); R4(d,e,a,b,c,77); R4(c,d,e,a,b,78); R4(b,c,d,e,a,79); + /* Add the working vars back into context.state[] */ + state[0] += a; + state[1] += b; + state[2] += c; + state[3] += d; + state[4] += e; + /* Wipe variables */ + a = b = c = d = e = 0; +} + + +/* SHA1Init - Initialize new context */ + +void SHA1Init(SHA1_CTX* context) +{ + /* SHA1 initialization constants */ + context->state[0] = 0x67452301; + context->state[1] = 0xEFCDAB89; + context->state[2] = 0x98BADCFE; + context->state[3] = 0x10325476; + context->state[4] = 0xC3D2E1F0; + context->count[0] = context->count[1] = 0; +} + + +/* Run your data through this. */ + +void SHA1Update(SHA1_CTX* context, const unsigned char* data, unsigned int len) +{ +unsigned int i, j; + + j = (context->count[0] >> 3) & 63; + if ((context->count[0] += len << 3) < (len << 3)) context->count[1]++; + context->count[1] += (len >> 29); + if ((j + len) > 63) { + memcpy(&context->buffer[j], data, (i = 64-j)); + SHA1Transform(context->state, context->buffer); + for ( ; i + 63 < len; i += 64) { + SHA1Transform(context->state, &data[i]); + } + j = 0; + } + else i = 0; + memcpy(&context->buffer[j], &data[i], len - i); +} + + +/* Add padding and return the message digest. */ + +void SHA1Final(unsigned char digest[20], SHA1_CTX* context) +{ +uint32 i, j; +unsigned char finalcount[8]; + + for (i = 0; i < 8; i++) { + finalcount[i] = (unsigned char)((context->count[(i >= 4 ? 0 : 1)] + >> ((3-(i & 3)) * 8) ) & 255); /* Endian independent */ + } + SHA1Update(context, (unsigned char *)"\200", 1); + while ((context->count[0] & 504) != 448) { + SHA1Update(context, (unsigned char *)"\0", 1); + } + SHA1Update(context, finalcount, 8); /* Should cause a SHA1Transform() */ + for (i = 0; i < 20; i++) { + digest[i] = (unsigned char) + ((context->state[i>>2] >> ((3-(i & 3)) * 8) ) & 255); + } + /* Wipe variables */ + i = j = 0; + memset(context->buffer, 0, 64); + memset(context->state, 0, 20); + memset(context->count, 0, 8); + memset(&finalcount, 0, 8); +#ifdef SHA1HANDSOFF /* make SHA1Transform overwrite its own static vars */ + SHA1Transform(context->state, context->buffer); +#endif +} diff --git a/package/network/services/ead/src/tinysrp/t_sha.h b/package/network/services/ead/src/tinysrp/t_sha.h new file mode 100644 index 0000000000..d10115e748 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_sha.h @@ -0,0 +1,26 @@ +#ifndef T_SHA_H +#define T_SHA_H + +#if !defined(P) +#ifdef __STDC__ +#define P(x) x +#else +#define P(x) () +#endif +#endif + +#define SHA_DIGESTSIZE 20 + +typedef unsigned int uint32; + +typedef struct { + uint32 state[5]; + uint32 count[2]; + unsigned char buffer[64]; +} SHA1_CTX; + +void SHA1Init P((SHA1_CTX* context)); +void SHA1Update P((SHA1_CTX* context, const unsigned char* data, unsigned int len)); +void SHA1Final P((unsigned char digest[20], SHA1_CTX* context)); + +#endif /* T_SHA_H */ diff --git a/package/network/services/ead/src/tinysrp/t_truerand.c b/package/network/services/ead/src/tinysrp/t_truerand.c new file mode 100644 index 0000000000..fa0d6ce603 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/t_truerand.c @@ -0,0 +1,151 @@ +/* + * Physically random numbers (very nearly uniform) + * D. P. Mitchell + * Modified by Matt Blaze 7/95 + */ +/* + * The authors of this software are Don Mitchell and Matt Blaze. + * Copyright (c) 1995 by AT&T. + * Permission to use, copy, and modify this software without fee + * is hereby granted, provided that this entire notice is included in + * all copies of any software which is or includes a copy or + * modification of this software and in all copies of the supporting + * documentation for such software. + * + * This software may be subject to United States export controls. + * + * THIS SOFTWARE IS BEING PROVIDED "AS IS", WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTY. IN PARTICULAR, NEITHER THE AUTHORS NOR AT&T MAKE ANY + * REPRESENTATION OR WARRANTY OF ANY KIND CONCERNING THE MERCHANTABILITY + * OF THIS SOFTWARE OR ITS FITNESS FOR ANY PARTICULAR PURPOSE. + */ + +/* + * WARNING: depending on the particular platform, raw_truerand() + * output may be biased or correlated. In general, you can expect + * about 16 bits of "pseudo-entropy" out of each 32 bit word returned + * by truerand(), but it may not be uniformly diffused. You should + * raw_therefore run the output through some post-whitening function + * (like MD5 or DES or whatever) before using it to generate key + * material. (RSAREF's random package does this for you when you feed + * raw_truerand() bits to the seed input function.) + * + * The application interface, for 8, 16, and 32 bit properly "whitened" + * random numbers, can be found in trand8(), trand16(), and trand32(). + * Use those instead of calling raw_truerand() directly. + * + * The basic idea here is that between clock "skew" and various + * hard-to-predict OS event arrivals, counting a tight loop will yield + * a little (maybe a third of a bit or so) of "good" randomness per + * interval clock tick. This seems to work well even on unloaded + * machines. If there is a human operator at the machine, you should + * augment truerand with other measure, like keyboard event timing. + * On server machines (e.g., when you need to generate a + * Diffie-Hellman secret) truerand alone may be good enough. + * + * Test these assumptions on your own platform before fielding a + * system based on this software or these techniques. + * + * This software seems to work well (at 10 or so bits per + * raw_truerand() call) on a Sun Sparc-20 under SunOS 4.1.3 and on a + * P100 under BSDI 2.0. You're on your own elsewhere. + * + */ + +#include "t_defines.h" + +#include <signal.h> +#include <setjmp.h> +#include <sys/time.h> +#include <math.h> +#include <stdio.h> + +#ifdef OLD_TRUERAND +static jmp_buf env; +#endif +static unsigned volatile count +#ifndef OLD_TRUERAND + , done = 0 +#endif +; + +static unsigned ocount; +static unsigned buffer; + +static void +tick() +{ + struct itimerval it, oit; + + it.it_interval.tv_sec = 0; + it.it_interval.tv_usec = 0; + it.it_value.tv_sec = 0; + it.it_value.tv_usec = 16665; + if (setitimer(ITIMER_REAL, &it, &oit) < 0) + perror("tick"); +} + +static void +interrupt() +{ + if (count) { +#ifdef OLD_TRUERAND + longjmp(env, 1); +#else + ++done; + return; +#endif + } + + (void) signal(SIGALRM, interrupt); + tick(); +} + +static unsigned long +roulette() +{ +#ifdef OLD_TRUERAND + if (setjmp(env)) { + count ^= (count>>3) ^ (count>>6) ^ ocount; + count &= 0x7; + ocount=count; + buffer = (buffer<<3) ^ count; + return buffer; + } +#else + done = 0; +#endif + (void) signal(SIGALRM, interrupt); + count = 0; + tick(); +#ifdef OLD_TRUERAND + for (;;) +#else + while(done == 0) +#endif + count++; /* about 1 MHz on VAX 11/780 */ +#ifndef OLD_TRUERAND + count ^= (count>>3) ^ (count>>6) ^ ocount; + count &= 0x7; + ocount=count; + buffer = (buffer<<3) ^ count; + return buffer; +#endif +} + +unsigned long +raw_truerand() +{ + count=0; + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + (void) roulette(); + return roulette(); +} diff --git a/package/network/services/ead/src/tinysrp/tconf.c b/package/network/services/ead/src/tinysrp/tconf.c new file mode 100644 index 0000000000..ad77f4cc1d --- /dev/null +++ b/package/network/services/ead/src/tinysrp/tconf.c @@ -0,0 +1,157 @@ +/* + * Copyright (c) 1997-2000 The Stanford SRP Authentication Project + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, + * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY + * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. + * + * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL, + * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF + * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * In addition, the following conditions apply: + * + * 1. Any software that incorporates the SRP authentication technology + * must display the following acknowlegment: + * "This product uses the 'Secure Remote Password' cryptographic + * authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)." + * + * 2. Any software that incorporates all or part of the SRP distribution + * itself must also display the following acknowledgment: + * "This product includes software developed by Tom Wu and Eugene + * Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)." + * + * 3. Redistributions in source or binary form must retain an intact copy + * of this copyright notice and list of conditions. + */ + +#include <unistd.h> /* close getlogin */ +#include <stdlib.h> /* atexit exit */ +#include <stdio.h> +#include <string.h> + +#include "t_pwd.h" + +#define MIN_BASIS_BITS 512 +#define BASIS_BITS 2048 + +extern int optind; +extern char *optarg; + +extern int errno; + +char *progName; + +int debug = 0; +int verbose = 0; +int composite = 0; + +int main(argc, argv) + int argc; + char *argv[]; +{ + char *chp; + char *configFile = NULL; + char cbuf[256]; + char b64buf[MAXB64PARAMLEN]; + int c, ch, i, lastidx, keylen, yesno, fsize, status, nparams; + FILE *efp; + + struct t_preconf * tpc; + struct t_conf tcs; + struct t_conf * tc = &tcs; + struct t_confent * tcent; + + progName = *argv; + if ((chp = strrchr(progName, '/')) != (char *) 0) progName = chp + 1; + + while ((ch = getopt(argc, argv, "dv2c:")) != EOF) + switch(ch) { + case 'c': + configFile = optarg; + break; + case 'v': + verbose++; + break; + case 'd': + debug++; + break; + case '2': + composite++; + break; + default: + fprintf(stderr, "usage: %s [-dv2] [-c configfile]\n", progName); + exit(1); + } + + argc -= optind; + argv += optind; + + lastidx = 0; + keylen = 0; + + tcent = t_newconfent(tc); + + printf("\nThis program will generate a set of parameters for the EPS\n"); + printf("password file. The size of these parameters, measured in bits,\n"); + printf("determines the level of security offered by SRP, and is related\n"); + printf("to the security of similarly-sized RSA or Diffie-Hellman keys.\n"); + printf("Choosing a predefined field is generally preferable to generating\n"); + printf("a new field because clients can avoid costly parameter verification.\n"); + printf("Either way, the values generated by this program are public and\n"); + printf("can even shared between systems.\n"); + + printf("\nEnter the new field size, in bits. Suggested sizes:\n\n"); + printf(" 512 (fast, minimally secure)\n"); + printf(" 768 (moderate security)\n"); + printf("1024 (most popular default)\n"); + printf("1536 (additional security, possibly slow)\n"); + printf("2048 (maximum supported security level)\n"); + printf("\nField size (%d to %d): ", MIN_BASIS_BITS, BASIS_BITS); + + fgets(cbuf, sizeof(cbuf), stdin); + fsize = atoi(cbuf); + if(fsize < MIN_BASIS_BITS || fsize > BASIS_BITS) { + fprintf(stderr, "%s: field size must be between %d and %d\n", + progName, MIN_BASIS_BITS, BASIS_BITS); + exit(1); + } + + if(fsize <= keylen) + fprintf(stderr, "Warning: new field size is not larger than old field size\n"); + + printf("\nInitializing random number generator..."); + fflush(stdout); + t_initrand(); + + if(composite) + printf("done.\n\nGenerating a %d-bit composite with safe prime factors. This may take a while.\n", fsize); + else + printf("done.\n\nGenerating a %d-bit safe prime. This may take a while.\n", fsize); + + while((tcent = (composite ? t_makeconfent_c(tc, fsize) : + t_makeconfent(tc, fsize))) == NULL) + printf("Parameter generation failed, retrying...\n"); + tcent->index = lastidx + 1; + + printf("\nParameters successfully generated.\n"); + printf("N = [%s]\n", t_tob64(b64buf, + tcent->modulus.data, tcent->modulus.len)); + printf("g = [%s]\n", t_tob64(b64buf, + tcent->generator.data, tcent->generator.len)); + printf("\nYou must update the pre_params array in t_getconf.c\n"); +} diff --git a/package/network/services/ead/src/tinysrp/tinysrp.c b/package/network/services/ead/src/tinysrp/tinysrp.c new file mode 100644 index 0000000000..fc01055417 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/tinysrp.c @@ -0,0 +1,235 @@ +/* This bit implements a simple API for using the SRP library over sockets. */ + +#include <stdio.h> +#include <string.h> +#include <stdlib.h> +#include <unistd.h> +#include <sys/types.h> +#include <sys/socket.h> +#include "t_defines.h" +#include "t_pwd.h" +#include "t_server.h" +#include "t_client.h" +#include "tinysrp.h" + +#ifndef MSG_WAITALL +#ifdef linux +#define MSG_WAITALL 0x100 /* somehow not defined on my box */ +#endif +#endif + +/* This is called by the client with a connected socket, username, and +passphrase. pass can be NULL in which case the user is queried. */ + +int tsrp_client_authenticate(int s, char *user, char *pass, TSRP_SESSION *tsrp) +{ + int i, index; + unsigned char username[MAXUSERLEN + 1], sbuf[MAXSALTLEN]; + unsigned char msgbuf[MAXPARAMLEN + 1], bbuf[MAXPARAMLEN]; + unsigned char passbuf[128], *skey; + struct t_client *tc; + struct t_preconf *tcp; /* @@@ should go away */ + struct t_num salt, *A, B; + + /* Send the username. */ + + i = strlen(user); + if (i > MAXUSERLEN) { + i = MAXUSERLEN; + } + msgbuf[0] = i; + memcpy(msgbuf + 1, user, i); + if (send(s, msgbuf, i + 1, 0) < 0) { + return 0; + } + memcpy(username, user, i); + username[i] = '\0'; + + /* Get the prime index and salt. */ + + i = recv(s, msgbuf, 2, MSG_WAITALL); + if (i <= 0) { + return 0; + } + index = msgbuf[0]; + if (index <= 0 || index > t_getprecount()) { + return 0; + } + tcp = t_getpreparam(index - 1); + salt.len = msgbuf[1]; + if (salt.len > MAXSALTLEN) { + return 0; + } + salt.data = sbuf; + i = recv(s, sbuf, salt.len, MSG_WAITALL); + if (i <= 0) { + return 0; + } + + /* @@@ t_clientopen() needs a variant that takes the index */ + + tc = t_clientopen(username, &tcp->modulus, &tcp->generator, &salt); + if (tc == NULL) { + return 0; + } + + /* Calculate A and send it to the server. */ + + A = t_clientgenexp(tc); + msgbuf[0] = A->len - 1; /* len is max 256 */ + memcpy(msgbuf + 1, A->data, A->len); + if (send(s, msgbuf, A->len + 1, 0) < 0) { + return 0; + } + + /* Ask the user for the passphrase. */ + + if (pass == NULL) { + t_getpass(passbuf, sizeof(passbuf), "Enter password:"); + pass = passbuf; + } + t_clientpasswd(tc, pass); + + /* Get B from the server. */ + + i = recv(s, msgbuf, 1, 0); + if (i <= 0) { + return 0; + } + B.len = msgbuf[0] + 1; + B.data = bbuf; + i = recv(s, bbuf, B.len, MSG_WAITALL); + if (i <= 0) { + return 0; + } + + /* Compute the session key. */ + + skey = t_clientgetkey(tc, &B); + if (skey == NULL) { + return 0; + } + + /* Send the response. */ + + if (send(s, t_clientresponse(tc), RESPONSE_LEN, 0) < 0) { + return 0; + } + + /* Get the server's response. */ + + i = recv(s, msgbuf, RESPONSE_LEN, MSG_WAITALL); + if (i <= 0) { + return 0; + } + if (t_clientverify(tc, msgbuf) != 0) { + return 0; + } + + /* All done. Now copy the key and clean up. */ + + if (tsrp) { + memcpy(tsrp->username, username, strlen(username) + 1); + memcpy(tsrp->key, skey, SESSION_KEY_LEN); + } + t_clientclose(tc); + + return 1; +} + +/* This is called by the server with a connected socket. */ + +int tsrp_server_authenticate(int s, TSRP_SESSION *tsrp) +{ + int i, j; + unsigned char username[MAXUSERLEN], *skey; + unsigned char msgbuf[MAXPARAMLEN + 1], abuf[MAXPARAMLEN]; + struct t_server *ts; + struct t_num A, *B; + + /* Get the username. */ + + i = recv(s, msgbuf, 1, 0); + if (i <= 0) { + return 0; + } + j = msgbuf[0]; + i = recv(s, username, j, MSG_WAITALL); + if (i <= 0) { + return 0; + } + username[j] = '\0'; + + ts = t_serveropen(username); + if (ts == NULL) { + return 0; + } + + /* Send the prime index and the salt. */ + + msgbuf[0] = ts->index; /* max 256 primes... */ + i = ts->s.len; + msgbuf[1] = i; + memcpy(msgbuf + 2, ts->s.data, i); + if (send(s, msgbuf, i + 2, 0) < 0) { + return 0; + } + + /* Calculate B while we're waiting. */ + + B = t_servergenexp(ts); + + /* Get A from the client. */ + + i = recv(s, msgbuf, 1, 0); + if (i <= 0) { + return 0; + } + A.len = msgbuf[0] + 1; + A.data = abuf; + i = recv(s, abuf, A.len, MSG_WAITALL); + if (i <= 0) { + return 0; + } + + /* Now send B. */ + + msgbuf[0] = B->len - 1; + memcpy(msgbuf + 1, B->data, B->len); + if (send(s, msgbuf, B->len + 1, 0) < 0) { + return 0; + } + + /* Calculate the session key while we're waiting. */ + + skey = t_servergetkey(ts, &A); + if (skey == NULL) { + return 0; + } + + /* Get the response from the client. */ + + i = recv(s, msgbuf, RESPONSE_LEN, MSG_WAITALL); + if (i <= 0) { + return 0; + } + if (t_serververify(ts, msgbuf) != 0) { + return 0; + } + + /* Client authenticated. Now authenticate ourselves to the client. */ + + if (send(s, t_serverresponse(ts), RESPONSE_LEN, 0) < 0) { + return 0; + } + + /* Copy the key and clean up. */ + + if (tsrp) { + memcpy(tsrp->username, username, strlen(username) + 1); + memcpy(tsrp->key, skey, SESSION_KEY_LEN); + } + t_serverclose(ts); + + return 1; +} diff --git a/package/network/services/ead/src/tinysrp/tinysrp.h b/package/network/services/ead/src/tinysrp/tinysrp.h new file mode 100644 index 0000000000..4420a196a3 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/tinysrp.h @@ -0,0 +1,18 @@ +/* Simple API for the tinysrp library. */ + +#ifndef T_PWD_H +#define MAXUSERLEN 32 +#define SESSION_KEY_LEN 40 /* 320-bit session key */ +#endif + +typedef struct { + char username[MAXUSERLEN + 1]; + unsigned char key[SESSION_KEY_LEN]; +} TSRP_SESSION; + +/* These functions are passed a connected socket, and return true for a +successful authentication. If tsrp is not NULL, the username and key +fields are filled in. */ + +extern int tsrp_server_authenticate(int s, TSRP_SESSION *tsrp); +extern int tsrp_client_authenticate(int s, char *user, char *pass, TSRP_SESSION *tsrp); diff --git a/package/network/services/ead/src/tinysrp/tpasswd b/package/network/services/ead/src/tinysrp/tpasswd new file mode 100644 index 0000000000..2ac7e2a1b6 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/tpasswd @@ -0,0 +1,2 @@ +moo:A9lHvOGAMJvw1m3vcDsQRUFovh6/QUmLDKqwhv.drKQzbE9nS7HrOZLUPx2MmS6ewwybN8RHqpWqnUJRCMFT14FMbYXR7kYNUUQNx43A7F.xrVOU7tlFq5NjoK9sfFtp6PMdbIOP5wzWmipiNFlCOu4sjlSZb.o7C1chLzTKU.0:19AI0Hc9jEkdFc:5 +new user:1FsanML2fbTOEsa072bLjyRD1LEqoRD2GwElfN0VmHeR.FAg5A.2.G5bTjIHmMmHL60kgoAHJZhRrgopalYmujlyAuQoKiHJb98SHm1oJaQ9nl/DrZCvfyw5LpVMqg.CupdiWz6OtmOz8fwC96ItExFnNDt6SmsVDIOn4HqXG6C0lLaqEvcqlN3gFDlJXyP2yldM.LJ1TkHTHmA3DjRkmWEUL3mWEgzkEHyPcRB3Jd5ncDT7jaNbJTTLRoOtgRsaqE7OXuPADoK8MGBcUquYBRrGwyU4Y/wW4gLc3QmV793zxkk.P3.dxkLSjro/Kk94D7kC6fx3K9tadLJyzd94rr:3v/KRlxT0.oYF1:1 diff --git a/package/network/services/ead/src/tinysrp/tphrase.c b/package/network/services/ead/src/tinysrp/tphrase.c new file mode 100644 index 0000000000..1aede0c832 --- /dev/null +++ b/package/network/services/ead/src/tinysrp/tphrase.c @@ -0,0 +1,348 @@ +/* Add passphrases to the tpasswd file. Use the last entry in the config +file by default or a particular one specified by index. */ + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/types.h> +#include <sys/stat.h> +#include "config.h" +#include "t_pwd.h" +#include "t_read.h" +#include "t_sha.h" +#include "t_defines.h" + +char *Progname; +char Usage[] = "usage: %s [-n configindex] [-p passfile] user\n"; +#define USAGE() fprintf(stderr, Usage, Progname) + +void doit(char *); + +int Configindex = -1; +char *Passfile = DEFAULT_PASSWD; + +int main(int argc, char **argv) +{ + int c; + + Progname = *argv; + + /* Parse option arguments. */ + + while ((c = getopt(argc, argv, "n:p:")) != EOF) { + switch (c) { + + case 'n': + Configindex = atoi(optarg); + break; + + case 'p': + Passfile = optarg; + break; + + default: + USAGE(); + exit(1); + } + } + argc -= optind; + argv += optind; + + if (argc != 1) { + USAGE(); + exit(1); + } + doit(argv[0]); + + return 0; +} + +void doit(char *name) +{ + char passphrase[128], passphrase1[128]; + FILE *f; + struct t_conf *tc; + struct t_confent *tcent; + struct t_pw eps_passwd; + + /* Get the config entry. */ + + if (Configindex <= 0) { + Configindex = t_getprecount(); + } + tcent = gettcid(Configindex); + if (tcent == NULL) { + fprintf(stderr, "Invalid configuration file entry.\n"); + exit(1); + } + + /* Ask for the passphrase twice. */ + + printf("Setting passphrase for %s\n", name); + + if (t_getpass(passphrase, sizeof(passphrase), "Enter passphrase: ") < 0) { + exit(1); + } + if (t_getpass(passphrase1, sizeof(passphrase1), "Verify: ") < 0) { + exit(1); + } + if (strcmp(passphrase, passphrase1) != 0) { + fprintf(stderr, "mismatch\n"); + exit(1); + } + + /* Create the passphrase verifier. */ + + t_makepwent(&eps_passwd, name, passphrase, NULL, tcent); + + /* Don't need these anymore. */ + + memset(passphrase, 0, sizeof(passphrase)); + memset(passphrase1, 0, sizeof(passphrase1)); + + /* See if the passphrase file is there; create it if not. */ + + if ((f = fopen(Passfile, "r+")) == NULL) { + creat(Passfile, 0400); + } else { + fclose(f); + } + + /* Change the passphrase. */ + + if (t_changepw(Passfile, &eps_passwd.pebuf) < 0) { + fprintf(stderr, "Error changing passphrase\n"); + exit(1); + } +} + +/* TODO: Implement a more general method to handle delete/change */ + +_TYPE( int ) +t_changepw(pwname, diff) + const char * pwname; + const struct t_pwent * diff; +{ + char * bakfile; + char * bakfile2; + struct stat st; + FILE * passfp; + FILE * bakfp; + + if(pwname == NULL) + pwname = DEFAULT_PASSWD; + + if((passfp = fopen(pwname, "rb")) == NULL || fstat(fileno(passfp), &st) < 0) + return -1; + + if((bakfile = malloc(strlen(pwname) + 5)) == NULL) { + fclose(passfp); + return -1; + } + else if((bakfile2 = malloc(strlen(pwname) + 5)) == NULL) { + fclose(passfp); + free(bakfile); + return -1; + } + + sprintf(bakfile, "%s.bak", pwname); + sprintf(bakfile2, "%s.sav", pwname); + + if((bakfp = fopen(bakfile2, "wb")) == NULL && + (unlink(bakfile2) < 0 || (bakfp = fopen(bakfile2, "wb")) == NULL)) { + fclose(passfp); + fclose(bakfp); + return -1; + } + +#ifdef NO_FCHMOD + chmod(bakfile2, st.st_mode & 0777); +#else + fchmod(fileno(bakfp), st.st_mode & 0777); +#endif + + t_pwcopy(bakfp, passfp, diff); + + fclose(bakfp); + fclose(passfp); + +#ifdef USE_RENAME + unlink(bakfile); + if(rename(pwname, bakfile) < 0) + return -1; + if(rename(bakfile2, pwname) < 0) + return -1; +#else + unlink(bakfile); + link(pwname, bakfile); + unlink(pwname); + link(bakfile2, pwname); + unlink(bakfile2); +#endif + free(bakfile); + free(bakfile2); + + return 0; +} + +_TYPE( struct t_pwent * ) +t_makepwent(tpw, user, pass, salt, confent) + struct t_pw * tpw; + const char * user; + const char * pass; + const struct t_num * salt; + const struct t_confent * confent; +{ + BigInteger x, v, n, g; + unsigned char dig[SHA_DIGESTSIZE]; + SHA1_CTX ctxt; + + tpw->pebuf.name = tpw->userbuf; + tpw->pebuf.password.data = tpw->pwbuf; + tpw->pebuf.salt.data = tpw->saltbuf; + + strncpy(tpw->pebuf.name, user, MAXUSERLEN); + tpw->pebuf.index = confent->index; + + if(salt) { + tpw->pebuf.salt.len = salt->len; + memcpy(tpw->pebuf.salt.data, salt->data, salt->len); + } + else { + memset(dig, 0, SALTLEN); /* salt is 80 bits */ + tpw->pebuf.salt.len = SALTLEN; + do { + t_random(tpw->pebuf.salt.data, SALTLEN); + } while(memcmp(tpw->pebuf.salt.data, dig, SALTLEN) == 0); + if(tpw->pebuf.salt.data[0] == 0) + tpw->pebuf.salt.data[0] = 0xff; + } + + n = BigIntegerFromBytes(confent->modulus.data, confent->modulus.len); + g = BigIntegerFromBytes(confent->generator.data, confent->generator.len); + v = BigIntegerFromInt(0); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, user, strlen(user)); + SHA1Update(&ctxt, ":", 1); + SHA1Update(&ctxt, pass, strlen(pass)); + SHA1Final(dig, &ctxt); + + SHA1Init(&ctxt); + SHA1Update(&ctxt, tpw->pebuf.salt.data, tpw->pebuf.salt.len); + SHA1Update(&ctxt, dig, sizeof(dig)); + SHA1Final(dig, &ctxt); + + /* x = H(s, H(u, ':', p)) */ + x = BigIntegerFromBytes(dig, sizeof(dig)); + + BigIntegerModExp(v, g, x, n); + tpw->pebuf.password.len = BigIntegerToBytes(v, tpw->pebuf.password.data); + + BigIntegerFree(v); + BigIntegerFree(x); + BigIntegerFree(g); + BigIntegerFree(n); + + return &tpw->pebuf; +} + +int +t_pwcopy(pwdest, pwsrc, diff) + FILE * pwdest; + FILE * pwsrc; + struct t_pwent * diff; +{ + struct t_pw * src; + struct t_pwent * ent; + + if((src = t_openpw(pwsrc)) == NULL) + return -1; + + while((ent = t_getpwent(src)) != NULL) + if(diff && strcmp(diff->name, ent->name) == 0) { + t_putpwent(diff, pwdest); + diff = NULL; + } + else + t_putpwent(ent, pwdest); + + if(diff) + t_putpwent(diff, pwdest); + + return 0; +} + +_TYPE( struct t_pwent * ) +t_getpwent(tpw) + struct t_pw * tpw; +{ + char indexbuf[16]; + char passbuf[MAXB64PARAMLEN]; + char saltstr[MAXB64SALTLEN]; + +#ifdef ENABLE_YP + struct t_passwd * nisent; + /* FIXME: should tell caller to get conf entry from NIS also */ + + if(tpw->state == IN_NIS) { + nisent = _yp_gettpent(); + if(nisent != NULL) { + savepwent(tpw, &nisent->tp); + return &tpw->pebuf; + } + tpw->state = FILE_NIS; + } +#endif + + while(1) { + if(t_nextfield(tpw->instream, tpw->userbuf, MAXUSERLEN) > 0) { +#ifdef ENABLE_YP + if(tpw->state == FILE_NIS && *tpw->userbuf == '+') { + t_nextline(tpw->instream); + if(strlen(tpw->userbuf) > 1) { /* +name:... */ + nisent = _yp_gettpnam(tpw->userbuf + 1); + if(nisent != NULL) { + savepwent(tpw, nisent); + return &tpw->pebuf; + } + } + else { /* +:... */ + tpw->state = IN_NIS; + _yp_settpent(); + return t_getpwent(tpw); + } + } +#endif + if(t_nextfield(tpw->instream, passbuf, MAXB64PARAMLEN) > 0 && + (tpw->pebuf.password.len = t_fromb64(tpw->pwbuf, passbuf)) > 0 && + t_nextfield(tpw->instream, saltstr, MAXB64SALTLEN) > 0 && + (tpw->pebuf.salt.len = t_fromb64(tpw->saltbuf, saltstr)) > 0 && + t_nextfield(tpw->instream, indexbuf, 16) > 0 && + (tpw->pebuf.index = atoi(indexbuf)) > 0) { + tpw->pebuf.name = tpw->userbuf; + tpw->pebuf.password.data = tpw->pwbuf; + tpw->pebuf.salt.data = tpw->saltbuf; + t_nextline(tpw->instream); + return &tpw->pebuf; + } + } + if(t_nextline(tpw->instream) < 0) + return NULL; + } +} + +_TYPE( void ) +t_putpwent(ent, fp) + const struct t_pwent * ent; + FILE * fp; +{ + char strbuf[MAXB64PARAMLEN]; + char saltbuf[MAXB64SALTLEN]; + + fprintf(fp, "%s:%s:%s:%d\n", ent->name, + t_tob64(strbuf, ent->password.data, ent->password.len), + t_tob64(saltbuf, ent->salt.data, ent->salt.len), ent->index); +} + |