From c446c5cc4ca8fdcf6e58ba6f7a5b03f93e62a212 Mon Sep 17 00:00:00 2001 From: "Pedro F. Giffuni" Date: Fri, 8 Jul 2016 03:39:10 +0000 Subject: [PATCH 01/86] Vendor GCC: Bring older verbatim version of cpuid.h This is mainly for reference: clang has a similar file with minor differences that may be affecting portability. Obtained from: GCC (gcc-4_3-branch, rev. 129548, pre GPLv3) --- gcc/config/i386/cpuid.h | 134 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 134 insertions(+) create mode 100644 gcc/config/i386/cpuid.h diff --git a/gcc/config/i386/cpuid.h b/gcc/config/i386/cpuid.h new file mode 100644 index 000000000000..7fa4f681547c --- /dev/null +++ b/gcc/config/i386/cpuid.h @@ -0,0 +1,134 @@ +/* + * Copyright (C) 2007 Free Software Foundation, Inc. + * + * This file 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. + * + * In addition to the permissions in the GNU General Public License, the + * Free Software Foundation gives you unlimited permission to link the + * compiled version of this file with other programs, and to distribute + * those programs without any restriction coming from the use of this + * file. (The General Public License restrictions do apply in other + * respects; for example, they cover modification of the file, and + * distribution when not linked into another program.) + * + * This file 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; see the file COPYING. If not, write to + * the Free Software Foundation, 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + * + * As a special exception, if you link this library with files + * compiled with GCC to produce an executable, this does not cause + * the resulting executable to be covered by the GNU General Public License. + * This exception does not however invalidate any other reasons why + * the executable file might be covered by the GNU General Public License. + */ + +/* %ecx */ +#define bit_SSE3 (1 << 0) +#define bit_SSSE3 (1 << 9) +#define bit_CMPXCHG16B (1 << 13) +#define bit_SSE4_1 (1 << 19) +#define bit_SSE4_2 (1 << 20) +#define bit_POPCNT (1 << 23) + +/* %edx */ +#define bit_CMPXCHG8B (1 << 8) +#define bit_CMOV (1 << 15) +#define bit_MMX (1 << 23) +#define bit_FXSAVE (1 << 24) +#define bit_SSE (1 << 25) +#define bit_SSE2 (1 << 26) + +/* Extended Features */ +/* %ecx */ +#define bit_LAHF_LM (1 << 0) +#define bit_SSE4a (1 << 6) +#define bit_SSE5 (1 << 11) + +/* %edx */ +#define bit_LM (1 << 29) +#define bit_3DNOWP (1 << 30) +#define bit_3DNOW (1 << 31) + + +#if defined(__i386__) && defined(__PIC__) +/* %ebx may be the PIC register. */ +#define __cpuid(level, a, b, c, d) \ + __asm__ ("xchg{l}\t{%%}ebx, %1\n\t" \ + "cpuid\n\t" \ + "xchg{l}\t{%%}ebx, %1\n\t" \ + : "=a" (a), "=r" (b), "=c" (c), "=d" (d) \ + : "0" (level)) +#else +#define __cpuid(level, a, b, c, d) \ + __asm__ ("cpuid\n\t" \ + : "=a" (a), "=b" (b), "=c" (c), "=d" (d) \ + : "0" (level)) +#endif + +/* Return highest supported input value for cpuid instruction. ext can + be either 0x0 or 0x8000000 to return highest supported value for + basic or extended cpuid information. Function returns 0 if cpuid + is not supported or whatever cpuid returns in eax register. If sig + pointer is non-null, then first four bytes of the signature + (as found in ebx register) are returned in location pointed by sig. */ + +static __inline unsigned int +__get_cpuid_max (unsigned int __ext, unsigned int *__sig) +{ + unsigned int __eax, __ebx, __ecx, __edx; + +#ifndef __x86_64__ + /* See if we can use cpuid. On AMD64 we always can. */ + __asm__ ("pushf{l|d}\n\t" + "pushf{l|d}\n\t" + "pop{l}\t%0\n\t" + "mov{l}\t{%0, %1|%1, %0}\n\t" + "xor{l}\t{%2, %0|%0, %2}\n\t" + "push{l}\t%0\n\t" + "popf{l|d}\n\t" + "pushf{l|d}\n\t" + "pop{l}\t%0\n\t" + "popf{l|d}\n\t" + : "=&r" (__eax), "=&r" (__ebx) + : "i" (0x00200000)); + + if (!((__eax ^ __ebx) & 0x00200000)) + return 0; +#endif + + /* Host supports cpuid. Return highest supported cpuid input value. */ + __cpuid (__ext, __eax, __ebx, __ecx, __edx); + + if (__sig) + *__sig = __ebx; + + return __eax; +} + +/* Return cpuid data for requested cpuid level, as found in returned + eax, ebx, ecx and edx registers. The function checks if cpuid is + supported and returns 1 for valid cpuid information or 0 for + unsupported cpuid level. All pointers are required to be non-null. */ + +static __inline int +__get_cpuid (unsigned int __level, + unsigned int *__eax, unsigned int *__ebx, + unsigned int *__ecx, unsigned int *__edx) +{ + unsigned int __ext = __level & 0x80000000; + + if (__get_cpuid_max (__ext, 0) < __level) + return 0; + + __cpuid (__level, *__eax, *__ebx, *__ecx, *__edx); + return 1; +} From adbe2685440d8971952c6f25daad7a1805338aaa Mon Sep 17 00:00:00 2001 From: Justin Hibbits Date: Tue, 30 Aug 2016 02:09:40 +0000 Subject: [PATCH 02/86] Attach and LAW problems to fix Summary: 1) Attach problem - mpc85xx_probe() relies on fact that 0xfff0 mask matches all QorIQ CPUs what is not true since e6500. This shall be reworked to match against all supported CPUs. 2) There is no any reason for operating system to re-program or anyhow else touch the LAWs programmed by firmware (u-boot). Right now mpc85xx_attach() removes all LaW entries except for DRAM. This causes MCE to be generated when later any of driver maps DTB-provided hardware addresses which do not exist anymore because corresponding LaWs were removed. Submitted by: Ivan Krivonos Differential Revision: https://reviews.freebsd.org/D7663 --- sys/powerpc/mpc85xx/platform_mpc85xx.c | 33 ++++++++------------------ 1 file changed, 10 insertions(+), 23 deletions(-) diff --git a/sys/powerpc/mpc85xx/platform_mpc85xx.c b/sys/powerpc/mpc85xx/platform_mpc85xx.c index 00c8a17b4439..972c3b166368 100644 --- a/sys/powerpc/mpc85xx/platform_mpc85xx.c +++ b/sys/powerpc/mpc85xx/platform_mpc85xx.c @@ -120,11 +120,16 @@ PLATFORM_DEF(mpc85xx_platform); static int mpc85xx_probe(platform_t plat) { - u_int pvr = mfpvr() >> 16; - - if ((pvr & 0xfff0) == FSL_E500v1) - return (BUS_PROBE_DEFAULT); + u_int pvr = (mfpvr() >> 16) & 0xFFFF; + switch (pvr) { + case FSL_E500v1: + case FSL_E500v2: + case FSL_E500mc: + case FSL_E5500: + case FSL_E6500: + return (BUS_PROBE_DEFAULT); + } return (ENXIO); } @@ -135,9 +140,8 @@ mpc85xx_attach(platform_t plat) const char *soc_name_guesses[] = {"/soc", "soc", NULL}; const char **name; pcell_t ranges[6], acells, pacells, scells; - uint32_t sr; uint64_t ccsrbar, ccsrsize; - int i, law_max, tgt; + int i; if ((cpus = OF_finddevice("/cpus")) != -1) { for (maxcpu = 0, child = OF_child(cpus); child != 0; @@ -194,23 +198,6 @@ mpc85xx_attach(platform_t plat) mpc85xx_fix_errata(ccsrbar_va); mpc85xx_enable_l3_cache(); - /* - * Clear local access windows. Skip DRAM entries, so we don't shoot - * ourselves in the foot. - */ - law_max = law_getmax(); - for (i = 0; i < law_max; i++) { - sr = ccsr_read4(OCP85XX_LAWSR(i)); - if ((sr & OCP85XX_ENA_MASK) == 0) - continue; - tgt = (sr & 0x01f00000) >> 20; - if (tgt == OCP85XX_TGTIF_RAM1 || tgt == OCP85XX_TGTIF_RAM2 || - tgt == OCP85XX_TGTIF_RAM_INTL) - continue; - - ccsr_write4(OCP85XX_LAWSR(i), sr & OCP85XX_DIS_MASK); - } - return (0); } From 8bb1a21b565ddb6ed9342bd08aa1fb9f4951e421 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 02:55:07 +0000 Subject: [PATCH 03/86] hyperv/hn: Move OIDs to net/rndis.h; they are standard NDIS OIDs. Actually all OIDs defined in net/rndis.h are standard NDIS OIDs. While I'm here, use the verbose macro name as in NDIS spec. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7679 --- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 5 +++-- sys/dev/hyperv/netvsc/ndis.h | 8 ++------ sys/net/rndis.h | 4 ++++ 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 1bffdba37c92..976340b8b092 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -941,7 +941,7 @@ hn_rndis_get_rsscaps(struct hn_softc *sc, int *rxr_cnt) in.ndis_hdr.ndis_size = NDIS_RSS_CAPS_SIZE; caps_len = NDIS_RSS_CAPS_SIZE; - error = hn_rndis_query(sc, OID_GEN_RSS_CAPABILITIES, + error = hn_rndis_query(sc, OID_GEN_RECEIVE_SCALE_CAPABILITIES, &in, NDIS_RSS_CAPS_SIZE, &caps, &caps_len); if (error) return (error); @@ -1092,7 +1092,8 @@ hn_rndis_conf_rss(struct hn_softc *sc, int nchan) for (i = 0; i < NDIS_HASH_INDCNT; ++i) rss->rss_ind[i] = i % nchan; - error = hn_rndis_set(sc, OID_GEN_RSS_PARAMETERS, rss, sizeof(*rss)); + error = hn_rndis_set(sc, OID_GEN_RECEIVE_SCALE_PARAMETERS, + rss, sizeof(*rss)); if (error) { if_printf(sc->hn_ifp, "RSS config failed: %d\n", error); } else { diff --git a/sys/dev/hyperv/netvsc/ndis.h b/sys/dev/hyperv/netvsc/ndis.h index e08952eb11b2..adf1db7ddb51 100644 --- a/sys/dev/hyperv/netvsc/ndis.h +++ b/sys/dev/hyperv/netvsc/ndis.h @@ -32,10 +32,6 @@ #define NDIS_MEDIA_STATE_CONNECTED 0 #define NDIS_MEDIA_STATE_DISCONNECTED 1 -#define OID_GEN_RSS_CAPABILITIES 0x00010203 -#define OID_GEN_RSS_PARAMETERS 0x00010204 -#define OID_TCP_OFFLOAD_PARAMETERS 0xFC01020C - #define NDIS_OBJTYPE_DEFAULT 0x80 #define NDIS_OBJTYPE_RSS_CAPS 0x88 #define NDIS_OBJTYPE_RSS_PARAMS 0x89 @@ -143,7 +139,7 @@ struct ndis_offload_params { #define NDIS_OFFLOAD_RSC_ON 2 /* - * OID_GEN_RSS_CAPABILITIES + * OID_GEN_RECEIVE_SCALE_CAPABILITIES * ndis_type: NDIS_OBJTYPE_RSS_CAPS */ struct ndis_rss_caps { @@ -174,7 +170,7 @@ struct ndis_rss_caps { #define NDIS_RSS_CAP_HASH_TOEPLITZ 0x00000001 /* - * OID_GEN_RSS_PARAMETERS + * OID_GEN_RECEIVE_SCALE_PARAMETERS * ndis_type: NDIS_OBJTYPE_RSS_PARAMS */ struct ndis_rss_params { diff --git a/sys/net/rndis.h b/sys/net/rndis.h index 5dd1d918b65e..0713a6ca5d82 100644 --- a/sys/net/rndis.h +++ b/sys/net/rndis.h @@ -62,6 +62,8 @@ #define OID_GEN_SUPPORTED_GUIDS 0x00010117 #define OID_GEN_NETWORK_LAYER_ADDRESSES 0x00010118 #define OID_GEN_TRANSPORT_HEADER_OFFSET 0x00010119 +#define OID_GEN_RECEIVE_SCALE_CAPABILITIES 0x00010203 +#define OID_GEN_RECEIVE_SCALE_PARAMETERS 0x00010204 #define OID_GEN_MACHINE_NAME 0x0001021A #define OID_GEN_RNDIS_CONFIG_PARAMETER 0x0001021B #define OID_GEN_VLAN_ID 0x0001021C @@ -82,6 +84,8 @@ #define OID_802_3_XMIT_TIMES_CRS_LOST 0x01020206 #define OID_802_3_XMIT_LATE_COLLISIONS 0x01020207 +#define OID_TCP_OFFLOAD_PARAMETERS 0xFC01020C + #define RNDIS_MEDIUM_802_3 0x00000000 /* Device flags */ From 77a48d615924a432c909f01abba57ed878153696 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 03:03:19 +0000 Subject: [PATCH 04/86] hyperv/hn: Indentation and field comment fixup for ndis.h. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7680 --- sys/dev/hyperv/netvsc/ndis.h | 179 +++++++++++++++++------------------ 1 file changed, 86 insertions(+), 93 deletions(-) diff --git a/sys/dev/hyperv/netvsc/ndis.h b/sys/dev/hyperv/netvsc/ndis.h index adf1db7ddb51..b5f9aa78f6ff 100644 --- a/sys/dev/hyperv/netvsc/ndis.h +++ b/sys/dev/hyperv/netvsc/ndis.h @@ -29,42 +29,41 @@ #ifndef _NET_NDIS_H_ #define _NET_NDIS_H_ -#define NDIS_MEDIA_STATE_CONNECTED 0 -#define NDIS_MEDIA_STATE_DISCONNECTED 1 +#define NDIS_MEDIA_STATE_CONNECTED 0 +#define NDIS_MEDIA_STATE_DISCONNECTED 1 -#define NDIS_OBJTYPE_DEFAULT 0x80 -#define NDIS_OBJTYPE_RSS_CAPS 0x88 -#define NDIS_OBJTYPE_RSS_PARAMS 0x89 - -/* common_set */ -#define NDIS_OFFLOAD_SET_NOCHG 0 -#define NDIS_OFFLOAD_SET_ON 1 -#define NDIS_OFFLOAD_SET_OFF 2 +#define NDIS_OFFLOAD_SET_NOCHG 0 +#define NDIS_OFFLOAD_SET_ON 1 +#define NDIS_OFFLOAD_SET_OFF 2 /* a.k.a GRE MAC */ -#define NDIS_ENCAP_TYPE_NVGRE 0x00000001 +#define NDIS_ENCAP_TYPE_NVGRE 0x00000001 -#define NDIS_HASH_FUNCTION_MASK 0x000000FF /* see hash function */ -#define NDIS_HASH_TYPE_MASK 0x00FFFF00 /* see hash type */ +#define NDIS_HASH_FUNCTION_MASK 0x000000FF /* see hash function */ +#define NDIS_HASH_TYPE_MASK 0x00FFFF00 /* see hash type */ /* hash function */ -#define NDIS_HASH_FUNCTION_TOEPLITZ 0x00000001 +#define NDIS_HASH_FUNCTION_TOEPLITZ 0x00000001 /* hash type */ -#define NDIS_HASH_IPV4 0x00000100 -#define NDIS_HASH_TCP_IPV4 0x00000200 -#define NDIS_HASH_IPV6 0x00000400 -#define NDIS_HASH_IPV6_EX 0x00000800 -#define NDIS_HASH_TCP_IPV6 0x00001000 -#define NDIS_HASH_TCP_IPV6_EX 0x00002000 +#define NDIS_HASH_IPV4 0x00000100 +#define NDIS_HASH_TCP_IPV4 0x00000200 +#define NDIS_HASH_IPV6 0x00000400 +#define NDIS_HASH_IPV6_EX 0x00000800 +#define NDIS_HASH_TCP_IPV6 0x00001000 +#define NDIS_HASH_TCP_IPV6_EX 0x00002000 -#define NDIS_HASH_KEYSIZE_TOEPLITZ 40 -#define NDIS_HASH_INDCNT 128 +#define NDIS_HASH_KEYSIZE_TOEPLITZ 40 +#define NDIS_HASH_INDCNT 128 + +#define NDIS_OBJTYPE_DEFAULT 0x80 +#define NDIS_OBJTYPE_RSS_CAPS 0x88 +#define NDIS_OBJTYPE_RSS_PARAMS 0x89 struct ndis_object_hdr { - uint8_t ndis_type; /* NDIS_OBJTYPE_ */ - uint8_t ndis_rev; /* type specific */ - uint16_t ndis_size; /* incl. this hdr */ + uint8_t ndis_type; /* NDIS_OBJTYPE_ */ + uint8_t ndis_rev; /* type specific */ + uint16_t ndis_size; /* incl. this hdr */ }; /* @@ -73,70 +72,64 @@ struct ndis_object_hdr { */ struct ndis_offload_params { struct ndis_object_hdr ndis_hdr; - uint8_t ndis_ip4csum; /* param_set */ - uint8_t ndis_tcp4csum; /* param_set */ - uint8_t ndis_udp4csum; /* param_set */ - uint8_t ndis_tcp6csum; /* param_set */ - uint8_t ndis_udp6csum; /* param_set */ - uint8_t ndis_lsov1; /* lsov1_set */ - uint8_t ndis_ipsecv1; /* ipsecv1_set */ - uint8_t ndis_lsov2_ip4; /* lsov2_set */ - uint8_t ndis_lsov2_ip6; /* lsov2_set */ - uint8_t ndis_tcp4conn; /* PARAM_NOCHG */ - uint8_t ndis_tcp6conn; /* PARAM_NOCHG */ - uint32_t ndis_flags; /* 0 */ + uint8_t ndis_ip4csum; /* NDIS_OFFLOAD_PARAM_ */ + uint8_t ndis_tcp4csum; /* NDIS_OFFLOAD_PARAM_ */ + uint8_t ndis_udp4csum; /* NDIS_OFFLOAD_PARAM_ */ + uint8_t ndis_tcp6csum; /* NDIS_OFFLOAD_PARAM_ */ + uint8_t ndis_udp6csum; /* NDIS_OFFLOAD_PARAM_ */ + uint8_t ndis_lsov1; /* NDIS_OFFLOAD_PARAM_ */ + uint8_t ndis_ipsecv1; /* NDIS_OFFLOAD_IPSECV1_ */ + uint8_t ndis_lsov2_ip4; /* NDIS_OFFLOAD_LSOV2_ */ + uint8_t ndis_lsov2_ip6; /* NDIS_OFFLOAD_LSOV2_ */ + uint8_t ndis_tcp4conn; /* 0 */ + uint8_t ndis_tcp6conn; /* 0 */ + uint32_t ndis_flags; /* 0 */ /* NDIS >= 6.1 */ - uint8_t ndis_ipsecv2; /* ipsecv2_set */ - uint8_t ndis_ipsecv2_ip4; /* ipsecv2_set */ + uint8_t ndis_ipsecv2; /* NDIS_OFFLOAD_IPSECV2_ */ + uint8_t ndis_ipsecv2_ip4;/* NDIS_OFFLOAD_IPSECV2_ */ /* NDIS >= 6.30 */ - uint8_t ndis_rsc_ip4; /* rsc_set */ - uint8_t ndis_rsc_ip6; /* rsc_set */ - uint8_t ndis_encap; /* common_set */ - uint8_t ndis_encap_types; /* NDIS_ENCAP_TYPE_ */ + uint8_t ndis_rsc_ip4; /* NDIS_OFFLOAD_RSC_ */ + uint8_t ndis_rsc_ip6; /* NDIS_OFFLOAD_RSC_ */ + uint8_t ndis_encap; /* NDIS_OFFLOAD_SET_ */ + uint8_t ndis_encap_types;/* NDIS_ENCAP_TYPE_ */ }; -#define NDIS_OFFLOAD_PARAMS_SIZE sizeof(struct ndis_offload_params) -#define NDIS_OFFLOAD_PARAMS_SIZE_6_1 \ +#define NDIS_OFFLOAD_PARAMS_SIZE sizeof(struct ndis_offload_params) +#define NDIS_OFFLOAD_PARAMS_SIZE_6_1 \ __offsetof(struct ndis_offload_params, ndis_rsc_ip4) -#define NDIS_OFFLOAD_PARAMS_REV_2 2 /* NDIS 6.1 */ -#define NDIS_OFFLOAD_PARAMS_REV_3 3 /* NDIS 6.30 */ +#define NDIS_OFFLOAD_PARAMS_REV_2 2 /* NDIS 6.1 */ +#define NDIS_OFFLOAD_PARAMS_REV_3 3 /* NDIS 6.30 */ -/* param_set */ -#define NDIS_OFFLOAD_PARAM_NOCHG 0 /* common to all sets */ -#define NDIS_OFFLOAD_PARAM_OFF 1 -#define NDIS_OFFLOAD_PARAM_TX 2 -#define NDIS_OFFLOAD_PARAM_RX 3 -#define NDIS_OFFLOAD_PARAM_TXRX 4 +#define NDIS_OFFLOAD_PARAM_NOCHG 0 /* common */ +#define NDIS_OFFLOAD_PARAM_OFF 1 +#define NDIS_OFFLOAD_PARAM_TX 2 +#define NDIS_OFFLOAD_PARAM_RX 3 +#define NDIS_OFFLOAD_PARAM_TXRX 4 -/* lsov1_set */ /* NDIS_OFFLOAD_PARAM_NOCHG */ -#define NDIS_OFFLOAD_LSOV1_OFF 1 -#define NDIS_OFFLOAD_LSOV1_ON 2 +#define NDIS_OFFLOAD_LSOV1_OFF 1 +#define NDIS_OFFLOAD_LSOV1_ON 2 -/* ipsecv1_set */ /* NDIS_OFFLOAD_PARAM_NOCHG */ -#define NDIS_OFFLOAD_IPSECV1_OFF 1 -#define NDIS_OFFLOAD_IPSECV1_AH 2 -#define NDIS_OFFLOAD_IPSECV1_ESP 3 -#define NDIS_OFFLOAD_IPSECV1_AH_ESP 4 +#define NDIS_OFFLOAD_IPSECV1_OFF 1 +#define NDIS_OFFLOAD_IPSECV1_AH 2 +#define NDIS_OFFLOAD_IPSECV1_ESP 3 +#define NDIS_OFFLOAD_IPSECV1_AH_ESP 4 -/* lsov2_set */ /* NDIS_OFFLOAD_PARAM_NOCHG */ -#define NDIS_OFFLOAD_LSOV2_OFF 1 -#define NDIS_OFFLOAD_LSOV2_ON 2 +#define NDIS_OFFLOAD_LSOV2_OFF 1 +#define NDIS_OFFLOAD_LSOV2_ON 2 -/* ipsecv2_set */ /* NDIS_OFFLOAD_PARAM_NOCHG */ -#define NDIS_OFFLOAD_IPSECV2_OFF 1 -#define NDIS_OFFLOAD_IPSECV2_AH 2 -#define NDIS_OFFLOAD_IPSECV2_ESP 3 -#define NDIS_OFFLOAD_IPSECV2_AH_ESP 4 +#define NDIS_OFFLOAD_IPSECV2_OFF 1 +#define NDIS_OFFLOAD_IPSECV2_AH 2 +#define NDIS_OFFLOAD_IPSECV2_ESP 3 +#define NDIS_OFFLOAD_IPSECV2_AH_ESP 4 -/* rsc_set */ /* NDIS_OFFLOAD_PARAM_NOCHG */ -#define NDIS_OFFLOAD_RSC_OFF 1 -#define NDIS_OFFLOAD_RSC_ON 2 +#define NDIS_OFFLOAD_RSC_OFF 1 +#define NDIS_OFFLOAD_RSC_ON 2 /* * OID_GEN_RECEIVE_SCALE_CAPABILITIES @@ -152,22 +145,22 @@ struct ndis_rss_caps { uint16_t ndis_pad; }; -#define NDIS_RSS_CAPS_SIZE \ +#define NDIS_RSS_CAPS_SIZE \ __offsetof(struct ndis_rss_caps, ndis_pad) -#define NDIS_RSS_CAPS_SIZE_6_0 \ +#define NDIS_RSS_CAPS_SIZE_6_0 \ __offsetof(struct ndis_rss_caps, ndis_nind) -#define NDIS_RSS_CAPS_REV_1 1 /* NDIS 6.{0,1,20} */ -#define NDIS_RSS_CAPS_REV_2 2 /* NDIS 6.30 */ +#define NDIS_RSS_CAPS_REV_1 1 /* NDIS 6.{0,1,20} */ +#define NDIS_RSS_CAPS_REV_2 2 /* NDIS 6.30 */ -#define NDIS_RSS_CAP_MSI 0x01000000 -#define NDIS_RSS_CAP_CLASSIFY_ISR 0x02000000 -#define NDIS_RSS_CAP_CLASSIFY_DPC 0x04000000 -#define NDIS_RSS_CAP_MSIX 0x08000000 -#define NDIS_RSS_CAP_IPV4 0x00000100 -#define NDIS_RSS_CAP_IPV6 0x00000200 -#define NDIS_RSS_CAP_IPV6_EX 0x00000400 -#define NDIS_RSS_CAP_HASH_TOEPLITZ 0x00000001 +#define NDIS_RSS_CAP_MSI 0x01000000 +#define NDIS_RSS_CAP_CLASSIFY_ISR 0x02000000 +#define NDIS_RSS_CAP_CLASSIFY_DPC 0x04000000 +#define NDIS_RSS_CAP_MSIX 0x08000000 +#define NDIS_RSS_CAP_IPV4 0x00000100 +#define NDIS_RSS_CAP_IPV6 0x00000200 +#define NDIS_RSS_CAP_IPV6_EX 0x00000400 +#define NDIS_RSS_CAP_HASH_TOEPLITZ 0x00000001 /* * OID_GEN_RECEIVE_SCALE_PARAMETERS @@ -188,18 +181,18 @@ struct ndis_rss_params { uint32_t ndis_cpumaskentsz; }; -#define NDIS_RSS_PARAMS_SIZE sizeof(struct ndis_rss_params) -#define NDIS_RSS_PARAMS_SIZE_6_0 \ +#define NDIS_RSS_PARAMS_SIZE sizeof(struct ndis_rss_params) +#define NDIS_RSS_PARAMS_SIZE_6_0 \ __offsetof(struct ndis_rss_params, ndis_cpumaskoffset) -#define NDIS_RSS_PARAMS_REV_1 1 /* NDIS 6.0 */ -#define NDIS_RSS_PARAMS_REV_2 2 /* NDIS 6.20 */ +#define NDIS_RSS_PARAMS_REV_1 1 /* NDIS 6.0 */ +#define NDIS_RSS_PARAMS_REV_2 2 /* NDIS 6.20 */ -#define NDIS_RSS_FLAG_BCPU_UNCHG 0x0001 -#define NDIS_RSS_FLAG_HASH_UNCHG 0x0002 -#define NDIS_RSS_FLAG_IND_UNCHG 0x0004 -#define NDIS_RSS_FLAG_KEY_UNCHG 0x0008 -#define NDIS_RSS_FLAG_DISABLE 0x0010 +#define NDIS_RSS_FLAG_BCPU_UNCHG 0x0001 +#define NDIS_RSS_FLAG_HASH_UNCHG 0x0002 +#define NDIS_RSS_FLAG_IND_UNCHG 0x0004 +#define NDIS_RSS_FLAG_KEY_UNCHG 0x0008 +#define NDIS_RSS_FLAG_DISABLE 0x0010 /* non-standard convenient struct */ struct ndis_rssprm_toeplitz { From 1010113dadcf7c8a1bcd6510848b0c398deb7868 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 03:11:07 +0000 Subject: [PATCH 05/86] net/rndis: Packet types are defined by NDIS; not RNDIS specific. Reviewed by: hps MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7681 --- sys/dev/hyperv/netvsc/hv_rndis.h | 13 ------------- sys/dev/usb/net/if_urndis.c | 4 ++-- sys/net/rndis.h | 24 ++++++++++++------------ 3 files changed, 14 insertions(+), 27 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis.h b/sys/dev/hyperv/netvsc/hv_rndis.h index 64beeb3854e5..6524340bb80d 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis.h +++ b/sys/dev/hyperv/netvsc/hv_rndis.h @@ -889,19 +889,6 @@ typedef struct rndismp_rx_bufs_info_ { #define RNDIS_HEADER_SIZE (sizeof(rndis_msg) - sizeof(rndis_msg_container)) -#define NDIS_PACKET_TYPE_DIRECTED 0x00000001 -#define NDIS_PACKET_TYPE_MULTICAST 0x00000002 -#define NDIS_PACKET_TYPE_ALL_MULTICAST 0x00000004 -#define NDIS_PACKET_TYPE_BROADCAST 0x00000008 -#define NDIS_PACKET_TYPE_SOURCE_ROUTING 0x00000010 -#define NDIS_PACKET_TYPE_PROMISCUOUS 0x00000020 -#define NDIS_PACKET_TYPE_SMT 0x00000040 -#define NDIS_PACKET_TYPE_ALL_LOCAL 0x00000080 -#define NDIS_PACKET_TYPE_GROUP 0x00000100 -#define NDIS_PACKET_TYPE_ALL_FUNCTIONAL 0x00000200 -#define NDIS_PACKET_TYPE_FUNCTIONAL 0x00000400 -#define NDIS_PACKET_TYPE_MAC_FRAME 0x00000800 - /* * Externs */ diff --git a/sys/dev/usb/net/if_urndis.c b/sys/dev/usb/net/if_urndis.c index 2c94d95616cf..f030476e1846 100644 --- a/sys/dev/usb/net/if_urndis.c +++ b/sys/dev/usb/net/if_urndis.c @@ -292,8 +292,8 @@ urndis_attach(device_t dev) memcpy(&sc->sc_ue.ue_eaddr, buf, ETHER_ADDR_LEN); /* Initialize packet filter */ - sc->sc_filter = RNDIS_PACKET_TYPE_BROADCAST | - RNDIS_PACKET_TYPE_ALL_MULTICAST; + sc->sc_filter = NDIS_PACKET_TYPE_BROADCAST | + NDIS_PACKET_TYPE_ALL_MULTICAST; msg.ibuf.filter = htole32(sc->sc_filter); URNDIS_LOCK(sc); error = urndis_ctrl_set(sc, OID_GEN_CURRENT_PACKET_FILTER, diff --git a/sys/net/rndis.h b/sys/net/rndis.h index 0713a6ca5d82..3a51454bfe9b 100644 --- a/sys/net/rndis.h +++ b/sys/net/rndis.h @@ -266,18 +266,18 @@ struct rndis_keepalive_comp { }; /* packet filter bits used by OID_GEN_CURRENT_PACKET_FILTER */ -#define RNDIS_PACKET_TYPE_DIRECTED 0x00000001 -#define RNDIS_PACKET_TYPE_MULTICAST 0x00000002 -#define RNDIS_PACKET_TYPE_ALL_MULTICAST 0x00000004 -#define RNDIS_PACKET_TYPE_BROADCAST 0x00000008 -#define RNDIS_PACKET_TYPE_SOURCE_ROUTING 0x00000010 -#define RNDIS_PACKET_TYPE_PROMISCUOUS 0x00000020 -#define RNDIS_PACKET_TYPE_SMT 0x00000040 -#define RNDIS_PACKET_TYPE_ALL_LOCAL 0x00000080 -#define RNDIS_PACKET_TYPE_GROUP 0x00001000 -#define RNDIS_PACKET_TYPE_ALL_FUNCTIONAL 0x00002000 -#define RNDIS_PACKET_TYPE_FUNCTIONAL 0x00004000 -#define RNDIS_PACKET_TYPE_MAC_FRAME 0x00008000 +#define NDIS_PACKET_TYPE_DIRECTED 0x00000001 +#define NDIS_PACKET_TYPE_MULTICAST 0x00000002 +#define NDIS_PACKET_TYPE_ALL_MULTICAST 0x00000004 +#define NDIS_PACKET_TYPE_BROADCAST 0x00000008 +#define NDIS_PACKET_TYPE_SOURCE_ROUTING 0x00000010 +#define NDIS_PACKET_TYPE_PROMISCUOUS 0x00000020 +#define NDIS_PACKET_TYPE_SMT 0x00000040 +#define NDIS_PACKET_TYPE_ALL_LOCAL 0x00000080 +#define NDIS_PACKET_TYPE_GROUP 0x00001000 +#define NDIS_PACKET_TYPE_ALL_FUNCTIONAL 0x00002000 +#define NDIS_PACKET_TYPE_FUNCTIONAL 0x00004000 +#define NDIS_PACKET_TYPE_MAC_FRAME 0x00008000 /* RNDIS offsets */ #define RNDIS_HEADER_OFFSET 8 /* bytes */ From 05bbfc3062e5c4af91c43722fb953a6c45607a90 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 03:40:22 +0000 Subject: [PATCH 06/86] hyperv/hn: Switch to new RNDIS set for RX filters. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7683 --- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 150 +++++------------------- 1 file changed, 30 insertions(+), 120 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 976340b8b092..47c1e730c53d 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -81,10 +81,7 @@ static void hv_rf_receive_data(struct hn_rx_ring *rxr, const void *data, int dlen); static inline int hv_rf_query_device_mac(rndis_device *device); static inline int hv_rf_query_device_link_status(rndis_device *device); -static int hv_rf_set_packet_filter(rndis_device *device, uint32_t new_filter); static int hv_rf_init_device(rndis_device *device); -static int hv_rf_open_device(rndis_device *device); -static int hv_rf_close_device(rndis_device *device); int hv_rf_send_offload_request(struct hn_softc *sc, rndis_offload_params *offloads); @@ -679,72 +676,6 @@ static uint8_t netvsc_hash_key[NDIS_HASH_KEYSIZE_TOEPLITZ] = { 0x6a, 0x42, 0xb7, 0x3b, 0xbe, 0xac, 0x01, 0xfa }; -/* - * RNDIS filter set packet filter - * Sends an rndis request with the new filter, then waits for a response - * from the host. - * Returns zero on success, non-zero on failure. - */ -static int -hv_rf_set_packet_filter(rndis_device *device, uint32_t new_filter) -{ - rndis_request *request; - rndis_set_request *set; - rndis_set_complete *set_complete; - uint32_t status; - int ret; - - request = hv_rndis_request(device, REMOTE_NDIS_SET_MSG, - RNDIS_MESSAGE_SIZE(rndis_set_request) + sizeof(uint32_t)); - if (request == NULL) { - ret = -1; - goto cleanup; - } - - /* Set up the rndis set */ - set = &request->request_msg.msg.set_request; - set->oid = RNDIS_OID_GEN_CURRENT_PACKET_FILTER; - set->info_buffer_length = sizeof(uint32_t); - set->info_buffer_offset = sizeof(rndis_set_request); - - memcpy((void *)((unsigned long)set + sizeof(rndis_set_request)), - &new_filter, sizeof(uint32_t)); - - ret = hv_rf_send_request(device, request, REMOTE_NDIS_SET_MSG); - if (ret != 0) { - goto cleanup; - } - - /* - * Wait for the response from the host. Another thread will signal - * us when the response has arrived. In the failure case, - * sema_timedwait() returns a non-zero status after waiting 5 seconds. - */ - ret = sema_timedwait(&request->wait_sema, 5 * hz); - if (ret == 0) { - /* Response received, check status */ - set_complete = &request->response_msg.msg.set_complete; - status = set_complete->status; - if (status != RNDIS_STATUS_SUCCESS) { - /* Bad response status, return error */ - ret = -2; - } - } else { - /* - * We cannot deallocate the request since we may still - * receive a send completion for it. - */ - goto exit; - } - -cleanup: - if (request != NULL) { - hv_put_rndis_request(device, request); - } -exit: - return (ret); -} - static const void * hn_rndis_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, uint32_t rid, size_t reqlen, size_t *comp_len0, uint32_t comp_type) @@ -1103,6 +1034,25 @@ hn_rndis_conf_rss(struct hn_softc *sc, int nchan) return (error); } +static int +hn_rndis_set_rxfilter(struct hn_softc *sc, uint32_t filter) +{ + int error; + + error = hn_rndis_set(sc, OID_GEN_CURRENT_PACKET_FILTER, + &filter, sizeof(filter)); + if (error) { + if_printf(sc->hn_ifp, "set RX filter 0x%08x failed: %d\n", + filter, error); + } else { + if (bootverbose) { + if_printf(sc->hn_ifp, "set RX filter 0x%08x done\n", + filter); + } + } + return (error); +} + /* * RNDIS filter init device */ @@ -1210,55 +1160,6 @@ hv_rf_halt_device(rndis_device *device) return (0); } -/* - * RNDIS filter open device - */ -static int -hv_rf_open_device(rndis_device *device) -{ - int ret; - - if (device->state != RNDIS_DEV_INITIALIZED) { - return (0); - } - - if (hv_promisc_mode != 1) { - ret = hv_rf_set_packet_filter(device, - NDIS_PACKET_TYPE_BROADCAST | - NDIS_PACKET_TYPE_ALL_MULTICAST | - NDIS_PACKET_TYPE_DIRECTED); - } else { - ret = hv_rf_set_packet_filter(device, - NDIS_PACKET_TYPE_PROMISCUOUS); - } - - if (ret == 0) { - device->state = RNDIS_DEV_DATAINITIALIZED; - } - - return (ret); -} - -/* - * RNDIS filter close device - */ -static int -hv_rf_close_device(rndis_device *device) -{ - int ret; - - if (device->state != RNDIS_DEV_DATAINITIALIZED) { - return (0); - } - - ret = hv_rf_set_packet_filter(device, 0); - if (ret == 0) { - device->state = RNDIS_DEV_INITIALIZED; - } - - return (ret); -} - /* * RNDIS filter on device add */ @@ -1442,8 +1343,17 @@ hv_rf_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel) int hv_rf_on_open(struct hn_softc *sc) { + uint32_t filter; - return (hv_rf_open_device(sc->rndis_dev)); + /* XXX */ + if (hv_promisc_mode != 1) { + filter = NDIS_PACKET_TYPE_BROADCAST | + NDIS_PACKET_TYPE_ALL_MULTICAST | + NDIS_PACKET_TYPE_DIRECTED; + } else { + filter = NDIS_PACKET_TYPE_PROMISCUOUS; + } + return (hn_rndis_set_rxfilter(sc, filter)); } /* @@ -1453,7 +1363,7 @@ int hv_rf_on_close(struct hn_softc *sc) { - return (hv_rf_close_device(sc->rndis_dev)); + return (hn_rndis_set_rxfilter(sc, 0)); } static void From c7359ebb0ccfb398570d753720cd4e81d503977f Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 03:55:43 +0000 Subject: [PATCH 07/86] hyperv/hn: Remove unused function MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7684 --- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 75 ------------------------- 1 file changed, 75 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 47c1e730c53d..b7aa303c4723 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -82,9 +82,6 @@ static void hv_rf_receive_data(struct hn_rx_ring *rxr, static inline int hv_rf_query_device_mac(rndis_device *device); static inline int hv_rf_query_device_link_status(rndis_device *device); static int hv_rf_init_device(rndis_device *device); -int -hv_rf_send_offload_request(struct hn_softc *sc, - rndis_offload_params *offloads); static void hn_rndis_sent_halt(struct hn_send_ctx *sndc, struct hn_softc *sc, struct vmbus_channel *chan, @@ -352,78 +349,6 @@ hv_rf_receive_response(rndis_device *device, const rndis_msg *response) } } -int -hv_rf_send_offload_request(struct hn_softc *sc, - rndis_offload_params *offloads) -{ - rndis_request *request; - rndis_set_request *set; - rndis_offload_params *offload_req; - rndis_set_complete *set_complete; - rndis_device *rndis_dev = sc->rndis_dev; - device_t dev = sc->hn_dev; - uint32_t extlen = sizeof(rndis_offload_params); - int ret; - - if (sc->hn_nvs_ver <= NVSP_PROTOCOL_VERSION_4) { - extlen = VERSION_4_OFFLOAD_SIZE; - /* On NVSP_PROTOCOL_VERSION_4 and below, we do not support - * UDP checksum offload. - */ - offloads->udp_ipv4_csum = 0; - offloads->udp_ipv6_csum = 0; - } - - request = hv_rndis_request(rndis_dev, REMOTE_NDIS_SET_MSG, - RNDIS_MESSAGE_SIZE(rndis_set_request) + extlen); - if (!request) - return (ENOMEM); - - set = &request->request_msg.msg.set_request; - set->oid = RNDIS_OID_TCP_OFFLOAD_PARAMETERS; - set->info_buffer_length = extlen; - set->info_buffer_offset = sizeof(rndis_set_request); - set->device_vc_handle = 0; - - offload_req = (rndis_offload_params *)((unsigned long)set + - set->info_buffer_offset); - *offload_req = *offloads; - offload_req->header.type = RNDIS_OBJECT_TYPE_DEFAULT; - offload_req->header.revision = RNDIS_OFFLOAD_PARAMETERS_REVISION_3; - offload_req->header.size = extlen; - - ret = hv_rf_send_request(rndis_dev, request, REMOTE_NDIS_SET_MSG); - if (ret != 0) { - device_printf(dev, "hv send offload request failed, ret=%d!\n", - ret); - goto cleanup; - } - - ret = sema_timedwait(&request->wait_sema, 5 * hz); - if (ret != 0) { - device_printf(dev, "hv send offload request timeout\n"); - goto cleanup; - } - - set_complete = &request->response_msg.msg.set_complete; - if (set_complete->status == RNDIS_STATUS_SUCCESS) { - device_printf(dev, "hv send offload request succeeded\n"); - ret = 0; - } else { - if (set_complete->status == RNDIS_STATUS_NOT_SUPPORTED) { - device_printf(dev, "HV Not support offload\n"); - ret = 0; - } else { - ret = set_complete->status; - } - } - -cleanup: - hv_put_rndis_request(rndis_dev, request); - - return (ret); -} - /* * RNDIS filter receive indicate status */ From 63d98d54aa2d16d6147494152f6dd508bd86a307 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 04:04:29 +0000 Subject: [PATCH 08/86] hyperv/hn: Factor out func to exec RNDIS transaction w/o checking result It will be used by RNDIS HALT and RESET. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7685 --- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 37 +++++++++++++++++-------- 1 file changed, 26 insertions(+), 11 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index b7aa303c4723..3e04136773b6 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -602,20 +602,15 @@ static uint8_t netvsc_hash_key[NDIS_HASH_KEYSIZE_TOEPLITZ] = { }; static const void * -hn_rndis_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, uint32_t rid, - size_t reqlen, size_t *comp_len0, uint32_t comp_type) +hn_rndis_xact_exec1(struct hn_softc *sc, struct vmbus_xact *xact, size_t reqlen, + struct hn_send_ctx *sndc, size_t *comp_len) { struct vmbus_gpa gpa[HN_XACT_REQ_PGCNT]; - const struct rndis_comp_hdr *comp; - bus_addr_t paddr; - size_t comp_len, min_complen = *comp_len0; int gpa_cnt, error; + bus_addr_t paddr; - KASSERT(rid > HN_RNDIS_RID_COMPAT_MAX, ("invalid rid %u\n", rid)); KASSERT(reqlen <= HN_XACT_REQ_SIZE && reqlen > 0, ("invalid request length %zu", reqlen)); - KASSERT(min_complen >= sizeof(*comp), - ("invalid minimum complete len %zu", min_complen)); /* * Setup the SG list. @@ -644,14 +639,34 @@ hn_rndis_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, uint32_t rid * message. */ vmbus_xact_activate(xact); - error = hv_nv_on_send(sc->hn_prichan, HN_NVS_RNDIS_MTYPE_CTRL, - &hn_send_ctx_none, gpa, gpa_cnt); + error = hv_nv_on_send(sc->hn_prichan, HN_NVS_RNDIS_MTYPE_CTRL, sndc, + gpa, gpa_cnt); if (error) { vmbus_xact_deactivate(xact); if_printf(sc->hn_ifp, "RNDIS ctrl send failed: %d\n", error); return (NULL); } - comp = vmbus_xact_wait(xact, &comp_len); + return (vmbus_xact_wait(xact, comp_len)); +} + +static const void * +hn_rndis_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, uint32_t rid, + size_t reqlen, size_t *comp_len0, uint32_t comp_type) +{ + const struct rndis_comp_hdr *comp; + size_t comp_len, min_complen = *comp_len0; + + KASSERT(rid > HN_RNDIS_RID_COMPAT_MAX, ("invalid rid %u\n", rid)); + KASSERT(min_complen >= sizeof(*comp), + ("invalid minimum complete len %zu", min_complen)); + + /* + * Execute the xact setup by the caller. + */ + comp = hn_rndis_xact_exec1(sc, xact, reqlen, &hn_send_ctx_none, + &comp_len); + if (comp == NULL) + return (NULL); /* * Check this RNDIS complete message. From 1eeba644f0f159bff1632004a0e1331e337e4f70 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 05:09:26 +0000 Subject: [PATCH 09/86] hyperv/hn: Switch to new RNDIS transaction execution for halt. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7686 --- sys/dev/hyperv/netvsc/hv_net_vsc.c | 4 +- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 206 +++--------------------- sys/dev/hyperv/netvsc/if_hnvar.h | 2 + 3 files changed, 23 insertions(+), 189 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_net_vsc.c b/sys/dev/hyperv/netvsc/hv_net_vsc.c index e1552cc84261..9518824508ce 100644 --- a/sys/dev/hyperv/netvsc/hv_net_vsc.c +++ b/sys/dev/hyperv/netvsc/hv_net_vsc.c @@ -74,8 +74,6 @@ static void hv_nv_on_receive(struct hn_softc *sc, static void hn_nvs_sent_none(struct hn_send_ctx *sndc, struct hn_softc *, struct vmbus_channel *chan, const void *, int); -static void hn_nvs_sent_xact(struct hn_send_ctx *, struct hn_softc *sc, - struct vmbus_channel *, const void *, int); struct hn_send_ctx hn_send_ctx_none = HN_SEND_CTX_INITIALIZER(hn_nvs_sent_none, NULL); @@ -655,7 +653,7 @@ hv_nv_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel) return (0); } -static void +void hn_nvs_sent_xact(struct hn_send_ctx *sndc, struct hn_softc *sc __unused, struct vmbus_channel *chan __unused, const void *data, int dlen) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 3e04136773b6..b45b33ec4d6e 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -71,8 +71,6 @@ __FBSDID("$FreeBSD$"); /* * Forward declarations */ -static int hv_rf_send_request(rndis_device *device, rndis_request *request, - uint32_t message_type); static void hv_rf_receive_response(rndis_device *device, const rndis_msg *response); static void hv_rf_receive_indicate_status(rndis_device *device, @@ -83,12 +81,6 @@ static inline int hv_rf_query_device_mac(rndis_device *device); static inline int hv_rf_query_device_link_status(rndis_device *device); static int hv_rf_init_device(rndis_device *device); -static void hn_rndis_sent_halt(struct hn_send_ctx *sndc, - struct hn_softc *sc, struct vmbus_channel *chan, - const void *data, int dlen); -static void hn_rndis_sent_cb(struct hn_send_ctx *sndc, - struct hn_softc *sc, struct vmbus_channel *chan, - const void *data, int dlen); static int hn_rndis_query(struct hn_softc *sc, uint32_t oid, const void *idata, size_t idlen, void *odata, size_t *odlen0); static int hn_rndis_set(struct hn_softc *sc, uint32_t oid, const void *data, @@ -196,120 +188,6 @@ hv_put_rndis_device(rndis_device *device) free(device, M_NETVSC); } -/* - * - */ -static inline rndis_request * -hv_rndis_request(rndis_device *device, uint32_t message_type, - uint32_t message_length) -{ - rndis_request *request; - rndis_msg *rndis_mesg; - rndis_set_request *set; - - request = malloc(sizeof(rndis_request), M_NETVSC, M_WAITOK | M_ZERO); - - sema_init(&request->wait_sema, 0, "rndis sema"); - - rndis_mesg = &request->request_msg; - rndis_mesg->ndis_msg_type = message_type; - rndis_mesg->msg_len = message_length; - - /* - * Set the request id. This field is always after the rndis header - * for request/response packet types so we just use the set_request - * as a template. - */ - set = &rndis_mesg->msg.set_request; - set->request_id = atomic_fetchadd_int(&device->new_request_id, 1) & - HN_RNDIS_RID_COMPAT_MASK; - - /* Add to the request list */ - mtx_lock(&device->req_lock); - STAILQ_INSERT_TAIL(&device->myrequest_list, request, mylist_entry); - mtx_unlock(&device->req_lock); - - return (request); -} - -/* - * - */ -static inline void -hv_put_rndis_request(rndis_device *device, rndis_request *request) -{ - mtx_lock(&device->req_lock); - /* Fixme: Has O(n) performance */ - /* - * XXXKYS: Use Doubly linked lists. - */ - STAILQ_REMOVE(&device->myrequest_list, request, rndis_request_, - mylist_entry); - mtx_unlock(&device->req_lock); - - sema_destroy(&request->wait_sema); - free(request, M_NETVSC); -} - -/* - * - */ -static int -hv_rf_send_request(rndis_device *device, rndis_request *request, - uint32_t message_type) -{ - struct hn_softc *sc = device->sc; - uint32_t send_buf_section_idx, tot_data_buf_len; - struct vmbus_gpa gpa[2]; - int gpa_cnt, send_buf_section_size; - hn_sent_callback_t cb; - - /* Set up the packet to send it */ - tot_data_buf_len = request->request_msg.msg_len; - - gpa_cnt = 1; - gpa[0].gpa_page = hv_get_phys_addr(&request->request_msg) >> PAGE_SHIFT; - gpa[0].gpa_len = request->request_msg.msg_len; - gpa[0].gpa_ofs = (unsigned long)&request->request_msg & (PAGE_SIZE - 1); - - if (gpa[0].gpa_ofs + gpa[0].gpa_len > PAGE_SIZE) { - gpa_cnt = 2; - gpa[0].gpa_len = PAGE_SIZE - gpa[0].gpa_ofs; - gpa[1].gpa_page = - hv_get_phys_addr((char*)&request->request_msg + - gpa[0].gpa_len) >> PAGE_SHIFT; - gpa[1].gpa_ofs = 0; - gpa[1].gpa_len = request->request_msg.msg_len - gpa[0].gpa_len; - } - - if (message_type != REMOTE_NDIS_HALT_MSG) - cb = hn_rndis_sent_cb; - else - cb = hn_rndis_sent_halt; - - if (tot_data_buf_len < sc->hn_chim_szmax) { - send_buf_section_idx = hn_chim_alloc(sc); - if (send_buf_section_idx != HN_NVS_CHIM_IDX_INVALID) { - uint8_t *dest = sc->hn_chim + - (send_buf_section_idx * sc->hn_chim_szmax); - - memcpy(dest, &request->request_msg, request->request_msg.msg_len); - send_buf_section_size = tot_data_buf_len; - gpa_cnt = 0; - goto sendit; - } - /* Failed to allocate chimney send buffer; move on */ - } - send_buf_section_idx = HN_NVS_CHIM_IDX_INVALID; - send_buf_section_size = 0; - -sendit: - hn_send_ctx_init(&request->send_ctx, cb, request, - send_buf_section_idx, send_buf_section_size); - return hv_nv_on_send(sc->hn_prichan, HN_NVS_RNDIS_MTYPE_CTRL, - &request->send_ctx, gpa, gpa_cnt); -} - /* * RNDIS filter receive response */ @@ -1052,51 +930,34 @@ hv_rf_init_device(rndis_device *device) return (error); } -#define HALT_COMPLETION_WAIT_COUNT 25 - /* * RNDIS filter halt device */ static int -hv_rf_halt_device(rndis_device *device) +hv_rf_halt_device(struct hn_softc *sc) { - rndis_request *request; - int i, ret; + struct vmbus_xact *xact; + struct rndis_halt_req *halt; + struct hn_send_ctx sndc; + size_t comp_len; - /* Attempt to do a rndis device halt */ - request = hv_rndis_request(device, REMOTE_NDIS_HALT_MSG, - RNDIS_MESSAGE_SIZE(rndis_halt_request)); - if (request == NULL) { - return (-1); + xact = vmbus_xact_get(sc->hn_xact, sizeof(*halt)); + if (xact == NULL) { + if_printf(sc->hn_ifp, "no xact for RNDIS halt\n"); + return (ENXIO); } + halt = vmbus_xact_req_data(xact); + halt->rm_type = REMOTE_NDIS_HALT_MSG; + halt->rm_len = sizeof(*halt); + halt->rm_rid = hn_rndis_rid(sc); - /* initialize "poor man's semaphore" */ - request->halt_complete_flag = 0; - - ret = hv_rf_send_request(device, request, REMOTE_NDIS_HALT_MSG); - if (ret != 0) { - return (-1); - } - - /* - * Wait for halt response from halt callback. We must wait for - * the transaction response before freeing the request and other - * resources. - */ - for (i=HALT_COMPLETION_WAIT_COUNT; i > 0; i--) { - if (request->halt_complete_flag != 0) { - break; - } - DELAY(400); - } - if (i == 0) { - return (-1); - } - - device->state = RNDIS_DEV_UNINITIALIZED; - - hv_put_rndis_request(device, request); + /* No RNDIS completion; rely on NVS message send completion */ + hn_send_ctx_init_simple(&sndc, hn_nvs_sent_xact, xact); + hn_rndis_xact_exec1(sc, xact, sizeof(*halt), &sndc, &comp_len); + vmbus_xact_put(xact); + if (bootverbose) + if_printf(sc->hn_ifp, "RNDIS halt done\n"); return (0); } @@ -1266,7 +1127,7 @@ hv_rf_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel) int ret; /* Halt and release the rndis device */ - ret = hv_rf_halt_device(rndis_dev); + ret = hv_rf_halt_device(sc); sc->rndis_dev = NULL; hv_put_rndis_device(rndis_dev); @@ -1306,33 +1167,6 @@ hv_rf_on_close(struct hn_softc *sc) return (hn_rndis_set_rxfilter(sc, 0)); } -static void -hn_rndis_sent_cb(struct hn_send_ctx *sndc, struct hn_softc *sc, - struct vmbus_channel *chan __unused, const void *data __unused, - int dlen __unused) -{ - if (sndc->hn_chim_idx != HN_NVS_CHIM_IDX_INVALID) - hn_chim_free(sc, sndc->hn_chim_idx); -} - -static void -hn_rndis_sent_halt(struct hn_send_ctx *sndc, struct hn_softc *sc, - struct vmbus_channel *chan __unused, const void *data __unused, - int dlen __unused) -{ - rndis_request *request = sndc->hn_cbarg; - - if (sndc->hn_chim_idx != HN_NVS_CHIM_IDX_INVALID) - hn_chim_free(sc, sndc->hn_chim_idx); - - /* - * Notify hv_rf_halt_device() about halt completion. - * The halt code must wait for completion before freeing - * the transaction resources. - */ - request->halt_complete_flag = 1; -} - void hv_rf_channel_rollup(struct hn_rx_ring *rxr, struct hn_tx_ring *txr) { diff --git a/sys/dev/hyperv/netvsc/if_hnvar.h b/sys/dev/hyperv/netvsc/if_hnvar.h index a819db3fbc31..90fc00b7e43e 100644 --- a/sys/dev/hyperv/netvsc/if_hnvar.h +++ b/sys/dev/hyperv/netvsc/if_hnvar.h @@ -112,6 +112,8 @@ struct vmbus_xact; const void *hn_nvs_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, void *req, int reqlen, size_t *resp_len); +void hn_nvs_sent_xact(struct hn_send_ctx *sndc, struct hn_softc *sc, + struct vmbus_channel *chan, const void *data, int dlen); uint32_t hn_chim_alloc(struct hn_softc *sc); void hn_chim_free(struct hn_softc *sc, uint32_t chim_idx); From 574e2cdce78d0bf74e8bea5c99365c585f65371c Mon Sep 17 00:00:00 2001 From: Kevin Lo Date: Tue, 30 Aug 2016 05:15:42 +0000 Subject: [PATCH 10/86] Zap M_IOVEC. Reviewed by: Matthew Macy --- sys/sys/mbuf.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sys/sys/mbuf.h b/sys/sys/mbuf.h index 6feccda085b8..5df745af36c8 100644 --- a/sys/sys/mbuf.h +++ b/sys/sys/mbuf.h @@ -391,7 +391,7 @@ struct mbuf { #define EXT_JUMBO9 4 /* jumbo cluster 9216 bytes */ #define EXT_JUMBO16 5 /* jumbo cluster 16184 bytes */ #define EXT_PACKET 6 /* mbuf+cluster from packet zone */ -#define EXT_MBUF 7 /* external mbuf reference (M_IOVEC) */ +#define EXT_MBUF 7 /* external mbuf reference */ #define EXT_SFBUF_NOCACHE 8 /* sendfile(2)'s sf_buf not to be cached */ #define EXT_VENDOR1 224 /* for vendor-internal use */ From ecb735a3ac8e4871312c112dc307018e2f31c6b9 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 05:21:34 +0000 Subject: [PATCH 11/86] hyperv/hn: Remove the useless rndis_device and related bits MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7687 --- sys/dev/hyperv/netvsc/hv_net_vsc.c | 2 +- sys/dev/hyperv/netvsc/hv_net_vsc.h | 8 +- sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c | 18 +- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 163 ++++-------------- sys/dev/hyperv/netvsc/hv_rndis_filter.h | 76 +------- 5 files changed, 44 insertions(+), 223 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_net_vsc.c b/sys/dev/hyperv/netvsc/hv_net_vsc.c index 9518824508ce..27e52f55351b 100644 --- a/sys/dev/hyperv/netvsc/hv_net_vsc.c +++ b/sys/dev/hyperv/netvsc/hv_net_vsc.c @@ -641,7 +641,7 @@ hv_nv_on_device_add(struct hn_softc *sc, struct hn_rx_ring *rxr) * Net VSC on device remove */ int -hv_nv_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel) +hv_nv_on_device_remove(struct hn_softc *sc) { hv_nv_disconnect_from_vsp(sc); diff --git a/sys/dev/hyperv/netvsc/hv_net_vsc.h b/sys/dev/hyperv/netvsc/hv_net_vsc.h index 16fbef0eb3ee..b4688ce3828b 100644 --- a/sys/dev/hyperv/netvsc/hv_net_vsc.h +++ b/sys/dev/hyperv/netvsc/hv_net_vsc.h @@ -237,8 +237,8 @@ typedef void (*pfn_on_send_rx_completion)(struct vmbus_channel *, void *); #define TRANSPORT_TYPE_IPV6_UDP ((TYPE_IPV6 << 16) | TYPE_UDP) typedef struct { - uint8_t mac_addr[6]; /* Assumption unsigned long */ - uint8_t link_state; + uint8_t mac_addr[ETHER_ADDR_LEN]; + uint32_t link_state; } netvsc_device_info; #define HN_XACT_REQ_PGCNT 2 @@ -351,7 +351,6 @@ typedef struct hn_softc { int hn_initdone; /* See hv_netvsc_drv_freebsd.c for rules on how to use */ int temp_unusable; - struct rndis_device_ *rndis_dev; struct vmbus_channel *hn_prichan; int hn_rx_ring_cnt; @@ -400,8 +399,7 @@ struct hn_send_ctx; void netvsc_linkstatus_callback(struct hn_softc *sc, uint32_t status); int hv_nv_on_device_add(struct hn_softc *sc, struct hn_rx_ring *rxr); -int hv_nv_on_device_remove(struct hn_softc *sc, - boolean_t destroy_channel); +int hv_nv_on_device_remove(struct hn_softc *sc); int hv_nv_on_send(struct vmbus_channel *chan, uint32_t rndis_mtype, struct hn_send_ctx *sndc, struct vmbus_gpa *gpa, int gpa_cnt); void hv_nv_subchan_attach(struct vmbus_channel *chan, diff --git a/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c b/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c index 24aa310f6e94..17094ce9c2e4 100644 --- a/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c +++ b/sys/dev/hyperv/netvsc/hv_netvsc_drv_freebsd.c @@ -154,8 +154,8 @@ __FBSDID("$FreeBSD$"); #define HN_TX_DATA_BOUNDARY PAGE_SIZE #define HN_TX_DATA_MAXSIZE IP_MAXPACKET #define HN_TX_DATA_SEGSIZE PAGE_SIZE -#define HN_TX_DATA_SEGCNT_MAX \ - (NETVSC_PACKET_MAXPAGE - HV_RF_NUM_TX_RESERVED_PAGE_BUFS) +/* -1 for RNDIS packet message */ +#define HN_TX_DATA_SEGCNT_MAX (NETVSC_PACKET_MAXPAGE - 1) #define HN_DIRECT_TX_SIZE_DEF 128 @@ -651,7 +651,7 @@ netvsc_detach(device_t dev) * the netdevice. */ - hv_rf_on_device_remove(sc, HV_RF_NV_DESTROY_CHANNEL); + hv_rf_on_device_remove(sc); hn_stop_tx_tasks(sc); @@ -1029,7 +1029,8 @@ hn_encap(struct hn_tx_ring *txr, struct hn_txdesc *txd, struct mbuf **m_head0) } *m_head0 = m_head; - txr->hn_gpa_cnt = nsegs + HV_RF_NUM_TX_RESERVED_PAGE_BUFS; + /* +1 RNDIS packet message */ + txr->hn_gpa_cnt = nsegs + 1; /* send packet with page buffer */ txr->hn_gpa[0].gpa_page = atop(txd->rndis_msg_paddr); @@ -1037,12 +1038,11 @@ hn_encap(struct hn_tx_ring *txr, struct hn_txdesc *txd, struct mbuf **m_head0) txr->hn_gpa[0].gpa_len = rndis_msg_size; /* - * Fill the page buffers with mbuf info starting at index - * HV_RF_NUM_TX_RESERVED_PAGE_BUFS. + * Fill the page buffers with mbuf info after the page + * buffer for RNDIS packet message. */ for (i = 0; i < nsegs; ++i) { - struct vmbus_gpa *gpa = &txr->hn_gpa[ - i + HV_RF_NUM_TX_RESERVED_PAGE_BUFS]; + struct vmbus_gpa *gpa = &txr->hn_gpa[i + 1]; gpa->gpa_page = atop(segs[i].ds_addr); gpa->gpa_ofs = segs[i].ds_addr & PAGE_MASK; @@ -1576,7 +1576,7 @@ hn_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data) * MTU to take effect. This includes tearing down, but not * deleting the channel, then bringing it back up. */ - error = hv_rf_on_device_remove(sc, HV_RF_NV_RETAIN_CHANNEL); + error = hv_rf_on_device_remove(sc); if (error) { NV_LOCK(sc); sc->temp_unusable = FALSE; diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index b45b33ec4d6e..647c04bb37b9 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -71,15 +71,14 @@ __FBSDID("$FreeBSD$"); /* * Forward declarations */ -static void hv_rf_receive_response(rndis_device *device, - const rndis_msg *response); -static void hv_rf_receive_indicate_status(rndis_device *device, +static void hv_rf_receive_indicate_status(struct hn_softc *sc, const rndis_msg *response); static void hv_rf_receive_data(struct hn_rx_ring *rxr, const void *data, int dlen); -static inline int hv_rf_query_device_mac(rndis_device *device); -static inline int hv_rf_query_device_link_status(rndis_device *device); -static int hv_rf_init_device(rndis_device *device); +static int hv_rf_query_device_mac(struct hn_softc *sc, uint8_t *eaddr); +static int hv_rf_query_device_link_status(struct hn_softc *sc, + uint32_t *link_status); +static int hv_rf_init_device(struct hn_softc *sc); static int hn_rndis_query(struct hn_softc *sc, uint32_t oid, const void *idata, size_t idlen, void *odata, size_t *odlen0); @@ -157,94 +156,24 @@ hv_get_ppi_data(rndis_packet *rpkt, uint32_t type) return (NULL); } - -/* - * Allow module_param to work and override to switch to promiscuous mode. - */ -static inline rndis_device * -hv_get_rndis_device(void) -{ - rndis_device *device; - - device = malloc(sizeof(rndis_device), M_NETVSC, M_WAITOK | M_ZERO); - - mtx_init(&device->req_lock, "HV-FRL", NULL, MTX_DEF); - - /* Same effect as STAILQ_HEAD_INITIALIZER() static initializer */ - STAILQ_INIT(&device->myrequest_list); - - device->state = RNDIS_DEV_UNINITIALIZED; - - return (device); -} - -/* - * - */ -static inline void -hv_put_rndis_device(rndis_device *device) -{ - mtx_destroy(&device->req_lock); - free(device, M_NETVSC); -} - -/* - * RNDIS filter receive response - */ -static void -hv_rf_receive_response(rndis_device *device, const rndis_msg *response) -{ - rndis_request *request = NULL; - rndis_request *next_request; - boolean_t found = FALSE; - - mtx_lock(&device->req_lock); - request = STAILQ_FIRST(&device->myrequest_list); - while (request != NULL) { - /* - * All request/response message contains request_id as the - * first field - */ - if (request->request_msg.msg.init_request.request_id == - response->msg.init_complete.request_id) { - found = TRUE; - break; - } - next_request = STAILQ_NEXT(request, mylist_entry); - request = next_request; - } - mtx_unlock(&device->req_lock); - - if (found) { - if (response->msg_len <= sizeof(rndis_msg)) { - memcpy(&request->response_msg, response, - response->msg_len); - } else { - request->response_msg.msg.init_complete.status = - RNDIS_STATUS_BUFFER_OVERFLOW; - } - sema_post(&request->wait_sema); - } -} - /* * RNDIS filter receive indicate status */ static void -hv_rf_receive_indicate_status(rndis_device *device, const rndis_msg *response) +hv_rf_receive_indicate_status(struct hn_softc *sc, const rndis_msg *response) { const rndis_indicate_status *indicate = &response->msg.indicate_status; switch(indicate->status) { case RNDIS_STATUS_MEDIA_CONNECT: - netvsc_linkstatus_callback(device->sc, 1); + netvsc_linkstatus_callback(sc, 1); break; case RNDIS_STATUS_MEDIA_DISCONNECT: - netvsc_linkstatus_callback(device->sc, 0); + netvsc_linkstatus_callback(sc, 0); break; default: /* TODO: */ - device_printf(device->sc->hn_dev, + if_printf(sc->hn_ifp, "unknown status %d received\n", indicate->status); break; } @@ -374,14 +303,9 @@ int hv_rf_on_receive(struct hn_softc *sc, struct hn_rx_ring *rxr, const void *data, int dlen) { - rndis_device *rndis_dev; const rndis_msg *rndis_hdr; const struct rndis_comp_hdr *comp; - rndis_dev = sc->rndis_dev; - if (rndis_dev->state == RNDIS_DEV_UNINITIALIZED) - return (EINVAL); - rndis_hdr = data; switch (rndis_hdr->ndis_msg_type) { /* data message */ @@ -395,17 +319,14 @@ hv_rf_on_receive(struct hn_softc *sc, struct hn_rx_ring *rxr, case REMOTE_NDIS_SET_CMPLT: case REMOTE_NDIS_KEEPALIVE_CMPLT: comp = data; - if (comp->rm_rid <= HN_RNDIS_RID_COMPAT_MAX) { - /* Transition time compat code */ - hv_rf_receive_response(rndis_dev, rndis_hdr); - } else { - vmbus_xact_ctx_wakeup(sc->hn_xact, data, dlen); - } + KASSERT(comp->rm_rid > HN_RNDIS_RID_COMPAT_MAX, + ("invalid rid 0x%08x\n", comp->rm_rid)); + vmbus_xact_ctx_wakeup(sc->hn_xact, comp, dlen); break; /* notification message */ case REMOTE_NDIS_INDICATE_STATUS_MSG: - hv_rf_receive_indicate_status(rndis_dev, rndis_hdr); + hv_rf_receive_indicate_status(sc, rndis_hdr); break; case REMOTE_NDIS_RESET_CMPLT: @@ -431,19 +352,18 @@ hv_rf_on_receive(struct hn_softc *sc, struct hn_rx_ring *rxr, * RNDIS filter query device MAC address */ static int -hv_rf_query_device_mac(rndis_device *device) +hv_rf_query_device_mac(struct hn_softc *sc, uint8_t *eaddr) { - struct hn_softc *sc = device->sc; - size_t hwaddr_len; + size_t eaddr_len; int error; - hwaddr_len = ETHER_ADDR_LEN; + eaddr_len = ETHER_ADDR_LEN; error = hn_rndis_query(sc, OID_802_3_PERMANENT_ADDRESS, NULL, 0, - device->hw_mac_addr, &hwaddr_len); + eaddr, &eaddr_len); if (error) return (error); - if (hwaddr_len != ETHER_ADDR_LEN) { - if_printf(sc->hn_ifp, "invalid hwaddr len %zu\n", hwaddr_len); + if (eaddr_len != ETHER_ADDR_LEN) { + if_printf(sc->hn_ifp, "invalid eaddr len %zu\n", eaddr_len); return (EINVAL); } return (0); @@ -452,16 +372,15 @@ hv_rf_query_device_mac(rndis_device *device) /* * RNDIS filter query device link status */ -static inline int -hv_rf_query_device_link_status(rndis_device *device) +static int +hv_rf_query_device_link_status(struct hn_softc *sc, uint32_t *link_status) { - struct hn_softc *sc = device->sc; size_t size; int error; - size = sizeof(uint32_t); + size = sizeof(*link_status); error = hn_rndis_query(sc, OID_GEN_MEDIA_CONNECT_STATUS, NULL, 0, - &device->link_status, &size); + link_status, &size); if (error) return (error); if (size != sizeof(uint32_t)) { @@ -875,9 +794,8 @@ hn_rndis_set_rxfilter(struct hn_softc *sc, uint32_t filter) * RNDIS filter init device */ static int -hv_rf_init_device(rndis_device *device) +hv_rf_init_device(struct hn_softc *sc) { - struct hn_softc *sc = device->sc; struct rndis_init_req *req; const struct rndis_init_comp *comp; struct vmbus_xact *xact; @@ -885,9 +803,6 @@ hv_rf_init_device(rndis_device *device) uint32_t rid; int error; - /* XXX */ - device->state = RNDIS_DEV_INITIALIZED; - xact = vmbus_xact_get(sc->hn_xact, sizeof(*req)); if (xact == NULL) { if_printf(sc->hn_ifp, "no xact for RNDIS init\n"); @@ -969,7 +884,6 @@ hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, int *nchan0, struct hn_rx_ring *rxr) { int ret; - rndis_device *rndis_dev; netvsc_device_info *dev_info = (netvsc_device_info *)additl_info; device_t dev = sc->hn_dev; struct hn_nvs_subch_req *req; @@ -980,13 +894,6 @@ hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, int nchan = *nchan0; int rxr_cnt; - rndis_dev = hv_get_rndis_device(); - if (rndis_dev == NULL) { - return (ENOMEM); - } - sc->rndis_dev = rndis_dev; - rndis_dev->sc = sc; - /* * Let the inner driver handle this first to create the netvsc channel * NOTE! Once the channel is created, we may get a receive callback @@ -994,17 +901,15 @@ hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, * Note: Earlier code used a function pointer here. */ ret = hv_nv_on_device_add(sc, rxr); - if (ret != 0) { - hv_put_rndis_device(rndis_dev); + if (ret != 0) return (ret); - } /* * Initialize the rndis device */ /* Send the rndis initialization message */ - ret = hv_rf_init_device(rndis_dev); + ret = hv_rf_init_device(sc); if (ret != 0) { /* * TODO: If rndis init failed, we will need to shut down @@ -1013,19 +918,15 @@ hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, } /* Get the mac address */ - ret = hv_rf_query_device_mac(rndis_dev); + ret = hv_rf_query_device_mac(sc, dev_info->mac_addr); if (ret != 0) { /* TODO: shut down rndis device and the channel */ } /* Configure NDIS offload settings */ hn_rndis_conf_offload(sc); - - memcpy(dev_info->mac_addr, rndis_dev->hw_mac_addr, ETHER_ADDR_LEN); - hv_rf_query_device_link_status(rndis_dev); - - dev_info->link_state = rndis_dev->link_status; + hv_rf_query_device_link_status(sc, &dev_info->link_state); if (sc->hn_ndis_ver < NDIS_VERSION_6_30 || nchan == 1) { /* @@ -1121,19 +1022,15 @@ hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, * RNDIS filter on device remove */ int -hv_rf_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel) +hv_rf_on_device_remove(struct hn_softc *sc) { - rndis_device *rndis_dev = sc->rndis_dev; int ret; /* Halt and release the rndis device */ ret = hv_rf_halt_device(sc); - sc->rndis_dev = NULL; - hv_put_rndis_device(rndis_dev); - /* Pass control to inner driver to remove the device */ - ret |= hv_nv_on_device_remove(sc, destroy_channel); + ret |= hv_nv_on_device_remove(sc); return (ret); } diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.h b/sys/dev/hyperv/netvsc/hv_rndis_filter.h index d8dce9509b06..82c4d7587bb6 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.h +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.h @@ -35,80 +35,6 @@ #include #include -/* - * Defines - */ - -/* Destroy or preserve channel on filter/netvsc teardown */ -#define HV_RF_NV_DESTROY_CHANNEL TRUE -#define HV_RF_NV_RETAIN_CHANNEL FALSE - -/* - * Number of page buffers to reserve for the RNDIS filter packet in the - * transmitted message. - */ -#define HV_RF_NUM_TX_RESERVED_PAGE_BUFS 1 - - -/* - * Data types - */ - -typedef enum { - RNDIS_DEV_UNINITIALIZED = 0, - RNDIS_DEV_INITIALIZING, - RNDIS_DEV_INITIALIZED, - RNDIS_DEV_DATAINITIALIZED, -} rndis_device_state; - -typedef struct rndis_request_ { - STAILQ_ENTRY(rndis_request_) mylist_entry; - struct sema wait_sema; - - /* - * The max response size is sizeof(rndis_msg) + PAGE_SIZE. - * - * XXX - * This is ugly and should be cleaned up once we busdma-fy - * RNDIS request bits. - */ - rndis_msg response_msg; - uint8_t buf_resp[PAGE_SIZE]; - - /* Simplify allocation by having a netvsc packet inline */ - struct hn_send_ctx send_ctx; - - /* - * The max request size is sizeof(rndis_msg) + PAGE_SIZE. - * - * NOTE: - * This is required for the large request like RSS settings. - * - * XXX - * This is ugly and should be cleaned up once we busdma-fy - * RNDIS request bits. - */ - rndis_msg request_msg; - uint8_t buf_req[PAGE_SIZE]; - - /* Fixme: Poor man's semaphore. */ - uint32_t halt_complete_flag; -} rndis_request; - -typedef struct rndis_device_ { - struct hn_softc *sc; - - rndis_device_state state; - uint32_t link_status; - uint32_t new_request_id; - - struct mtx req_lock; - - STAILQ_HEAD(RQ, rndis_request_) myrequest_list; - - uint8_t hw_mac_addr[ETHER_ADDR_LEN]; -} rndis_device; - /* * Externs */ @@ -119,7 +45,7 @@ int hv_rf_on_receive(struct hn_softc *sc, struct hn_rx_ring *rxr, void hv_rf_channel_rollup(struct hn_rx_ring *rxr, struct hn_tx_ring *txr); int hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, int *nchan, struct hn_rx_ring *rxr); -int hv_rf_on_device_remove(struct hn_softc *sc, boolean_t destroy_channel); +int hv_rf_on_device_remove(struct hn_softc *sc); int hv_rf_on_open(struct hn_softc *sc); int hv_rf_on_close(struct hn_softc *sc); From fa021050df311f609a10d6823744664b72ee50fe Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 05:35:19 +0000 Subject: [PATCH 12/86] hyperv/hn: Log packet message alignment. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7689 --- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 647c04bb37b9..397a72c762d7 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -833,9 +833,10 @@ hv_rf_init_device(struct hn_softc *sc) goto done; } if (bootverbose) { - if_printf(sc->hn_ifp, "RNDIS ver %u.%u, pktsz %u, pktcnt %u\n", - comp->rm_ver_major, comp->rm_ver_minor, - comp->rm_pktmaxsz, comp->rm_pktmaxcnt); + if_printf(sc->hn_ifp, "RNDIS ver %u.%u, pktsz %u, pktcnt %u, " + "align %u\n", comp->rm_ver_major, comp->rm_ver_minor, + comp->rm_pktmaxsz, comp->rm_pktmaxcnt, + 1U << comp->rm_align); } error = 0; From 96376f14a95d348c1fc284bda87fa92616689d37 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Tue, 30 Aug 2016 05:47:58 +0000 Subject: [PATCH 13/86] hyperv/hn: Remove unnecessary NULL check. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7690 --- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 397a72c762d7..5c81740ba2c8 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -839,10 +839,8 @@ hv_rf_init_device(struct hn_softc *sc) 1U << comp->rm_align); } error = 0; - done: - if (xact != NULL) - vmbus_xact_put(xact); + vmbus_xact_put(xact); return (error); } From 7447ca0eb235974642312b9555caec00b57d8fc1 Mon Sep 17 00:00:00 2001 From: Mark Johnston Date: Tue, 30 Aug 2016 05:50:42 +0000 Subject: [PATCH 14/86] Recursively enumerate anonymous structs and unions in ctf_member_info(). Previously, ctf_member_info() would ignore members belonging to an anonymous struct or union. This made it impossible to, for example, trace the m_next field of an mbuf using DTrace. Reported and tested by: gallatin MFC after: 2 weeks --- .../opensolaris/common/ctf/ctf_types.c | 31 ++++++++++++++----- 1 file changed, 24 insertions(+), 7 deletions(-) diff --git a/cddl/contrib/opensolaris/common/ctf/ctf_types.c b/cddl/contrib/opensolaris/common/ctf/ctf_types.c index ab1b9ff14bd2..21b061cd9356 100644 --- a/cddl/contrib/opensolaris/common/ctf/ctf_types.c +++ b/cddl/contrib/opensolaris/common/ctf/ctf_types.c @@ -644,11 +644,8 @@ ctf_type_compat(ctf_file_t *lfp, ctf_id_t ltype, } } -/* - * Return the type and offset for a given member of a STRUCT or UNION. - */ -int -ctf_member_info(ctf_file_t *fp, ctf_id_t type, const char *name, +static int +_ctf_member_info(ctf_file_t *fp, ctf_id_t type, const char *name, ulong_t off, ctf_membinfo_t *mip) { ctf_file_t *ofp = fp; @@ -673,9 +670,13 @@ ctf_member_info(ctf_file_t *fp, ctf_id_t type, const char *name, ((uintptr_t)tp + increment); for (n = LCTF_INFO_VLEN(fp, tp->ctt_info); n != 0; n--, mp++) { + if (mp->ctm_name == 0 && + _ctf_member_info(fp, mp->ctm_type, name, + mp->ctm_offset + off, mip) == 0) + return (0); if (strcmp(ctf_strptr(fp, mp->ctm_name), name) == 0) { mip->ctm_type = mp->ctm_type; - mip->ctm_offset = mp->ctm_offset; + mip->ctm_offset = mp->ctm_offset + off; return (0); } } @@ -684,9 +685,14 @@ ctf_member_info(ctf_file_t *fp, ctf_id_t type, const char *name, ((uintptr_t)tp + increment); for (n = LCTF_INFO_VLEN(fp, tp->ctt_info); n != 0; n--, lmp++) { + if (lmp->ctlm_name == 0 && + _ctf_member_info(fp, lmp->ctlm_name, name, + (ulong_t)CTF_LMEM_OFFSET(lmp) + off, mip) == 0) + return (0); if (strcmp(ctf_strptr(fp, lmp->ctlm_name), name) == 0) { mip->ctm_type = lmp->ctlm_type; - mip->ctm_offset = (ulong_t)CTF_LMEM_OFFSET(lmp); + mip->ctm_offset = + (ulong_t)CTF_LMEM_OFFSET(lmp) + off; return (0); } } @@ -695,6 +701,17 @@ ctf_member_info(ctf_file_t *fp, ctf_id_t type, const char *name, return (ctf_set_errno(ofp, ECTF_NOMEMBNAM)); } +/* + * Return the type and offset for a given member of a STRUCT or UNION. + */ +int +ctf_member_info(ctf_file_t *fp, ctf_id_t type, const char *name, + ctf_membinfo_t *mip) +{ + + return (_ctf_member_info(fp, type, name, 0, mip)); +} + /* * Return the array type, index, and size information for the specified ARRAY. */ From 915d1b71cd7f7b440c4bb03e8317a20f246cd73e Mon Sep 17 00:00:00 2001 From: Mark Johnston Date: Tue, 30 Aug 2016 05:56:21 +0000 Subject: [PATCH 15/86] Restore swap pager readahead after r292373. The removal of vm_fault_additional_pages() meant that a hard fault on a swap-backed page would result in only that page being read in. This change implements readahead and readbehind for the swap pager in swap_pager_getpages(). swap_pager_haspage() is modified to return the largest contiguous non-resident range of pages containing the requested range. Reviewed by: alc, kib Tested by: pho MFC after: 1 month Differential Revision: https://reviews.freebsd.org/D7677 --- sys/vm/swap_pager.c | 190 +++++++++++++++++++++++++------------------- sys/vm/vm_page.c | 4 +- 2 files changed, 109 insertions(+), 85 deletions(-) diff --git a/sys/vm/swap_pager.c b/sys/vm/swap_pager.c index 97fdbc9691f8..b797f46037cf 100644 --- a/sys/vm/swap_pager.c +++ b/sys/vm/swap_pager.c @@ -990,22 +990,21 @@ swap_pager_copy(vm_object_t srcobject, vm_object_t dstobject, * page and return TRUE if it does, FALSE if it doesn't. * * If TRUE, we also try to determine how much valid, contiguous backing - * store exists before and after the requested page within a reasonable - * distance. We do not try to restrict it to the swap device stripe - * (that is handled in getpages/putpages). It probably isn't worth - * doing here. + * store exists before and after the requested page. */ static boolean_t -swap_pager_haspage(vm_object_t object, vm_pindex_t pindex, int *before, int *after) +swap_pager_haspage(vm_object_t object, vm_pindex_t pindex, int *before, + int *after) { - daddr_t blk0; + daddr_t blk, blk0; + int i; VM_OBJECT_ASSERT_LOCKED(object); + /* * do we have good backing store at the requested index ? */ blk0 = swp_pager_meta_ctl(object, pindex, 0); - if (blk0 == SWAPBLK_NONE) { if (before) *before = 0; @@ -1018,34 +1017,26 @@ swap_pager_haspage(vm_object_t object, vm_pindex_t pindex, int *before, int *aft * find backwards-looking contiguous good backing store */ if (before != NULL) { - int i; - - for (i = 1; i < (SWB_NPAGES/2); ++i) { - daddr_t blk; - + for (i = 1; i < SWB_NPAGES; i++) { if (i > pindex) break; blk = swp_pager_meta_ctl(object, pindex - i, 0); if (blk != blk0 - i) break; } - *before = (i - 1); + *before = i - 1; } /* * find forward-looking contiguous good backing store */ if (after != NULL) { - int i; - - for (i = 1; i < (SWB_NPAGES/2); ++i) { - daddr_t blk; - + for (i = 1; i < SWB_NPAGES; i++) { blk = swp_pager_meta_ctl(object, pindex + i, 0); if (blk != blk0 + i) break; } - *after = (i - 1); + *after = i - 1; } return (TRUE); } @@ -1077,62 +1068,107 @@ swap_pager_unswapped(vm_page_t m) } /* - * SWAP_PAGER_GETPAGES() - bring pages in from swap + * swap_pager_getpages() - bring pages in from swap * - * Attempt to retrieve (m, count) pages from backing store, but make - * sure we retrieve at least m[reqpage]. We try to load in as large - * a chunk surrounding m[reqpage] as is contiguous in swap and which - * belongs to the same object. + * Attempt to page in the pages in array "m" of length "count". The caller + * may optionally specify that additional pages preceding and succeeding + * the specified range be paged in. The number of such pages is returned + * in the "rbehind" and "rahead" parameters, and they will be in the + * inactive queue upon return. * - * The code is designed for asynchronous operation and - * immediate-notification of 'reqpage' but tends not to be - * used that way. Please do not optimize-out this algorithmic - * feature, I intend to improve on it in the future. - * - * The parent has a single vm_object_pip_add() reference prior to - * calling us and we should return with the same. - * - * The parent has BUSY'd the pages. We should return with 'm' - * left busy, but the others adjusted. + * The pages in "m" must be busied and will remain busied upon return. */ static int swap_pager_getpages(vm_object_t object, vm_page_t *m, int count, int *rbehind, int *rahead) { struct buf *bp; + vm_page_t mpred, msucc, p; + vm_pindex_t pindex; daddr_t blk; + int i, j, reqcount, shift; - /* - * Calculate range to retrieve. The pages have already been assigned - * their swapblks. We require a *contiguous* range but we know it to - * not span devices. If we do not supply it, bad things - * happen. Note that blk, iblk & jblk can be SWAPBLK_NONE, but the - * loops are set up such that the case(s) are handled implicitly. - * - * The swp_*() calls must be made with the object locked. - */ - blk = swp_pager_meta_ctl(m[0]->object, m[0]->pindex, 0); + reqcount = count; - if (blk == SWAPBLK_NONE) - return (VM_PAGER_FAIL); - -#ifdef INVARIANTS - for (int i = 0; i < count; i++) - KASSERT(blk + i == - swp_pager_meta_ctl(m[i]->object, m[i]->pindex, 0), - ("%s: range is not contiguous", __func__)); -#endif - - /* - * Getpbuf() can sleep. - */ VM_OBJECT_WUNLOCK(object); - /* - * Get a swap buffer header to perform the IO - */ bp = getpbuf(&nsw_rcount); - bp->b_flags |= B_PAGING; + VM_OBJECT_WLOCK(object); + if (!swap_pager_haspage(object, m[0]->pindex, rbehind, rahead)) { + relpbuf(bp, &nsw_rcount); + return (VM_PAGER_FAIL); + } + + /* + * Clip the readahead and readbehind ranges to exclude resident pages. + */ + if (rahead != NULL) { + KASSERT(reqcount - 1 <= *rahead, + ("page count %d extends beyond swap block", reqcount)); + *rahead -= reqcount - 1; + pindex = m[reqcount - 1]->pindex; + msucc = TAILQ_NEXT(m[reqcount - 1], listq); + if (msucc != NULL && msucc->pindex - pindex - 1 < *rahead) + *rahead = msucc->pindex - pindex - 1; + } + if (rbehind != NULL) { + pindex = m[0]->pindex; + mpred = TAILQ_PREV(m[0], pglist, listq); + if (mpred != NULL && pindex - mpred->pindex - 1 < *rbehind) + *rbehind = pindex - mpred->pindex - 1; + } + + /* + * Allocate readahead and readbehind pages. + */ + shift = rbehind != NULL ? *rbehind : 0; + if (shift != 0) { + for (i = 1; i <= shift; i++) { + p = vm_page_alloc(object, m[0]->pindex - i, + VM_ALLOC_NORMAL | VM_ALLOC_IFNOTCACHED); + if (p == NULL) { + /* Shift allocated pages to the left. */ + for (j = 0; j < i - 1; j++) + bp->b_pages[j] = + bp->b_pages[j + shift - i + 1]; + break; + } + bp->b_pages[shift - i] = p; + } + shift = i - 1; + *rbehind = shift; + } + for (i = 0; i < reqcount; i++) + bp->b_pages[i + shift] = m[i]; + if (rahead != NULL) { + for (i = 0; i < *rahead; i++) { + p = vm_page_alloc(object, + m[reqcount - 1]->pindex + i + 1, + VM_ALLOC_NORMAL | VM_ALLOC_IFNOTCACHED); + if (p == NULL) + break; + bp->b_pages[shift + reqcount + i] = p; + } + *rahead = i; + } + if (rbehind != NULL) + count += *rbehind; + if (rahead != NULL) + count += *rahead; + + vm_object_pip_add(object, count); + + for (i = 0; i < count; i++) + bp->b_pages[i]->oflags |= VPO_SWAPINPROG; + + pindex = bp->b_pages[0]->pindex; + blk = swp_pager_meta_ctl(object, pindex, 0); + KASSERT(blk != SWAPBLK_NONE, + ("no swap blocking containing %p(%jx)", object, (uintmax_t)pindex)); + + VM_OBJECT_WUNLOCK(object); + + bp->b_flags |= B_PAGING; bp->b_iocmd = BIO_READ; bp->b_iodone = swp_pager_async_iodone; bp->b_rcred = crhold(thread0.td_ucred); @@ -1141,22 +1177,11 @@ swap_pager_getpages(vm_object_t object, vm_page_t *m, int count, int *rbehind, bp->b_bcount = PAGE_SIZE * count; bp->b_bufsize = PAGE_SIZE * count; bp->b_npages = count; - - VM_OBJECT_WLOCK(object); - for (int i = 0; i < count; i++) { - bp->b_pages[i] = m[i]; - m[i]->oflags |= VPO_SWAPINPROG; - } + bp->b_pgbefore = rbehind != NULL ? *rbehind : 0; + bp->b_pgafter = rahead != NULL ? *rahead : 0; PCPU_INC(cnt.v_swapin); - PCPU_ADD(cnt.v_swappgsin, bp->b_npages); - - /* - * We still hold the lock on mreq, and our automatic completion routine - * does not remove it. - */ - vm_object_pip_add(object, bp->b_npages); - VM_OBJECT_WUNLOCK(object); + PCPU_ADD(cnt.v_swappgsin, count); /* * perform the I/O. NOTE!!! bp cannot be considered valid after @@ -1173,9 +1198,9 @@ swap_pager_getpages(vm_object_t object, vm_page_t *m, int count, int *rbehind, swp_pager_strategy(bp); /* - * wait for the page we want to complete. VPO_SWAPINPROG is always + * Wait for the pages we want to complete. VPO_SWAPINPROG is always * cleared on completion. If an I/O error occurs, SWAPBLK_NONE - * is set in the meta-data. + * is set in the metadata for each page in the request. */ VM_OBJECT_WLOCK(object); while ((m[0]->oflags & VPO_SWAPINPROG) != 0) { @@ -1192,15 +1217,10 @@ swap_pager_getpages(vm_object_t object, vm_page_t *m, int count, int *rbehind, /* * If we had an unrecoverable read error pages will not be valid. */ - for (int i = 0; i < count; i++) + for (i = 0; i < reqcount; i++) if (m[i]->valid != VM_PAGE_BITS_ALL) return (VM_PAGER_ERROR); - if (rbehind) - *rbehind = 0; - if (rahead) - *rahead = 0; - return (VM_PAGER_OK); /* @@ -1518,7 +1538,11 @@ swp_pager_async_iodone(struct buf *bp) ("swp_pager_async_iodone: page %p is mapped", m)); KASSERT(m->dirty == 0, ("swp_pager_async_iodone: page %p is dirty", m)); + m->valid = VM_PAGE_BITS_ALL; + if (i < bp->b_pgbefore || + i >= bp->b_npages - bp->b_pgafter) + vm_page_readahead_finish(m); } else { /* * For write success, clear the dirty diff --git a/sys/vm/vm_page.c b/sys/vm/vm_page.c index b64e911f50df..47cdc6c0560d 100644 --- a/sys/vm/vm_page.c +++ b/sys/vm/vm_page.c @@ -1030,8 +1030,8 @@ vm_page_free_zero(vm_page_t m) } /* - * Unbusy and handle the page queueing for a page from the VOP_GETPAGES() - * array which was optionally read ahead or behind. + * Unbusy and handle the page queueing for a page from a getpages request that + * was optionally read ahead or behind. */ void vm_page_readahead_finish(vm_page_t m) From a951a788211cc4e730fb1753ee647aa046954d2d Mon Sep 17 00:00:00 2001 From: Kevin Lo Date: Tue, 30 Aug 2016 08:34:49 +0000 Subject: [PATCH 16/86] Update a comment to reflect r305051. --- share/man/man9/mbuf.9 | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/share/man/man9/mbuf.9 b/share/man/man9/mbuf.9 index a6aec87ff782..233caf086e66 100644 --- a/share/man/man9/mbuf.9 +++ b/share/man/man9/mbuf.9 @@ -24,7 +24,7 @@ .\" .\" $FreeBSD$ .\" -.Dd February 29, 2016 +.Dd August 30, 2016 .Dt MBUF 9 .Os .\" @@ -255,7 +255,7 @@ The available external buffer types are defined as follows: #define EXT_JUMBO9 4 /* jumbo cluster 9216 bytes */ #define EXT_JUMBO16 5 /* jumbo cluster 16184 bytes */ #define EXT_PACKET 6 /* mbuf+cluster from packet zone */ -#define EXT_MBUF 7 /* external mbuf reference (M_IOVEC) */ +#define EXT_MBUF 7 /* external mbuf reference */ #define EXT_NET_DRV 252 /* custom ext_buf provided by net driver(s) */ #define EXT_MOD_TYPE 253 /* custom module's ext_buf type */ #define EXT_DISPOSABLE 254 /* can throw this buffer away w/page flipping */ From c60d891c4ffded2a06607045b07261988561b18b Mon Sep 17 00:00:00 2001 From: Jared McNeill Date: Tue, 30 Aug 2016 10:21:32 +0000 Subject: [PATCH 17/86] Add support for Allwinner A64 watchdog timer. --- sys/arm/allwinner/aw_wdog.c | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/sys/arm/allwinner/aw_wdog.c b/sys/arm/allwinner/aw_wdog.c index 263062372bee..59ee28d86e59 100644 --- a/sys/arm/allwinner/aw_wdog.c +++ b/sys/arm/allwinner/aw_wdog.c @@ -30,6 +30,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #include #include #include @@ -54,6 +55,7 @@ __FBSDID("$FreeBSD$"); #define A10_WDOG_CTRL 0x00 #define A31_WDOG_CTRL 0x10 #define WDOG_CTRL_RESTART (1 << 0) +#define A31_WDOG_CTRL_KEY (0xa57 << 1) #define A10_WDOG_MODE 0x04 #define A31_WDOG_MODE 0x18 #define A10_WDOG_MODE_INTVL_SHIFT 3 @@ -92,6 +94,7 @@ struct aw_wdog_softc { struct resource * res; struct mtx mtx; uint8_t wdog_ctrl; + uint32_t wdog_ctrl_key; uint8_t wdog_mode; uint8_t wdog_mode_intvl_shift; uint8_t wdog_mode_en; @@ -108,7 +111,8 @@ static struct ofw_compat_data compat_data[] = { {NULL, 0} }; -static void aw_wdog_watchdog_fn(void *private, u_int cmd, int *error); +static void aw_wdog_watchdog_fn(void *, u_int, int *); +static void aw_wdog_shutdown_fn(void *, int); static int aw_wdog_probe(device_t dev) @@ -160,6 +164,7 @@ aw_wdog_attach(device_t dev) break; case A31_WATCHDOG: sc->wdog_ctrl = A31_WDOG_CTRL; + sc->wdog_ctrl_key = A31_WDOG_CTRL_KEY; sc->wdog_mode = A31_WDOG_MODE; sc->wdog_mode_intvl_shift = A31_WDOG_MODE_INTVL_SHIFT; sc->wdog_mode_en = WDOG_MODE_EN; @@ -173,6 +178,9 @@ aw_wdog_attach(device_t dev) mtx_init(&sc->mtx, "AW Watchdog", "aw_wdog", MTX_DEF); EVENTHANDLER_REGISTER(watchdog_list, aw_wdog_watchdog_fn, sc, 0); + EVENTHANDLER_REGISTER(shutdown_final, aw_wdog_shutdown_fn, sc, + SHUTDOWN_PRI_LAST - 1); + return (0); } @@ -198,7 +206,8 @@ aw_wdog_watchdog_fn(void *private, u_int cmd, int *error) WRITE(sc, sc->wdog_mode, (wd_intervals[i].value << sc->wdog_mode_intvl_shift) | sc->wdog_mode_en); - WRITE(sc, sc->wdog_ctrl, WDOG_CTRL_RESTART); + WRITE(sc, sc->wdog_ctrl, + WDOG_CTRL_RESTART | sc->wdog_ctrl_key); if (sc->wdog_config) WRITE(sc, sc->wdog_config, sc->wdog_config_value); @@ -222,6 +231,13 @@ aw_wdog_watchdog_fn(void *private, u_int cmd, int *error) mtx_unlock(&sc->mtx); } +static void +aw_wdog_shutdown_fn(void *private, int howto) +{ + if ((howto & (RB_POWEROFF|RB_HALT)) == 0) + aw_wdog_watchdog_reset(); +} + void aw_wdog_watchdog_reset() { @@ -237,6 +253,8 @@ aw_wdog_watchdog_reset() if (aw_wdog_sc->wdog_config) WRITE(aw_wdog_sc, aw_wdog_sc->wdog_config, aw_wdog_sc->wdog_config_value); + WRITE(aw_wdog_sc, aw_wdog_sc->wdog_ctrl, + WDOG_CTRL_RESTART | aw_wdog_sc->wdog_ctrl_key); while(1) ; From 81306e463e9b5e281c8d80dbb58cc4789ffa1010 Mon Sep 17 00:00:00 2001 From: Bruce Evans Date: Tue, 30 Aug 2016 10:57:19 +0000 Subject: [PATCH 18/86] Start adding locking to sc_cngetc(). Restore an splx() lost in r228644. We aren't nearly ready to remove spl's. They give hints about missing locking. This lost one was misplaced. Dropping it early for convenience gave race windows for accesses to the fkey buffer. Giant locking accidentally fixed this for non-console cases. Put the spl's around the whole function. Since there are many returns that would need splx() just before them for a direct fix, split the function into a wrapper that does the spl's and a "locked" function that does the work. Return earlier when no keyboard is attached to match the ordering in a planned version. This breaks the dubious feature of returning keys from the fkey buffer after the keyboard has gone away. Losing the keys wouldn't matter, but we keep them too long now. --- sys/dev/syscons/syscons.c | 29 ++++++++++++++++++----------- 1 file changed, 18 insertions(+), 11 deletions(-) diff --git a/sys/dev/syscons/syscons.c b/sys/dev/syscons/syscons.c index 1401aa1ed65e..e4906cf4ac3b 100644 --- a/sys/dev/syscons/syscons.c +++ b/sys/dev/syscons/syscons.c @@ -1648,6 +1648,7 @@ sc_cnterm(struct consdev *cp) } static void sccnclose(sc_softc_t *sc, struct sc_cnstate *sp); +static int sc_cngetc_locked(struct sc_cnstate *sp); static void sccnopen(sc_softc_t *sc, struct sc_cnstate *sp, int flags); static void sccnscrlock(sc_softc_t *sc, struct sc_cnstate *sp); static void sccnscrunlock(sc_softc_t *sc, struct sc_cnstate *sp); @@ -1823,16 +1824,29 @@ sc_cnputc(struct consdev *cd, int c) static int sc_cngetc(struct consdev *cd) +{ + int c, s; + + /* assert(sc_console != NULL) */ + s = spltty(); /* block sckbdevent and scrn_timer while we poll */ + if (sc_console->sc->kbd == NULL) { + splx(s); + return -1; + } + c = sc_cngetc_locked(NULL); + splx(s); + return c; +} + +static int +sc_cngetc_locked(struct sc_cnstate *sp) { static struct fkeytab fkey; static int fkeycp; scr_stat *scp; const u_char *p; - int s = spltty(); /* block sckbdevent and scrn_timer while we poll */ int c; - /* assert(sc_console != NULL) */ - /* * Stop the screen saver and update the screen if necessary. * What if we have been running in the screen saver code... XXX @@ -1841,15 +1855,8 @@ sc_cngetc(struct consdev *cd) scp = sc_console->sc->cur_scp; /* XXX */ sccnupdate(scp); - if (fkeycp < fkey.len) { - splx(s); + if (fkeycp < fkey.len) return fkey.str[fkeycp++]; - } - - if (scp->sc->kbd == NULL) { - splx(s); - return -1; - } c = scgetc(scp->sc, SCGETC_CN | SCGETC_NONBLOCK, NULL); From cc43fd1ab5afa9f4ed20168193fd1f16a363be88 Mon Sep 17 00:00:00 2001 From: Bruce Evans Date: Tue, 30 Aug 2016 12:36:14 +0000 Subject: [PATCH 19/86] Fix keyboard polling "on/off" to support recursion. vt depends on this, and sc will soon depend on it again. The on/off request is passed without modification to lower layers, so the bug was smaller in this layer than in in lower layers (the sequence on;on;off left polling off when it should be on, but the sequence on;on;off;on;off... doesn't allow the interrupt handler to eat the input after an "off" that should't turn off polled mode, provided lower layers don't have the bug, since this layer is virtual. The bug was small in lower layers too. Normally everything is Giant locked for keyboards, and this locks out the interrupt handler in on;on;off;on;off... sequences. However, PR 211884 says that fixing this bug in ukbd in r303765 apparently causes the eating-by-interrupt behaviour that the fix is to prevent. Discussed with: emax --- sys/dev/kbdmux/kbdmux.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/sys/dev/kbdmux/kbdmux.c b/sys/dev/kbdmux/kbdmux.c index 0dce120ad6a8..4720a0e6fc88 100644 --- a/sys/dev/kbdmux/kbdmux.c +++ b/sys/dev/kbdmux/kbdmux.c @@ -150,9 +150,9 @@ struct kbdmux_state int ks_flags; /* flags */ #define COMPOSE (1 << 0) /* compose char flag */ -#define POLLING (1 << 1) /* polling */ #define TASK (1 << 2) /* interrupt task queued */ + int ks_polling; /* poll nesting count */ int ks_mode; /* K_XLATE, K_RAW, K_CODE */ int ks_state; /* state */ int ks_accents; /* accent key index (> 0) */ @@ -666,7 +666,7 @@ kbdmux_read_char(keyboard_t *kbd, int wait) /* see if there is something in the keyboard queue */ scancode = kbdmux_kbd_getc(state); if (scancode == -1) { - if (state->ks_flags & POLLING) { + if (state->ks_polling != 0) { kbdmux_kbd_t *k; SLIST_FOREACH(k, &state->ks_kbds, next) { @@ -1244,7 +1244,8 @@ kbdmux_clear_state_locked(kbdmux_state_t *state) { KBDMUX_LOCK_ASSERT(state, MA_OWNED); - state->ks_flags &= ~(COMPOSE|POLLING); + state->ks_flags &= ~COMPOSE; + state->ks_polling = 0; state->ks_state &= LOCK_MASK; /* preserve locking key state */ state->ks_accents = 0; state->ks_composed_char = 0; @@ -1304,9 +1305,9 @@ kbdmux_poll(keyboard_t *kbd, int on) KBDMUX_LOCK(state); if (on) - state->ks_flags |= POLLING; + state->ks_polling++; else - state->ks_flags &= ~POLLING; + state->ks_polling--; /* set poll on slave keyboards */ SLIST_FOREACH(k, &state->ks_kbds, next) From 9287c0323dd839e0b1ac20c2a84878211865ee89 Mon Sep 17 00:00:00 2001 From: Marcelo Araujo Date: Tue, 30 Aug 2016 12:40:12 +0000 Subject: [PATCH 20/86] Invert calloc(3) argument order. Reviewed by: grehan, mav MFC after: 1 week Differential Revision: https://reviews.freebsd.org/D7613 --- usr.sbin/bhyve/pci_e82545.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/usr.sbin/bhyve/pci_e82545.c b/usr.sbin/bhyve/pci_e82545.c index 03a324e49102..54bebd062629 100644 --- a/usr.sbin/bhyve/pci_e82545.c +++ b/usr.sbin/bhyve/pci_e82545.c @@ -2273,7 +2273,7 @@ e82545_init(struct vmctx *ctx, struct pci_devinst *pi, char *opts) int mac_provided; /* Setup our softc */ - sc = calloc(sizeof(*sc), 1); + sc = calloc(1, sizeof(*sc)); pi->pi_arg = sc; sc->esc_pi = pi; From b2af61ec69826890d075ceb3e20e206be20d6fea Mon Sep 17 00:00:00 2001 From: Kurt Lidl Date: Tue, 30 Aug 2016 14:09:24 +0000 Subject: [PATCH 21/86] Add refactored blacklist support to sshd Change the calls to of blacklist_init() and blacklist_notify to be macros defined in the blacklist_client.h file. This avoids the need for #ifdef USE_BLACKLIST / #endif except in the blacklist.c file. Remove redundent initialization attempts from within blacklist_notify - everything always goes through blacklistd_init(). Added UseBlacklist option to sshd, which defaults to off. To enable the functionality, use '-o UseBlacklist=yes' on the command line, or uncomment in the sshd_config file. Reviewed by: des Approved by: des MFC after: 1 week Sponsored by: The FreeBSD Foundation Differential Revision: https://reviews.freebsd.org/D7051 --- crypto/openssh/auth-pam.c | 2 + crypto/openssh/auth.c | 7 +- crypto/openssh/auth1.c | 3 + crypto/openssh/auth2.c | 2 + crypto/openssh/blacklist.c | 97 ++++++++++++++++++++++++++++ crypto/openssh/blacklist_client.h | 57 ++++++++++++++++ crypto/openssh/packet.c | 2 + crypto/openssh/servconf.c | 10 +++ crypto/openssh/servconf.h | 1 + crypto/openssh/sshd.c | 5 ++ crypto/openssh/sshd_config | 1 + crypto/openssh/sshd_config.5 | 9 +++ secure/usr.sbin/sshd/Makefile | 7 ++ secure/usr.sbin/sshd/Makefile.depend | 1 + 14 files changed, 203 insertions(+), 1 deletion(-) create mode 100644 crypto/openssh/blacklist.c create mode 100644 crypto/openssh/blacklist_client.h diff --git a/crypto/openssh/auth-pam.c b/crypto/openssh/auth-pam.c index 8425af1ea33a..bbd18e596951 100644 --- a/crypto/openssh/auth-pam.c +++ b/crypto/openssh/auth-pam.c @@ -98,6 +98,7 @@ #include "ssh-gss.h" #endif #include "monitor_wrap.h" +#include "blacklist_client.h" extern ServerOptions options; extern Buffer loginmsg; @@ -794,6 +795,7 @@ sshpam_query(void *ctx, char **name, char **info, free(msg); return (0); } + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); error("PAM: %s for %s%.100s from %.100s", msg, sshpam_authctxt->valid ? "" : "illegal user ", sshpam_authctxt->user, diff --git a/crypto/openssh/auth.c b/crypto/openssh/auth.c index ba908801a169..1259385f8af9 100644 --- a/crypto/openssh/auth.c +++ b/crypto/openssh/auth.c @@ -75,6 +75,7 @@ __RCSID("$FreeBSD$"); #include "authfile.h" #include "ssherr.h" #include "compat.h" +#include "blacklist_client.h" /* import */ extern ServerOptions options; @@ -292,8 +293,11 @@ auth_log(Authctxt *authctxt, int authenticated, int partial, authmsg = "Postponed"; else if (partial) authmsg = "Partial"; - else + else { authmsg = authenticated ? "Accepted" : "Failed"; + BLACKLIST_NOTIFY(authenticated ? + BLACKLIST_AUTH_OK : BLACKLIST_AUTH_FAIL); + } authlog("%s %s%s%s for %s%.100s from %.200s port %d %s%s%s", authmsg, @@ -640,6 +644,7 @@ getpwnamallow(const char *user) } #endif if (pw == NULL) { + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); logit("Invalid user %.100s from %.100s", user, get_remote_ipaddr()); #ifdef CUSTOM_FAILED_LOGIN diff --git a/crypto/openssh/auth1.c b/crypto/openssh/auth1.c index 5073c49bb37d..71eb0c21b260 100644 --- a/crypto/openssh/auth1.c +++ b/crypto/openssh/auth1.c @@ -43,6 +43,7 @@ #endif #include "monitor_wrap.h" #include "buffer.h" +#include "blacklist_client.h" /* import */ extern ServerOptions options; @@ -337,6 +338,7 @@ do_authloop(Authctxt *authctxt) char *msg; size_t len; + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); error("Access denied for user %s by PAM account " "configuration", authctxt->user); len = buffer_len(&loginmsg); @@ -404,6 +406,7 @@ do_authentication(Authctxt *authctxt) else { debug("do_authentication: invalid user %s", user); authctxt->pw = fakepw(); + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); } /* Configuration may have changed as a result of Match */ diff --git a/crypto/openssh/auth2.c b/crypto/openssh/auth2.c index 1d9aab037dd6..ee3c5dd87ce1 100644 --- a/crypto/openssh/auth2.c +++ b/crypto/openssh/auth2.c @@ -52,6 +52,7 @@ __RCSID("$FreeBSD$"); #include "pathnames.h" #include "buffer.h" #include "canohost.h" +#include "blacklist_client.h" #ifdef GSSAPI #include "ssh-gss.h" @@ -248,6 +249,7 @@ input_userauth_request(int type, u_int32_t seq, void *ctxt) } else { logit("input_userauth_request: invalid user %s", user); authctxt->pw = fakepw(); + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); #ifdef SSH_AUDIT_EVENTS PRIVSEP(audit_event(SSH_INVALID_USER)); #endif diff --git a/crypto/openssh/blacklist.c b/crypto/openssh/blacklist.c new file mode 100644 index 000000000000..4c9d91dec164 --- /dev/null +++ b/crypto/openssh/blacklist.c @@ -0,0 +1,97 @@ +/*- + * Copyright (c) 2015 The NetBSD Foundation, Inc. + * Copyright (c) 2016 The FreeBSD Foundation, Inc. + * All rights reserved. + * + * Portions of this software were developed by Kurt Lidl + * under sponsorship from the FreeBSD Foundation. + * + * This code is derived from software contributed to The NetBSD Foundation + * by Christos Zoulas. + * + * 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. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. 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 THE FOUNDATION 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 "includes.h" + +#include +#include +#include +#include +#include +#include +#include + +#include "ssh.h" +#include "packet.h" +#include "log.h" +#include "misc.h" +#include "servconf.h" +#include "blacklist_client.h" +#include + +static struct blacklist *blstate = NULL; + +/* import */ +extern ServerOptions options; + +/* internal definition from bl.h */ +struct blacklist *bl_create(bool, char *, void (*)(int, const char *, va_list)); + +/* impedence match vsyslog() to sshd's internal logging levels */ +void +im_log(int priority, const char *message, va_list args) +{ + LogLevel imlevel; + + switch (priority) { + case LOG_ERR: + imlevel = SYSLOG_LEVEL_ERROR; + break; + case LOG_DEBUG: + imlevel = SYSLOG_LEVEL_DEBUG1; + break; + case LOG_INFO: + imlevel = SYSLOG_LEVEL_INFO; + break; + default: + imlevel = SYSLOG_LEVEL_DEBUG2; + } + do_log(imlevel, message, args); +} + +void +blacklist_init(void) +{ + + if (options.use_blacklist) + blstate = bl_create(false, NULL, im_log); +} + +void +blacklist_notify(int action) +{ + + if (blstate != NULL && packet_connection_is_on_socket()) + (void)blacklist_r(blstate, action, + packet_get_connection_in(), "ssh"); +} diff --git a/crypto/openssh/blacklist_client.h b/crypto/openssh/blacklist_client.h new file mode 100644 index 000000000000..9479bb27be46 --- /dev/null +++ b/crypto/openssh/blacklist_client.h @@ -0,0 +1,57 @@ +/*- + * Copyright (c) 2015 The NetBSD Foundation, Inc. + * Copyright (c) 2016 The FreeBSD Foundation, Inc. + * All rights reserved. + * + * Portions of this software were developed by Kurt Lidl + * under sponsorship from the FreeBSD Foundation. + * + * This code is derived from software contributed to The NetBSD Foundation + * by Christos Zoulas. + * + * 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. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. 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 THE FOUNDATION 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. + */ + +#ifndef BLACKLIST_CLIENT_H +#define BLACKLIST_CLIENT_H + +enum { + BLACKLIST_AUTH_OK = 0, + BLACKLIST_AUTH_FAIL +}; + +#ifdef USE_BLACKLIST +void blacklist_init(void); +void blacklist_notify(int); + +#define BLACKLIST_INIT() blacklist_init() +#define BLACKLIST_NOTIFY(x) blacklist_notify(x) + +#else + +#define BLACKLIST_INIT() +#define BLACKLIST_NOTIFY(x) + +#endif + + +#endif /* BLACKLIST_CLIENT_H */ diff --git a/crypto/openssh/packet.c b/crypto/openssh/packet.c index f3b3ce9cf250..be4b4b6e22d9 100644 --- a/crypto/openssh/packet.c +++ b/crypto/openssh/packet.c @@ -86,6 +86,7 @@ __RCSID("$FreeBSD$"); #include "packet.h" #include "ssherr.h" #include "sshbuf.h" +#include "blacklist_client.h" #ifdef PACKET_DEBUG #define DBG(x) x @@ -2071,6 +2072,7 @@ sshpkt_fatal(struct ssh *ssh, const char *tag, int r) case SSH_ERR_NO_KEX_ALG_MATCH: case SSH_ERR_NO_HOSTKEY_ALG_MATCH: if (ssh && ssh->kex && ssh->kex->failed_choice) { + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); fatal("Unable to negotiate with %.200s port %d: %s. " "Their offer: %s", ssh_remote_ipaddr(ssh), ssh_remote_port(ssh), ssh_err(r), diff --git a/crypto/openssh/servconf.c b/crypto/openssh/servconf.c index 6fb8be5bfd5a..66d24cefd4e2 100644 --- a/crypto/openssh/servconf.c +++ b/crypto/openssh/servconf.c @@ -172,6 +172,7 @@ initialize_server_options(ServerOptions *options) options->ip_qos_bulk = -1; options->version_addendum = NULL; options->fingerprint_hash = -1; + options->use_blacklist = -1; } /* Returns 1 if a string option is unset or set to "none" or 0 otherwise. */ @@ -360,6 +361,8 @@ fill_default_server_options(ServerOptions *options) options->fwd_opts.streamlocal_bind_unlink = 0; if (options->fingerprint_hash == -1) options->fingerprint_hash = SSH_FP_HASH_DEFAULT; + if (options->use_blacklist == -1) + options->use_blacklist = 0; assemble_algorithms(options); @@ -437,6 +440,7 @@ typedef enum { sAuthenticationMethods, sHostKeyAgent, sPermitUserRC, sStreamLocalBindMask, sStreamLocalBindUnlink, sAllowStreamLocalForwarding, sFingerprintHash, + sUseBlacklist, sDeprecated, sUnsupported } ServerOpCodes; @@ -579,6 +583,7 @@ static struct { { "streamlocalbindunlink", sStreamLocalBindUnlink, SSHCFG_ALL }, { "allowstreamlocalforwarding", sAllowStreamLocalForwarding, SSHCFG_ALL }, { "fingerprinthash", sFingerprintHash, SSHCFG_GLOBAL }, + { "useblacklist", sUseBlacklist, SSHCFG_GLOBAL }, { "noneenabled", sUnsupported, SSHCFG_ALL }, { "hpndisabled", sDeprecated, SSHCFG_ALL }, { "hpnbuffersize", sDeprecated, SSHCFG_ALL }, @@ -1861,6 +1866,10 @@ process_server_config_line(ServerOptions *options, char *line, options->fingerprint_hash = value; break; + case sUseBlacklist: + intptr = &options->use_blacklist; + goto parse_flag; + case sDeprecated: logit("%s line %d: Deprecated option %s", filename, linenum, arg); @@ -2304,6 +2313,7 @@ dump_config(ServerOptions *o) dump_cfg_fmtint(sAllowStreamLocalForwarding, o->allow_streamlocal_forwarding); dump_cfg_fmtint(sUsePrivilegeSeparation, use_privsep); dump_cfg_fmtint(sFingerprintHash, o->fingerprint_hash); + dump_cfg_fmtint(sUseBlacklist, o->use_blacklist); /* string arguments */ dump_cfg_string(sPidFile, o->pid_file); diff --git a/crypto/openssh/servconf.h b/crypto/openssh/servconf.h index f4137af7d666..8c37a63dd4f4 100644 --- a/crypto/openssh/servconf.h +++ b/crypto/openssh/servconf.h @@ -195,6 +195,7 @@ typedef struct { char *auth_methods[MAX_AUTH_METHODS]; int fingerprint_hash; + int use_blacklist; } ServerOptions; /* Information about the incoming connection as used by Match */ diff --git a/crypto/openssh/sshd.c b/crypto/openssh/sshd.c index dd7fcdda3e94..38b772d10855 100644 --- a/crypto/openssh/sshd.c +++ b/crypto/openssh/sshd.c @@ -135,6 +135,7 @@ __RCSID("$FreeBSD$"); #include "ssh-sandbox.h" #include "version.h" #include "ssherr.h" +#include "blacklist_client.h" #ifdef LIBWRAP #include @@ -388,6 +389,8 @@ grace_alarm_handler(int sig) kill(0, SIGTERM); } + BLACKLIST_NOTIFY(BLACKLIST_AUTH_FAIL); + /* Log error and exit. */ sigdie("Timeout before authentication for %s", get_remote_ipaddr()); } @@ -2251,6 +2254,8 @@ main(int ac, char **av) buffer_init(&loginmsg); auth_debug_reset(); + BLACKLIST_INIT(); + if (use_privsep) { if (privsep_preauth(authctxt) == 1) goto authenticated; diff --git a/crypto/openssh/sshd_config b/crypto/openssh/sshd_config index 6ea0b0885732..a842e6efef9a 100644 --- a/crypto/openssh/sshd_config +++ b/crypto/openssh/sshd_config @@ -120,6 +120,7 @@ #MaxStartups 10:30:100 #PermitTunnel no #ChrootDirectory none +#UseBlacklist no #VersionAddendum FreeBSD-20160310 # no default banner path diff --git a/crypto/openssh/sshd_config.5 b/crypto/openssh/sshd_config.5 index 78531214a1f9..54c95ad74220 100644 --- a/crypto/openssh/sshd_config.5 +++ b/crypto/openssh/sshd_config.5 @@ -1537,6 +1537,15 @@ for authentication using .Cm TrustedUserCAKeys . For more details on certificates, see the CERTIFICATES section in .Xr ssh-keygen 1 . +.It Cm UseBlacklist +Specifies whether +.Xr sshd 8 +attempts to send authentication success and failure messages +to the +.Xr blacklistd 8 +daemon. +The default is +.Dq no . .It Cm UseDNS Specifies whether .Xr sshd 8 diff --git a/secure/usr.sbin/sshd/Makefile b/secure/usr.sbin/sshd/Makefile index f9589a37ae37..af760992b725 100644 --- a/secure/usr.sbin/sshd/Makefile +++ b/secure/usr.sbin/sshd/Makefile @@ -40,6 +40,13 @@ CFLAGS+= -DUSE_BSM_AUDIT -DHAVE_GETAUDIT_ADDR LIBADD+= bsm .endif +.if ${MK_BLACKLIST_SUPPORT} != "no" +CFLAGS+= -DUSE_BLACKLIST -I${SRCTOP}/contrib/blacklist/include +SRCS+= blacklist.c +LIBADD+= blacklist +LDFLAGS+=-L${LIBBLACKLISTDIR} +.endif + .if ${MK_KERBEROS_SUPPORT} != "no" CFLAGS+= -include krb5_config.h SRCS+= krb5_config.h diff --git a/secure/usr.sbin/sshd/Makefile.depend b/secure/usr.sbin/sshd/Makefile.depend index d24b0bef5d55..220aae36c11c 100644 --- a/secure/usr.sbin/sshd/Makefile.depend +++ b/secure/usr.sbin/sshd/Makefile.depend @@ -17,6 +17,7 @@ DIRDEPS = \ kerberos5/lib/libroken \ kerberos5/lib/libwind \ lib/${CSU_DIR} \ + lib/libblacklist \ lib/libbsm \ lib/libc \ lib/libcom_err \ From 66096993b4be9df15f9aa5fef91d55885781aa59 Mon Sep 17 00:00:00 2001 From: "George V. Neville-Neil" Date: Tue, 30 Aug 2016 14:28:35 +0000 Subject: [PATCH 22/86] Update cryptotest for modern algorithms Reviewed by: cem Sponsored by: Rubicon Communications, LLC (Netgate) Differential Revision: https://reviews.freebsd.org/D7598 --- tools/tools/crypto/cryptotest.c | 45 ++++++++++++++++++--------------- 1 file changed, 25 insertions(+), 20 deletions(-) diff --git a/tools/tools/crypto/cryptotest.c b/tools/tools/crypto/cryptotest.c index c13d3a45b9e1..24954e1caa45 100644 --- a/tools/tools/crypto/cryptotest.c +++ b/tools/tools/crypto/cryptotest.c @@ -126,9 +126,10 @@ struct alg { { "blf", 0, 8, 5, 56, CRYPTO_BLF_CBC }, { "cast", 0, 8, 5, 16, CRYPTO_CAST_CBC }, { "skj", 0, 8, 10, 10, CRYPTO_SKIPJACK_CBC }, - { "aes", 0, 16, 16, 16, CRYPTO_RIJNDAEL128_CBC}, - { "aes192", 0, 16, 24, 24, CRYPTO_RIJNDAEL128_CBC}, - { "aes256", 0, 16, 32, 32, CRYPTO_RIJNDAEL128_CBC}, + { "rij", 0, 16, 16, 16, CRYPTO_RIJNDAEL128_CBC}, + { "aes", 0, 16, 16, 16, CRYPTO_AES_CBC}, + { "aes192", 0, 16, 24, 24, CRYPTO_AES_CBC}, + { "aes256", 0, 16, 32, 32, CRYPTO_AES_CBC}, #ifdef notdef { "arc4", 0, 8, 1, 32, CRYPTO_ARC4 }, #endif @@ -139,19 +140,20 @@ struct alg { { "sha512", 1, 8, 64, 64, CRYPTO_SHA2_512_HMAC }, }; -static void +void usage(const char* cmd) { printf("usage: %s [-czsbv] [-d dev] [-a algorithm] [count] [size ...]\n", cmd); printf("where algorithm is one of:\n"); - printf(" des 3des (default) blowfish cast skipjack\n"); - printf(" aes (aka rijndael) aes192 aes256 arc4\n"); + printf(" des 3des (default) blowfish cast skipjack rij\n"); + printf(" aes aes192 aes256 arc4\n"); printf("count is the number of encrypt/decrypt ops to do\n"); printf("size is the number of bytes of text to encrypt+decrypt\n"); printf("\n"); printf("-c check the results (slows timing)\n"); - printf("-d use specific device\n"); + printf("-d use specific device, specify 'soft' for testing software implementations\n"); + printf("\tNOTE: to use software you must set:\n\t sysctl kern.cryptodevallowsoft=1\n"); printf("-z run all available algorithms on a variety of sizes\n"); printf("-v be verbose\n"); printf("-b mark operations for batching\n"); @@ -159,7 +161,7 @@ usage(const char* cmd) exit(-1); } -static struct alg* +struct alg* getalgbycode(int cipher) { int i; @@ -170,7 +172,7 @@ getalgbycode(int cipher) return NULL; } -static struct alg* +struct alg* getalgbyname(const char* name) { int i; @@ -181,10 +183,10 @@ getalgbyname(const char* name) return NULL; } -static int +int devcrypto(void) { - static int fd = -1; + int fd = -1; if (fd < 0) { fd = open(_PATH_DEV "crypto", O_RDWR, 0); @@ -196,11 +198,14 @@ devcrypto(void) return fd; } -static int +int crlookup(const char *devname) { struct crypt_find_op find; + if (strncmp(devname, "soft", 4) == 0) + return CRYPTO_FLAG_SOFTWARE; + find.crid = -1; strlcpy(find.name, devname, sizeof(find.name)); if (ioctl(devcrypto(), CIOCFINDDEV, &find) == -1) @@ -208,10 +213,10 @@ crlookup(const char *devname) return find.crid; } -static const char * +const char * crfind(int crid) { - static struct crypt_find_op find; + struct crypt_find_op find; bzero(&find, sizeof(find)); find.crid = crid; @@ -220,7 +225,7 @@ crfind(int crid) return find.name; } -static int +int crget(void) { int fd; @@ -232,7 +237,7 @@ crget(void) return fd; } -static char +char rdigit(void) { const char a[] = { @@ -242,7 +247,7 @@ rdigit(void) return 0x20+a[random()%nitems(a)]; } -static void +void runtest(struct alg *alg, int count, int size, u_long cmd, struct timeval *tv) { int i, fd = crget(); @@ -386,7 +391,7 @@ runtest(struct alg *alg, int count, int size, u_long cmd, struct timeval *tv) } #ifdef __FreeBSD__ -static void +void resetstats() { struct cryptostats stats; @@ -409,7 +414,7 @@ resetstats() perror("kern.cryptostats"); } -static void +void printt(const char* tag, struct cryptotstat *ts) { uint64_t avg, min, max; @@ -424,7 +429,7 @@ printt(const char* tag, struct cryptotstat *ts) } #endif -static void +void runtests(struct alg *alg, int count, int size, u_long cmd, int threads, int profile) { int i, status; From 7090a451421b43d5951c4bb5f8d5e4b8078eef70 Mon Sep 17 00:00:00 2001 From: Andrew Turner Date: Tue, 30 Aug 2016 16:45:15 +0000 Subject: [PATCH 23/86] Because we need to use a break-before-make sequence when promoting pages there is a short period where functions that walk the kernel page table without locking them may see an invalid entry. One solution would be to add locking to these functions, however some may be called from locations where we are unable to sleep. Until a better solution can be found stop promoting pages in the kernel pmap so these functions work as expected. Obtained from: ABT Systems Ltd MFC after: 1 month Sponsored by: The FreeBSD Foundation --- sys/arm64/arm64/pmap.c | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/sys/arm64/arm64/pmap.c b/sys/arm64/arm64/pmap.c index 961c5b1e68d2..71b29c4de25a 100644 --- a/sys/arm64/arm64/pmap.c +++ b/sys/arm64/arm64/pmap.c @@ -2936,14 +2936,17 @@ pmap_enter(pmap_t pmap, vm_offset_t va, vm_page_t m, vm_prot_t prot, PTE_SYNC(l3); pmap_invalidate_page(pmap, va); - if ((pmap != pmap_kernel()) && (pmap == &curproc->p_vmspace->vm_pmap)) - cpu_icache_sync_range(va, PAGE_SIZE); + if (pmap != pmap_kernel()) { + if (pmap == &curproc->p_vmspace->vm_pmap) + cpu_icache_sync_range(va, PAGE_SIZE); - if ((mpte == NULL || mpte->wire_count == NL3PG) && - pmap_superpages_enabled() && (m->flags & PG_FICTITIOUS) == 0 && - vm_reserv_level_iffullpop(m) == 0) { - KASSERT(lvl == 2, ("Invalid pde level %d", lvl)); - pmap_promote_l2(pmap, pde, va, &lock); + if ((mpte == NULL || mpte->wire_count == NL3PG) && + pmap_superpages_enabled() && + (m->flags & PG_FICTITIOUS) == 0 && + vm_reserv_level_iffullpop(m) == 0) { + KASSERT(lvl == 2, ("Invalid pde level %d", lvl)); + pmap_promote_l2(pmap, pde, va, &lock); + } } if (lock != NULL) From 4a9fb9fb80c51a884aa3ab12bb0a44a1fa51fe37 Mon Sep 17 00:00:00 2001 From: Warner Losh Date: Tue, 30 Aug 2016 18:01:19 +0000 Subject: [PATCH 24/86] Remove CHS alignment. It's not needed and causes problems for the BBB boot partition. NetBSD removed it in 1.10 in their repo some time ago. Submitted by: Guy Yur PR: 183234 --- sbin/newfs_msdos/mkfs_msdos.c | 7 ------- 1 file changed, 7 deletions(-) diff --git a/sbin/newfs_msdos/mkfs_msdos.c b/sbin/newfs_msdos/mkfs_msdos.c index 90d7df855a25..f29760f7f25e 100644 --- a/sbin/newfs_msdos/mkfs_msdos.c +++ b/sbin/newfs_msdos/mkfs_msdos.c @@ -313,15 +313,8 @@ mkfs_msdos(const char *fname, const char *dtype, const struct msdos_options *op) bpb.bpbHiddenSecs = o.hidden_sectors; if (!(o.floppy || (o.drive_heads && o.sectors_per_track && o.bytes_per_sector && o.size && o.hidden_sectors_set))) { - off_t delta; getdiskinfo(fd, fname, dtype, o.hidden_sectors_set, &bpb); bpb.bpbHugeSectors -= (o.offset / bpb.bpbBytesPerSec); - delta = bpb.bpbHugeSectors % bpb.bpbSecPerTrack; - if (delta != 0) { - warnx("trim %d sectors to adjust to a multiple of %d", - (int)delta, bpb.bpbSecPerTrack); - bpb.bpbHugeSectors -= delta; - } if (bpb.bpbSecPerClust == 0) { /* set defaults */ if (bpb.bpbHugeSectors <= 6000) /* about 3MB -> 512 bytes */ bpb.bpbSecPerClust = 1; From bf0d940a2f48022204b3de50c6aca9993fc40527 Mon Sep 17 00:00:00 2001 From: Warner Losh Date: Tue, 30 Aug 2016 18:01:26 +0000 Subject: [PATCH 25/86] The code only converts from bpbHugeSectors to bpbSectors if the sum of the hidden and huge sectors is less than or equal MAXU16. When formatting in Windows bpbSectors is still used for 63488 sectors and 2048 hidden (sum > MAXU16). The hidden sectors count is the number of sectors before the FAT16 Boot Record so it shouldn't affect the sector count. Attached patch (huge_sec_conversion.patch) to only check for bpb.bpbHugeSectors <= MAXU16 when converting to bpbSectors. Submitted by: Guy Yur PR: 183234 --- sbin/newfs_msdos/mkfs_msdos.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sbin/newfs_msdos/mkfs_msdos.c b/sbin/newfs_msdos/mkfs_msdos.c index f29760f7f25e..b961e25c431c 100644 --- a/sbin/newfs_msdos/mkfs_msdos.c +++ b/sbin/newfs_msdos/mkfs_msdos.c @@ -556,7 +556,7 @@ mkfs_msdos(const char *fname, const char *dtype, const struct msdos_options *op) bpb.bpbMedia = !bpb.bpbHiddenSecs ? 0xf0 : 0xf8; if (fat == 32) bpb.bpbRootClust = RESFTE; - if (bpb.bpbHiddenSecs + bpb.bpbHugeSectors <= MAXU16) { + if (bpb.bpbHugeSectors <= MAXU16) { bpb.bpbSectors = bpb.bpbHugeSectors; bpb.bpbHugeSectors = 0; } From c43262580d22b8537aace19582a77027e07f554c Mon Sep 17 00:00:00 2001 From: Dimitry Andric Date: Tue, 30 Aug 2016 19:02:15 +0000 Subject: [PATCH 26/86] Squelch clang 3.9.0 warnings about BASE (which is 32768) being converted to -32768 when it is used as an argument to mp_itom(), in both libtelnet and newkey. This code has been wrong since r26238 (!), so after almost 20 years it is rather useless to try to correct it. MFC after: 1 week --- contrib/telnet/libtelnet/pk.c | 2 +- usr.bin/newkey/generic.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/contrib/telnet/libtelnet/pk.c b/contrib/telnet/libtelnet/pk.c index 05b74f43d414..52efebad4693 100644 --- a/contrib/telnet/libtelnet/pk.c +++ b/contrib/telnet/libtelnet/pk.c @@ -164,7 +164,7 @@ genkeys(char *public, char *secret) MINT *pk = mp_itom(0); MINT *sk = mp_itom(0); MINT *tmp; - MINT *base = mp_itom(BASE); + MINT *base = mp_itom((short)BASE); MINT *root = mp_itom(PROOT); MINT *modulus = mp_xtom(HEXMODULUS); short r; diff --git a/usr.bin/newkey/generic.c b/usr.bin/newkey/generic.c index 3626960f9540..368b051155a4 100644 --- a/usr.bin/newkey/generic.c +++ b/usr.bin/newkey/generic.c @@ -82,7 +82,7 @@ genkeys(char *public, char *secret, char *pass) MINT *pk = mp_itom(0); MINT *sk = mp_itom(0); MINT *tmp; - MINT *base = mp_itom(BASE); + MINT *base = mp_itom((short)BASE); MINT *root = mp_itom(PROOT); MINT *modulus = mp_xtom(HEXMODULUS); short r; From 718d07c040d31be1411ebd71d58fe9c0a0ba6db7 Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Tue, 30 Aug 2016 19:20:26 +0000 Subject: [PATCH 27/86] iscsi_initiator: make logout_req::reason unsigned char Previously this reported an error from Clang 3.9.0: implict conversion from 'int' to 'char' changes value from 128 to -128. Discussed with: dim, trasz Sponsored by: The FreeBSD Foundation Differential Revision: https://reviews.freebsd.org/D7699 --- sys/dev/iscsi_initiator/iscsi.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sys/dev/iscsi_initiator/iscsi.h b/sys/dev/iscsi_initiator/iscsi.h index 31421138ea15..5f9d36b1b2b7 100644 --- a/sys/dev/iscsi_initiator/iscsi.h +++ b/sys/dev/iscsi_initiator/iscsi.h @@ -356,7 +356,7 @@ typedef struct text_req { typedef struct logout_req { char cmd; // 0x06 - char reason; // 0 - close session + u_char reason; // 0 - close session // 1 - close connection // 2 - remove the connection for recovery char _2[2]; From 533f3e1026c2e2ab4ddc136aafeecae024dd8e49 Mon Sep 17 00:00:00 2001 From: Bryan Drewery Date: Tue, 30 Aug 2016 19:26:07 +0000 Subject: [PATCH 28/86] Reduce duplicated logic for !SMP Sponsored by: EMC / Isilon Storage Division --- sys/kern/subr_smp.c | 11 ++--------- 1 file changed, 2 insertions(+), 9 deletions(-) diff --git a/sys/kern/subr_smp.c b/sys/kern/subr_smp.c index 4f3b51de2765..d98b1b7212ea 100644 --- a/sys/kern/subr_smp.c +++ b/sys/kern/subr_smp.c @@ -779,15 +779,8 @@ smp_rendezvous(void (*setup_func)(void *), void *arg) { - /* Look comments in the smp_rendezvous_cpus() case. */ - spinlock_enter(); - if (setup_func != NULL) - setup_func(arg); - if (action_func != NULL) - action_func(arg); - if (teardown_func != NULL) - teardown_func(arg); - spinlock_exit(); + smp_rendezvous_cpus(all_cpus, setup_func, action_func, teardown_func, + arg); } /* From 66a5fa5d99e242b91d2151ecf06776d45112eaa0 Mon Sep 17 00:00:00 2001 From: "Pedro F. Giffuni" Date: Tue, 30 Aug 2016 19:39:33 +0000 Subject: [PATCH 29/86] libcpp: Complete the __COUNTER__ support with upstream implementation. We brought an original __COUNTER__ implementation in r228474, however, it was missing documentation and it had a different behaviour for precompiled headers with respect to the upstream version. Since the upstream version is under the same license as GCC4.2, bring the missing pieces to reduce differences against upstream. Optained from: GCC pre-4.3 (rev. 125041 ; GPLv2) --- contrib/gcc/doc/cpp.texi | 7 +++++ contrib/gcclibs/libcpp/ChangeLog.gcc43 | 11 +++++++ contrib/gcclibs/libcpp/internal.h | 3 +- contrib/gcclibs/libcpp/macro.c | 2 +- contrib/gcclibs/libcpp/pch.c | 41 ++++++++++++++++++++++++++ 5 files changed, 62 insertions(+), 2 deletions(-) diff --git a/contrib/gcc/doc/cpp.texi b/contrib/gcc/doc/cpp.texi index 26bc6b70080c..fa6822771476 100644 --- a/contrib/gcc/doc/cpp.texi +++ b/contrib/gcc/doc/cpp.texi @@ -1912,6 +1912,13 @@ underscores. @table @code +@item __COUNTER__ +This macro expands to sequential integral values starting from 0. In +conjuction with the @code{##} operator, this provides a convenient means to +generate unique identifiers. Care must be taken to ensure that +@code{__COUNTER__} is not expanded prior to inclusion of precompiled headers +which use it. Otherwise, the precompiled headers will not be used. + @item __GNUC__ @itemx __GNUC_MINOR__ @itemx __GNUC_PATCHLEVEL__ diff --git a/contrib/gcclibs/libcpp/ChangeLog.gcc43 b/contrib/gcclibs/libcpp/ChangeLog.gcc43 index da70d1c30056..be5174336323 100644 --- a/contrib/gcclibs/libcpp/ChangeLog.gcc43 +++ b/contrib/gcclibs/libcpp/ChangeLog.gcc43 @@ -12,6 +12,17 @@ PR preprocessor/14331 * lex.c (_cpp_get_fresh_line): Don't warn if no newline at EOF. +2007-05-24 Ollie Wild (r125041) + + * macro.c (_cpp_builtin_macro_text): Handle BT_COUNTER. + * pch.c (cpp_write_pch_deps): Save __COUNTER__ state. + (cpp_write_pch_state): Save __COUNTER__ state. + (cpp_valid_state): Check valid __COUNTER__ state. + (cpp_read_state): Read new __COUNTER__ state. + * include/cpplib.h (enum builtin_type): Add BT_COUNTER enumerator. + * init.c (builtin_array): Add __COUNTER__/BT_COUNTER. + * internal.h (struct cpp_reader): Add counter member. + 2007-05-21 Ian Lance Taylor (r124929) * internal.h (struct cpp_reader): Add new fields: diff --git a/contrib/gcclibs/libcpp/internal.h b/contrib/gcclibs/libcpp/internal.h index d685e283c5cf..d882d8d9b304 100644 --- a/contrib/gcclibs/libcpp/internal.h +++ b/contrib/gcclibs/libcpp/internal.h @@ -458,7 +458,8 @@ struct cpp_reader of precompiled headers. */ struct cpp_savedstate *savedstate; - unsigned int nextcounter; + /* Next value of __COUNTER__ macro. */ + unsigned int counter; }; /* Character classes. Based on the more primitive macros in safe-ctype.h. diff --git a/contrib/gcclibs/libcpp/macro.c b/contrib/gcclibs/libcpp/macro.c index e9d4681a398a..059f0e3c3ae4 100644 --- a/contrib/gcclibs/libcpp/macro.c +++ b/contrib/gcclibs/libcpp/macro.c @@ -268,7 +268,7 @@ _cpp_builtin_macro_text (cpp_reader *pfile, cpp_hashnode *node) if (CPP_OPTION (pfile, directives_only) && pfile->state.in_directive) cpp_error (pfile, CPP_DL_ERROR, "__COUNTER__ expanded inside directive with -fdirectives-only"); - number = pfile->nextcounter++; + number = pfile->counter++; break; } diff --git a/contrib/gcclibs/libcpp/pch.c b/contrib/gcclibs/libcpp/pch.c index 624befd09d8f..1db2aa70b80b 100644 --- a/contrib/gcclibs/libcpp/pch.c +++ b/contrib/gcclibs/libcpp/pch.c @@ -337,6 +337,14 @@ cpp_write_pch_deps (cpp_reader *r, FILE *f) /* Free the saved state. */ free (ss); r->savedstate = NULL; + + /* Save the next value of __COUNTER__. */ + if (fwrite (&r->counter, sizeof (r->counter), 1, f) != 1) + { + cpp_errno (r, CPP_DL_ERROR, "while writing precompiled header"); + return -1; + } + return 0; } @@ -361,6 +369,15 @@ cpp_write_pch_state (cpp_reader *r, FILE *f) return -1; } + /* Save the next __COUNTER__ value. When we include a precompiled header, + we need to start at the offset we would have if the header had been + included normally. */ + if (fwrite (&r->counter, sizeof (r->counter), 1, f) != 1) + { + cpp_errno (r, CPP_DL_ERROR, "while writing precompiled header"); + return -1; + } + return 0; } @@ -423,6 +440,7 @@ cpp_valid_state (cpp_reader *r, const char *name, int fd) struct ht_node_list nl = { 0, 0, 0 }; unsigned char *first, *last; unsigned int i; + unsigned int counter; /* Read in the list of identifiers that must be defined Check that they are defined in the same way. */ @@ -524,7 +542,23 @@ cpp_valid_state (cpp_reader *r, const char *name, int fd) } free(nl.defs); + nl.defs = NULL; free (undeftab); + undeftab = NULL; + + /* Read in the next value of __COUNTER__. + Check that (a) __COUNTER__ was not used in the pch or (b) __COUNTER__ + has not been used in this translation unit. */ + if (read (fd, &counter, sizeof (counter)) != sizeof (counter)) + goto error; + if (counter && r->counter) + { + if (CPP_OPTION (r, warn_invalid_pch)) + cpp_error (r, CPP_DL_WARNING_SYSHDR, + "%s: not used because `__COUNTER__' is invalid", + name); + goto fail; + } /* We win! */ return 0; @@ -631,6 +665,7 @@ cpp_read_state (cpp_reader *r, const char *name, FILE *f, { size_t i; struct lexer_state old_state; + unsigned int counter; /* Restore spec_nodes, which will be full of references to the old hashtable entries and so will now be invalid. */ @@ -690,6 +725,12 @@ cpp_read_state (cpp_reader *r, const char *name, FILE *f, if (! _cpp_read_file_entries (r, f)) goto error; + if (fread (&counter, sizeof (counter), 1, f) != 1) + goto error; + + if (!r->counter) + r->counter = counter; + return 0; error: From d7795033dd391c7fd45b3e6a5abad7d75669cf88 Mon Sep 17 00:00:00 2001 From: Mariusz Zaborski Date: Tue, 30 Aug 2016 19:58:41 +0000 Subject: [PATCH 30/86] Fix Capsicum syscalls test suite. --- .../regression/capsicum/syscalls/cap_fcntls_limit.c | 10 ++++++++-- .../regression/capsicum/syscalls/cap_ioctls_limit.c | 12 ++++++++++-- 2 files changed, 18 insertions(+), 4 deletions(-) diff --git a/tools/regression/capsicum/syscalls/cap_fcntls_limit.c b/tools/regression/capsicum/syscalls/cap_fcntls_limit.c index f37710d9df12..e3a05bf66149 100644 --- a/tools/regression/capsicum/syscalls/cap_fcntls_limit.c +++ b/tools/regression/capsicum/syscalls/cap_fcntls_limit.c @@ -157,13 +157,16 @@ static void fcntl_tests_1(int fd) { uint32_t fcntlrights; + cap_rights_t rights; CHECK(cap_fcntls_limit(fd, CAP_FCNTL_GETFL) == 0); fcntlrights = 0; CHECK(cap_fcntls_get(fd, &fcntlrights) == 0); CHECK(fcntlrights == CAP_FCNTL_GETFL); - CHECK(cap_rights_limit(fd, CAP_ALL & ~CAP_FCNTL) == 0); + CAP_ALL(&rights); + cap_rights_clear(&rights, CAP_FCNTL); + CHECK(cap_rights_limit(fd, &rights) == 0); fcntlrights = CAP_FCNTL_ALL; CHECK(cap_fcntls_get(fd, &fcntlrights) == 0); @@ -206,8 +209,11 @@ static void fcntl_tests_2(int fd) { uint32_t fcntlrights; + cap_rights_t rights; - CHECK(cap_rights_limit(fd, CAP_ALL & ~CAP_FCNTL) == 0); + CAP_ALL(&rights); + cap_rights_clear(&rights, CAP_FCNTL); + CHECK(cap_rights_limit(fd, &rights) == 0); fcntlrights = CAP_FCNTL_ALL; CHECK(cap_fcntls_get(fd, &fcntlrights) == 0); diff --git a/tools/regression/capsicum/syscalls/cap_ioctls_limit.c b/tools/regression/capsicum/syscalls/cap_ioctls_limit.c index 27d85896533f..2ed00f175469 100644 --- a/tools/regression/capsicum/syscalls/cap_ioctls_limit.c +++ b/tools/regression/capsicum/syscalls/cap_ioctls_limit.c @@ -131,6 +131,7 @@ static void ioctl_tests_1(int fd) { unsigned long cmds[2]; + cap_rights_t rights; cmds[0] = FIOCLEX; CHECK(cap_ioctls_limit(fd, cmds, 1) == 0); @@ -139,7 +140,10 @@ ioctl_tests_1(int fd) CHECK(cmds[0] == FIOCLEX); CHECK(cmds[1] == 0); - CHECK(cap_rights_limit(fd, CAP_ALL & ~CAP_IOCTL) == 0); + CAP_ALL(&rights); + cap_rights_clear(&rights, CAP_IOCTL); + + CHECK(cap_rights_limit(fd, &rights) == 0); CHECK(cap_ioctls_get(fd, cmds, nitems(cmds)) == 0); cmds[0] = FIOCLEX; @@ -173,8 +177,12 @@ static void ioctl_tests_2(int fd) { unsigned long cmds[2]; + cap_rights_t rights; - CHECK(cap_rights_limit(fd, CAP_ALL & ~CAP_IOCTL) == 0); + CAP_ALL(&rights); + cap_rights_clear(&rights, CAP_IOCTL); + + CHECK(cap_rights_limit(fd, &rights) == 0); CHECK(cap_ioctls_get(fd, cmds, nitems(cmds)) == 0); cmds[0] = FIOCLEX; From deda53cd9b7deca6dfda13c25769d540d6dd5c84 Mon Sep 17 00:00:00 2001 From: Dimitry Andric Date: Tue, 30 Aug 2016 20:24:50 +0000 Subject: [PATCH 31/86] Fix warnings in tnftp about invalid constant conversions, e.g.: contrib/tnftp/src/ftp.c:2067:11: error: implicit conversion from 'int' to 'char' changes value from 255 to -1 [-Werror,-Wconstant-conversion] buf[0] = IAC; ~ ^~~ /usr/include/arpa/telnet.h:39:13: note: expanded from macro 'IAC' #define IAC 255 /* interpret as command: */ ^~~ contrib/tnftp/src/ftp.c:2068:11: error: implicit conversion from 'int' to 'char' changes value from 244 to -12 [-Werror,-Wconstant-conversion] buf[1] = IP; ~ ^~ /usr/include/arpa/telnet.h:50:12: note: expanded from macro 'IP' #define IP 244 /* interrupt process--permanently */ ^~~ Use an unsigned char buffer instead. MFC after: 1 week --- contrib/tnftp/src/ftp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contrib/tnftp/src/ftp.c b/contrib/tnftp/src/ftp.c index 4c4942f1bc1d..82d4042e1494 100644 --- a/contrib/tnftp/src/ftp.c +++ b/contrib/tnftp/src/ftp.c @@ -2050,7 +2050,7 @@ abort_squared(int dummy) void abort_remote(FILE *din) { - char buf[BUFSIZ]; + unsigned char buf[BUFSIZ]; int nfnd; if (cout == NULL) { From 866616de6e692e17b3aaa14865b92a770ad51515 Mon Sep 17 00:00:00 2001 From: Dimitry Andric Date: Tue, 30 Aug 2016 20:27:22 +0000 Subject: [PATCH 32/86] Fix warnings in telnet about invalid constant conversions, e.g.: contrib/telnet/telnet/commands.c:2914:13: error: implicit conversion from 'int' to 'char' changes value from 137 to -119 [-Werror,-Wconstant-conversion] *lsrp++ = IPOPT_SSRR; ~ ^~~~~~~~~~ /usr/include/netinet/ip.h:152:21: note: expanded from macro 'IPOPT_SSRR' #define IPOPT_SSRR 137 /* strict source route */ ^~~ contrib/telnet/telnet/commands.c:2916:13: error: implicit conversion from 'int' to 'char' changes value from 131 to -125 [-Werror,-Wconstant-conversion] *lsrp++ = IPOPT_LSRR; ~ ^~~~~~~~~~ /usr/include/netinet/ip.h:148:21: note: expanded from macro 'IPOPT_LSRR' #define IPOPT_LSRR 131 /* loose source route */ ^~~ Use unsigned char buffers instead. MFC after: 1 week --- contrib/telnet/telnet/commands.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/contrib/telnet/telnet/commands.c b/contrib/telnet/telnet/commands.c index 74cce6d5dedc..02a0de524d3f 100644 --- a/contrib/telnet/telnet/commands.c +++ b/contrib/telnet/telnet/commands.c @@ -112,7 +112,7 @@ static int send_tncmd(void (*)(int, int), const char *, char *); static int setmod(int); static int clearmode(int); static int modehelp(void); -static int sourceroute(struct addrinfo *, char *, char **, int *, int *, int *); +static int sourceroute(struct addrinfo *, char *, unsigned char **, int *, int *, int *); typedef struct { const char *name; /* command name */ @@ -2171,7 +2171,7 @@ switch_af(struct addrinfo **aip) int tn(int argc, char *argv[]) { - char *srp = 0; + unsigned char *srp = 0; int proto, opt; int srlen; int srcroute = 0, result; @@ -2844,10 +2844,10 @@ cmdrc(char *m1, char *m2) * setsockopt, as socket protocol family. */ static int -sourceroute(struct addrinfo *ai, char *arg, char **cpp, int *lenp, int *protop, int *optp) +sourceroute(struct addrinfo *ai, char *arg, unsigned char **cpp, int *lenp, int *protop, int *optp) { static char buf[1024 + ALIGNBYTES]; /*XXX*/ - char *cp, *cp2, *lsrp, *ep; + unsigned char *cp, *cp2, *lsrp, *ep; struct sockaddr_in *_sin; #ifdef INET6 struct sockaddr_in6 *sin6; From 1221d4299083f5db12d023625bb10fa287450136 Mon Sep 17 00:00:00 2001 From: Jilles Tjoelker Date: Tue, 30 Aug 2016 21:43:57 +0000 Subject: [PATCH 33/86] getvfsbyname(3): Remove [EFAULT] error. Since r101651 in 2002, getvfsbyname() has written *vfc using userland memcpy(), so the [EFAULT] error no longer occurs. MFC after: 1 week --- lib/libc/gen/getvfsbyname.3 | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/lib/libc/gen/getvfsbyname.3 b/lib/libc/gen/getvfsbyname.3 index f2a5965e826f..a0fc843a0123 100644 --- a/lib/libc/gen/getvfsbyname.3 +++ b/lib/libc/gen/getvfsbyname.3 @@ -28,7 +28,7 @@ .\" @(#)kvm_getvfsbyname.3 8.3 (Berkeley) 5/4/95 .\" $FreeBSD$ .\" -.Dd April 5, 2007 +.Dd August 30, 2016 .Dt GETVFSBYNAME 3 .Os .Sh NAME @@ -97,11 +97,6 @@ sysctl is set to .Sh ERRORS The following errors may be reported: .Bl -tag -width Er -.It Bq Er EFAULT -The -.Fa vfc -argument -points to an invalid address. .It Bq Er ENOENT The .Fa name From 7f5b9769ec0636b7b550275c66cd20c97780607e Mon Sep 17 00:00:00 2001 From: Mateusz Guzik Date: Tue, 30 Aug 2016 21:48:10 +0000 Subject: [PATCH 34/86] fd: simplify fd testing in fget_locked by casting to u_int --- sys/sys/filedesc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sys/sys/filedesc.h b/sys/sys/filedesc.h index b34a2f1ad645..89e8855fc52e 100644 --- a/sys/sys/filedesc.h +++ b/sys/sys/filedesc.h @@ -201,7 +201,7 @@ fget_locked(struct filedesc *fdp, int fd) FILEDESC_LOCK_ASSERT(fdp); - if (fd < 0 || fd > fdp->fd_lastfile) + if ((u_int)fd > fdp->fd_lastfile) return (NULL); return (fdp->fd_ofiles[fd].fde_file); From 4cbafea09c219fd146e4f045f705620e485b1611 Mon Sep 17 00:00:00 2001 From: Mateusz Guzik Date: Tue, 30 Aug 2016 21:53:22 +0000 Subject: [PATCH 35/86] fd: add fdeget_locked and use in kern_descrip --- sys/kern/kern_descrip.c | 26 ++++++++++++-------------- sys/sys/filedesc.h | 12 ++++++++++++ 2 files changed, 24 insertions(+), 14 deletions(-) diff --git a/sys/kern/kern_descrip.c b/sys/kern/kern_descrip.c index f3959acfbd5c..0302084fb202 100644 --- a/sys/kern/kern_descrip.c +++ b/sys/kern/kern_descrip.c @@ -517,28 +517,26 @@ kern_fcntl(struct thread *td, int fd, int cmd, intptr_t arg) break; case F_GETFD: + error = EBADF; FILEDESC_SLOCK(fdp); - if (fget_locked(fdp, fd) == NULL) { - FILEDESC_SUNLOCK(fdp); - error = EBADF; - break; + fde = fdeget_locked(fdp, fd); + if (fde != NULL) { + td->td_retval[0] = + (fde->fde_flags & UF_EXCLOSE) ? FD_CLOEXEC : 0; + error = 0; } - fde = &fdp->fd_ofiles[fd]; - td->td_retval[0] = - (fde->fde_flags & UF_EXCLOSE) ? FD_CLOEXEC : 0; FILEDESC_SUNLOCK(fdp); break; case F_SETFD: + error = EBADF; FILEDESC_XLOCK(fdp); - if (fget_locked(fdp, fd) == NULL) { - FILEDESC_XUNLOCK(fdp); - error = EBADF; - break; + fde = fdeget_locked(fdp, fd); + if (fde != NULL) { + fde->fde_flags = (fde->fde_flags & ~UF_EXCLOSE) | + (arg & FD_CLOEXEC ? UF_EXCLOSE : 0); + error = 0; } - fde = &fdp->fd_ofiles[fd]; - fde->fde_flags = (fde->fde_flags & ~UF_EXCLOSE) | - (arg & FD_CLOEXEC ? UF_EXCLOSE : 0); FILEDESC_XUNLOCK(fdp); break; diff --git a/sys/sys/filedesc.h b/sys/sys/filedesc.h index 89e8855fc52e..bdb42460c9c4 100644 --- a/sys/sys/filedesc.h +++ b/sys/sys/filedesc.h @@ -207,6 +207,18 @@ fget_locked(struct filedesc *fdp, int fd) return (fdp->fd_ofiles[fd].fde_file); } +static __inline struct filedescent * +fdeget_locked(struct filedesc *fdp, int fd) +{ + + FILEDESC_LOCK_ASSERT(fdp); + + if ((u_int)fd > fdp->fd_lastfile) + return (NULL); + + return (&fdp->fd_ofiles[fd]); +} + static __inline bool fd_modified(struct filedesc *fdp, int fd, seq_t seq) { From dd6ca285cbd0522e310458838d9a156b360db16a Mon Sep 17 00:00:00 2001 From: Olivier Houchard Date: Tue, 30 Aug 2016 22:32:33 +0000 Subject: [PATCH 36/86] Garbage collect bits forgotten in r295267. --- sys/arm/arm/cpufunc_asm_xscale_c3.S | 2 -- 1 file changed, 2 deletions(-) diff --git a/sys/arm/arm/cpufunc_asm_xscale_c3.S b/sys/arm/arm/cpufunc_asm_xscale_c3.S index 4e2c99999cac..a8344a611f53 100644 --- a/sys/arm/arm/cpufunc_asm_xscale_c3.S +++ b/sys/arm/arm/cpufunc_asm_xscale_c3.S @@ -364,8 +364,6 @@ ENTRY(xscalec3_setttb) #ifdef CACHE_CLEAN_BLOCK_INTR msr cpsr_fsxc, r3 -#else - str r2, [r3] #endif RET END(xscalec3_setttb) From 82d38881181137327b918320869a0310ec0e5a06 Mon Sep 17 00:00:00 2001 From: Bryan Drewery Date: Tue, 30 Aug 2016 22:48:05 +0000 Subject: [PATCH 37/86] AUTO_OBJ: Support SRCS/DPSRCS that contain '/' and require a nested OBJDIR. This is to be used by the new clang3.9 build and extends functionality added to 'make obj' in r279980. MFC after: 2 weeks Sponsored by: EMC / Isilon Storage Division --- share/mk/bsd.obj.mk | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/share/mk/bsd.obj.mk b/share/mk/bsd.obj.mk index 235d6eb12953..c9377db63c55 100644 --- a/share/mk/bsd.obj.mk +++ b/share/mk/bsd.obj.mk @@ -51,6 +51,30 @@ CANONICALOBJDIR= ${.OBJDIR} # but this makefile does not want it! .OBJDIR: ${.CURDIR} .endif +# Handle special case where SRCS is full-pathed and requires +# nested objdirs. This duplicates some auto.obj.mk logic. +.if (!empty(SRCS:M*/*) || !empty(DPSRCS:M*/*)) && \ + (${.TARGETS} == "" || ${.TARGETS:Nclean*:N*clean:Ndestroy*} != "") +_wantdirs= ${SRCS:M*/*:H} ${DPSRCS:M*/*:H} +.if !empty(_wantdirs) +_wantdirs:= ${_wantdirs:O:u} +_needdirs= +.for _dir in ${_wantdirs} +.if !exists(${.OBJDIR}/${_dir}/) +_needdirs+= ${_dir} +.endif +.endfor +.endif +.if !empty(_needdirs) +#_mkneededdirs!= umask ${OBJDIR_UMASK:U002}; ${Mkdirs} ${_needdirs} +__objdir_made != umask ${OBJDIR_UMASK:U002}; ${Mkdirs}; \ + for dir in ${_needdirs}; do \ + dir=${.OBJDIR}/$${dir}; \ + ${ECHO_TRACE} "[Creating nested objdir $${dir}...]" >&2; \ + Mkdirs $${dir}; \ + done +.endif +.endif # !empty(SRCS:M*/*) || !empty(DPSRCS:M*/*) .elif defined(MAKEOBJDIRPREFIX) CANONICALOBJDIR:=${MAKEOBJDIRPREFIX}${.CURDIR} .elif defined(MAKEOBJDIR) && ${MAKEOBJDIR:M/*} != "" From 5d621118feb7a35ba417dfee63230732af2fa213 Mon Sep 17 00:00:00 2001 From: Olivier Houchard Date: Tue, 30 Aug 2016 23:30:26 +0000 Subject: [PATCH 38/86] Some old arm ports don't load the kernel at the beginning of the memory, because the bootloader, ie redboot, won't let them do so, and so used the memory before the kernel for early memory allocation, such as pagetables, stacks, etc... Make a bit of an effort to try to get that memory mapped. --- sys/arm/arm/locore-v4.S | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/sys/arm/arm/locore-v4.S b/sys/arm/arm/locore-v4.S index bd39ae12b028..4d10fb3f0e7e 100644 --- a/sys/arm/arm/locore-v4.S +++ b/sys/arm/arm/locore-v4.S @@ -195,6 +195,16 @@ Lunmapped: ldr r2, =(KERNVIRTADDR) mov r3, #64 bl build_pagetables +#if defined(PHYSADDR) && (KERNVIRTADDR != KERNBASE) +/* + * If the kernel wasn't loaded at the beginning of the ram, map the memory + * before the kernel too, as some ports use that for pagetables, stack, etc... + */ + ldr r1, =PHYSADDR + ldr r2, =KERNBASE + ldr r3, =((KERNVIRTADDR - KERNBASE) / L1_S_SIZE) + bl build_pagetables +#endif /* Create a device mapping for early_printf if specified. */ #if defined(SOCDEV_PA) && defined(SOCDEV_VA) From 3681e5c3ecdbeda9194d02240377f174ca16e9cc Mon Sep 17 00:00:00 2001 From: Olivier Houchard Date: Tue, 30 Aug 2016 23:32:38 +0000 Subject: [PATCH 39/86] Nuke obio_bs_tag, it was used before it was initialized, and arm_base_bs_tag is the same, anyway. --- sys/arm/xscale/i8134x/crb_machdep.c | 2 +- sys/arm/xscale/i8134x/obio.c | 5 +---- sys/arm/xscale/i8134x/obiovar.h | 1 - sys/arm/xscale/i8134x/uart_cpu_i81342.c | 4 ++-- 4 files changed, 4 insertions(+), 8 deletions(-) diff --git a/sys/arm/xscale/i8134x/crb_machdep.c b/sys/arm/xscale/i8134x/crb_machdep.c index 898bbaa36876..1b0852c80093 100644 --- a/sys/arm/xscale/i8134x/crb_machdep.c +++ b/sys/arm/xscale/i8134x/crb_machdep.c @@ -286,7 +286,7 @@ initarm(struct arm_boot_params *abp) cpu_setup(); i80321_calibrate_delay(); - i81342_sdram_bounds(obio_bs_tag, IOP34X_VADDR, &memstart, &memsize); + i81342_sdram_bounds(arm_base_bs_tag, IOP34X_VADDR, &memstart, &memsize); physmem = memsize / PAGE_SIZE; cninit(); /* Set stack for exception handlers */ diff --git a/sys/arm/xscale/i8134x/obio.c b/sys/arm/xscale/i8134x/obio.c index f61893befdac..a1ebc890a367 100644 --- a/sys/arm/xscale/i8134x/obio.c +++ b/sys/arm/xscale/i8134x/obio.c @@ -56,8 +56,6 @@ __FBSDID("$FreeBSD$"); #include #include -bus_space_tag_t obio_bs_tag; - static int obio_probe(device_t dev) { @@ -69,8 +67,7 @@ obio_attach(device_t dev) { struct obio_softc *sc = device_get_softc(dev); - obio_bs_tag = arm_base_bs_tag; - sc->oba_st = obio_bs_tag; + sc->oba_st = arm_base_bs_tag; sc->oba_rman.rm_type = RMAN_ARRAY; sc->oba_rman.rm_descr = "OBIO I/O"; if (rman_init(&sc->oba_rman) != 0 || diff --git a/sys/arm/xscale/i8134x/obiovar.h b/sys/arm/xscale/i8134x/obiovar.h index 237dd9e7d944..9ae86fe0857c 100644 --- a/sys/arm/xscale/i8134x/obiovar.h +++ b/sys/arm/xscale/i8134x/obiovar.h @@ -50,6 +50,5 @@ struct obio_softc { struct rman oba_irq_rman; }; -extern bus_space_tag_t obio_bs_tag; #endif /* _IQ80321_OBIOVAR_H_ */ diff --git a/sys/arm/xscale/i8134x/uart_cpu_i81342.c b/sys/arm/xscale/i8134x/uart_cpu_i81342.c index 1d98d78bcfe2..8f4581ce0094 100644 --- a/sys/arm/xscale/i8134x/uart_cpu_i81342.c +++ b/sys/arm/xscale/i8134x/uart_cpu_i81342.c @@ -54,14 +54,14 @@ uart_cpu_getdev(int devtype, struct uart_devinfo *di) di->ops = uart_getops(&uart_ns8250_class); di->bas.chan = 0; - di->bas.bst = obio_bs_tag; + di->bas.bst = arm_base_bs_tag; di->bas.regshft = 2; di->bas.rclk = 33334000; di->baudrate = 115200; di->databits = 8; di->stopbits = 1; di->parity = UART_PARITY_NONE; - uart_bus_space_io = obio_bs_tag; + uart_bus_space_io = arm_base_bs_tag; uart_bus_space_mem = NULL; di->bas.bsh = IOP34X_UART0_VADDR; return (0); From 3de3ff08ffae1e49cb2b9d8ad655ab506d1d97b3 Mon Sep 17 00:00:00 2001 From: Baptiste Daroussin Date: Wed, 31 Aug 2016 00:04:09 +0000 Subject: [PATCH 40/86] Make libc++.so ldscript sysroot friendly --- lib/libc++/libc++.ldscript | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/libc++/libc++.ldscript b/lib/libc++/libc++.ldscript index bec57f161698..aad599d8cdc5 100644 --- a/lib/libc++/libc++.ldscript +++ b/lib/libc++/libc++.ldscript @@ -1,2 +1,2 @@ /* $FreeBSD$ */ -GROUP ( @@SHLIB@@ @@LIBDIR@@/libcxxrt.so ) +GROUP ( =@@SHLIB@@ =@@LIBDIR@@/libcxxrt.so ) From 4b5fbd3078415972823303833f2cd8867d4b239c Mon Sep 17 00:00:00 2001 From: Baptiste Daroussin Date: Wed, 31 Aug 2016 00:11:35 +0000 Subject: [PATCH 41/86] Revert 305098 Was a wrong assumption from me badly look at the errors cross toolchain was telling me --- lib/libc++/libc++.ldscript | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/libc++/libc++.ldscript b/lib/libc++/libc++.ldscript index aad599d8cdc5..bec57f161698 100644 --- a/lib/libc++/libc++.ldscript +++ b/lib/libc++/libc++.ldscript @@ -1,2 +1,2 @@ /* $FreeBSD$ */ -GROUP ( =@@SHLIB@@ =@@LIBDIR@@/libcxxrt.so ) +GROUP ( @@SHLIB@@ @@LIBDIR@@/libcxxrt.so ) From 591ef90abd4f85c68e0f19f4f5ff4b8f27e895a7 Mon Sep 17 00:00:00 2001 From: Oleksandr Tymoshenko Date: Wed, 31 Aug 2016 01:04:57 +0000 Subject: [PATCH 42/86] Update VCHIQ driver to upstream version 4eda74f2 PR: 211525 Submitted by: Sylvain Garrigues --- .../vchiq/interface/vchiq_arm/vchiq_arm.c | 75 ++++++++++++------- .../vchiq/interface/vchiq_arm/vchiq_core.c | 45 ++++++----- 2 files changed, 69 insertions(+), 51 deletions(-) diff --git a/sys/contrib/vchiq/interface/vchiq_arm/vchiq_arm.c b/sys/contrib/vchiq/interface/vchiq_arm/vchiq_arm.c index 5bd50591e212..89d9b9ef9138 100644 --- a/sys/contrib/vchiq/interface/vchiq_arm/vchiq_arm.c +++ b/sys/contrib/vchiq/interface/vchiq_arm/vchiq_arm.c @@ -46,10 +46,10 @@ #define VCHIQ_MINOR 0 /* Some per-instance constants */ -#define MAX_COMPLETIONS 16 +#define MAX_COMPLETIONS 128 #define MAX_SERVICES 64 #define MAX_ELEMENTS 8 -#define MSG_QUEUE_SIZE 64 +#define MSG_QUEUE_SIZE 128 #define KEEPALIVE_VER 1 #define KEEPALIVE_VER_MIN KEEPALIVE_VER @@ -208,30 +208,32 @@ add_completion(VCHIQ_INSTANCE_T instance, VCHIQ_REASON_T reason, void *bulk_userdata) { VCHIQ_COMPLETION_DATA_T *completion; + int insert; DEBUG_INITIALISE(g_state.local) - while (instance->completion_insert == - (instance->completion_remove + MAX_COMPLETIONS)) { + insert = instance->completion_insert; + while ((insert - instance->completion_remove) >= MAX_COMPLETIONS) { /* Out of space - wait for the client */ DEBUG_TRACE(SERVICE_CALLBACK_LINE); vchiq_log_trace(vchiq_arm_log_level, "add_completion - completion queue full"); DEBUG_COUNT(COMPLETION_QUEUE_FULL_COUNT); + if (down_interruptible(&instance->remove_event) != 0) { vchiq_log_info(vchiq_arm_log_level, "service_callback interrupted"); return VCHIQ_RETRY; - } else if (instance->closing) { + } + + if (instance->closing) { vchiq_log_info(vchiq_arm_log_level, "service_callback closing"); - return VCHIQ_ERROR; + return VCHIQ_SUCCESS; } DEBUG_TRACE(SERVICE_CALLBACK_LINE); } - completion = - &instance->completions[instance->completion_insert & - (MAX_COMPLETIONS - 1)]; + completion = &instance->completions[insert & (MAX_COMPLETIONS - 1)]; completion->header = header; completion->reason = reason; @@ -252,9 +254,9 @@ add_completion(VCHIQ_INSTANCE_T instance, VCHIQ_REASON_T reason, wmb(); if (reason == VCHIQ_MESSAGE_AVAILABLE) - user_service->message_available_pos = - instance->completion_insert; - instance->completion_insert++; + user_service->message_available_pos = insert; + + instance->completion_insert = ++insert; up(&instance->insert_event); @@ -279,6 +281,7 @@ service_callback(VCHIQ_REASON_T reason, VCHIQ_HEADER_T *header, USER_SERVICE_T *user_service; VCHIQ_SERVICE_T *service; VCHIQ_INSTANCE_T instance; + int skip_completion = 0; DEBUG_INITIALISE(g_state.local) DEBUG_TRACE(SERVICE_CALLBACK_LINE); @@ -345,9 +348,6 @@ service_callback(VCHIQ_REASON_T reason, VCHIQ_HEADER_T *header, user_service->msg_queue[user_service->msg_insert & (MSG_QUEUE_SIZE - 1)] = header; user_service->msg_insert++; - spin_unlock(&msg_queue_spinlock); - - up(&user_service->insert_event); /* If there is a thread waiting in DEQUEUE_MESSAGE, or if ** there is a MESSAGE_AVAILABLE in the completion queue then @@ -356,13 +356,22 @@ service_callback(VCHIQ_REASON_T reason, VCHIQ_HEADER_T *header, if (((user_service->message_available_pos - instance->completion_remove) >= 0) || user_service->dequeue_pending) { - DEBUG_TRACE(SERVICE_CALLBACK_LINE); user_service->dequeue_pending = 0; - return VCHIQ_SUCCESS; + skip_completion = 1; } + spin_unlock(&msg_queue_spinlock); + + up(&user_service->insert_event); + header = NULL; } + + if (skip_completion) { + DEBUG_TRACE(SERVICE_CALLBACK_LINE); + return VCHIQ_SUCCESS; + } + DEBUG_TRACE(SERVICE_CALLBACK_LINE); return add_completion(instance, reason, header, user_service, @@ -789,7 +798,7 @@ vchiq_ioctl(struct cdev *cdev, u_long cmd, caddr_t arg, int fflag, break; } - memcpy(&args, (const void*)arg, sizeof(args)); + memcpy(&args, (const void*)arg, sizeof(args)); lmutex_lock(&instance->completion_mutex); @@ -797,6 +806,7 @@ vchiq_ioctl(struct cdev *cdev, u_long cmd, caddr_t arg, int fflag, while ((instance->completion_remove == instance->completion_insert) && !instance->closing) { + DEBUG_TRACE(AWAIT_COMPLETION_LINE); lmutex_unlock(&instance->completion_mutex); rc = down_interruptible(&instance->insert_event); @@ -811,24 +821,29 @@ vchiq_ioctl(struct cdev *cdev, u_long cmd, caddr_t arg, int fflag, } DEBUG_TRACE(AWAIT_COMPLETION_LINE); - /* A read memory barrier is needed to stop prefetch of a stale - ** completion record - */ - rmb(); - if (ret == 0) { int msgbufcount = args.msgbufcount; + int remove; + + remove = instance->completion_remove; + for (count = 0; count < args.count; count++) { VCHIQ_COMPLETION_DATA_T *completion; VCHIQ_SERVICE_T *service1; USER_SERVICE_T *user_service; VCHIQ_HEADER_T *header; - if (instance->completion_remove == - instance->completion_insert) + + if (remove == instance->completion_insert) break; + completion = &instance->completions[ - instance->completion_remove & - (MAX_COMPLETIONS - 1)]; + remove & (MAX_COMPLETIONS - 1)]; + + + /* A read memory barrier is needed to prevent + ** the prefetch of a stale completion record + */ + rmb(); service1 = completion->service_userdata; user_service = service1->base.userdata; @@ -905,7 +920,11 @@ vchiq_ioctl(struct cdev *cdev, u_long cmd, caddr_t arg, int fflag, break; } - instance->completion_remove++; + /* Ensure that the above copy has completed + ** before advancing the remove pointer. */ + mb(); + + instance->completion_remove = ++remove; } if (msgbufcount != args.msgbufcount) { diff --git a/sys/contrib/vchiq/interface/vchiq_arm/vchiq_core.c b/sys/contrib/vchiq/interface/vchiq_arm/vchiq_core.c index 2ded208bae35..d96fcfd74297 100644 --- a/sys/contrib/vchiq/interface/vchiq_arm/vchiq_core.c +++ b/sys/contrib/vchiq/interface/vchiq_arm/vchiq_core.c @@ -622,15 +622,15 @@ process_free_queue(VCHIQ_STATE_T *state) BITSET_T service_found[BITSET_SIZE(VCHIQ_MAX_SERVICES)]; int slot_queue_available; - /* Use a read memory barrier to ensure that any state that may have - ** been modified by another thread is not masked by stale prefetched - ** values. */ - rmb(); - /* Find slots which have been freed by the other side, and return them ** to the available queue. */ slot_queue_available = state->slot_queue_available; + /* Use a memory barrier to ensure that any state that may have been + ** modified by another thread is not masked by stale prefetched + ** values. */ + mb(); + while (slot_queue_available != local->slot_queue_recycle) { unsigned int pos; int slot_index = local->slot_queue[slot_queue_available++ & @@ -638,6 +638,8 @@ process_free_queue(VCHIQ_STATE_T *state) char *data = (char *)SLOT_DATA_FROM_INDEX(state, slot_index); int data_found = 0; + rmb(); + vchiq_log_trace(vchiq_core_log_level, "%d: pfq %d=%x %x %x", state->id, slot_index, (unsigned int)data, local->slot_queue_recycle, slot_queue_available); @@ -753,6 +755,8 @@ process_free_queue(VCHIQ_STATE_T *state) up(&state->data_quota_event); } + mb(); + state->slot_queue_available = slot_queue_available; up(&state->slot_available_event); } @@ -904,16 +908,14 @@ queue_message(VCHIQ_STATE_T *state, VCHIQ_SERVICE_T *service, error_count); return VCHIQ_ERROR; } - if (i == 0) { - if (SRVTRACE_ENABLED(service, - VCHIQ_LOG_INFO)) - vchiq_log_dump_mem("Sent", 0, - header->data + pos, - min(64u, - elements[0].size)); - } } + if (SRVTRACE_ENABLED(service, + VCHIQ_LOG_INFO)) + vchiq_log_dump_mem("Sent", 0, + header->data, + min(16, pos)); + spin_lock("a_spinlock); service_quota->message_use_count++; @@ -1052,16 +1054,13 @@ queue_message_sync(VCHIQ_STATE_T *state, VCHIQ_SERVICE_T *service, error_count); return VCHIQ_ERROR; } - if (i == 0) { - if (vchiq_sync_log_level >= - VCHIQ_LOG_TRACE) - vchiq_log_dump_mem("Sent Sync", - 0, header->data + pos, - min(64u, - elements[0].size)); - } } + if (vchiq_sync_log_level >= VCHIQ_LOG_TRACE) + vchiq_log_dump_mem("Sent Sync", + 0, header->data, + min(16, pos)); + VCHIQ_SERVICE_STATS_INC(service, ctrl_tx_count); VCHIQ_SERVICE_STATS_ADD(service, ctrl_tx_bytes, size); } else { @@ -1732,7 +1731,7 @@ parse_rx_slots(VCHIQ_STATE_T *state) remoteport, localport, size); if (size > 0) vchiq_log_dump_mem("Rcvd", 0, header->data, - min(64, size)); + min(16, size)); } if (((unsigned int)header & VCHIQ_SLOT_MASK) + calc_stride(size) @@ -2202,7 +2201,7 @@ sync_func(void *v) remoteport, localport, size); if (size > 0) vchiq_log_dump_mem("Rcvd", 0, header->data, - min(64, size)); + min(16, size)); } switch (type) { From 0b1c7ee3222442381b3cb8d1e2ffc23508c22bf1 Mon Sep 17 00:00:00 2001 From: Warner Losh Date: Wed, 31 Aug 2016 03:55:50 +0000 Subject: [PATCH 43/86] Create a hook 'post-initialize' for people that want to define something (perhaps in loader.rc.local) that can read in .conf files after all the other .conf files have been read and override settings in them. This is quite handy if the .conf file name is determined while the loader is running, but might be generically useful for other things. If this hook exists, call it, otherwise don't do anything. Doing it in these functions ensures that this file is reliably read. It also works around a defect in forth where s" isn't allowed outside a function (well, in a compile context) leading to gross workarounds if one were to hack loader.rc like: : maybe-some-func s" some-func" sfind if execute else drop then ; maybe-some-func which somehow seems worse. Though I'm sure there's some clever forthy way of doing that with a macro. Sponsored by: Netflix, Inc --- sys/boot/forth/loader.4th | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/sys/boot/forth/loader.4th b/sys/boot/forth/loader.4th index a18fa1e351bc..bbacf2b08609 100644 --- a/sys/boot/forth/loader.4th +++ b/sys/boot/forth/loader.4th @@ -143,6 +143,8 @@ only forth definitions also support-functions s" /boot/defaults/loader.conf" initialize include_conf_files include_nextboot_file + \ If the user defined a post-initialize hook, call it now + s" post-initialize" sfind if execute else drop then \ Will *NOT* try to load kernel and modules if no configuration file \ was successfully loaded! any_conf_read? if @@ -165,12 +167,15 @@ only forth definitions also support-functions \ \ Overrides support.4th initialization word with one that does \ everything start one does, short of loading the kernel and -\ modules. Returns a flag +\ modules. Returns a flag. Unsure why we don't just have start +\ call this... : initialize ( -- flag ) s" /boot/defaults/loader.conf" initialize include_conf_files include_nextboot_file + \ If the user defined a post-initialize hook, call it now + s" post-initialize" sfind if execute else drop then any_conf_read? ; From c9a124dc9af605cb9c305197deb20ede82341a09 Mon Sep 17 00:00:00 2001 From: Nathan Whitehorn Date: Wed, 31 Aug 2016 04:02:52 +0000 Subject: [PATCH 44/86] Refix operation on sparse CPU mappings as in r302372, temporarily broken by r304716. PR: kern/210106 MFC after: 2 days --- sys/kern/imgact_elf.c | 3 +++ sys/kern/subr_gtaskqueue.c | 7 +++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/sys/kern/imgact_elf.c b/sys/kern/imgact_elf.c index c4aea9b1d702..771010f0e3f2 100644 --- a/sys/kern/imgact_elf.c +++ b/sys/kern/imgact_elf.c @@ -1105,6 +1105,9 @@ __elfN(freebsd_fixup)(register_t **stack_base, struct image_params *imgp) AUXARGS_ENTRY(pos, AT_TIMEKEEP, imgp->sysent->sv_timekeep_base); } +#ifdef AT_HWCAP + AUXARGS_ENTRY(pos, AT_HWCAP, cpu_features); +#endif AUXARGS_ENTRY(pos, AT_STACKPROT, imgp->sysent->sv_shared_page_obj != NULL && imgp->stack_prot != 0 ? imgp->stack_prot : imgp->sysent->sv_stackprot); diff --git a/sys/kern/subr_gtaskqueue.c b/sys/kern/subr_gtaskqueue.c index 2d655bde0b25..6b431f085375 100644 --- a/sys/kern/subr_gtaskqueue.c +++ b/sys/kern/subr_gtaskqueue.c @@ -742,7 +742,7 @@ _taskqgroup_adjust(struct taskqgroup *qgroup, int cnt, int stride) LIST_HEAD(, grouptask) gtask_head = LIST_HEAD_INITIALIZER(NULL); cpuset_t mask; struct grouptask *gtask; - int i, old_cnt, qid; + int i, k, old_cnt, qid, cpu; mtx_assert(&qgroup->tqg_lock, MA_OWNED); @@ -806,8 +806,11 @@ _taskqgroup_adjust(struct taskqgroup *qgroup, int cnt, int stride) /* * Set new CPU and IRQ affinity */ + cpu = CPU_FIRST(); for (i = 0; i < cnt; i++) { - qgroup->tqg_queue[i].tgc_cpu = i * qgroup->tqg_stride; + qgroup->tqg_queue[i].tgc_cpu = cpu; + for (k = 0; k < qgroup->tqg_stride; k++) + cpu = CPU_NEXT(cpu); CPU_ZERO(&mask); CPU_SET(qgroup->tqg_queue[i].tgc_cpu, &mask); LIST_FOREACH(gtask, &qgroup->tqg_queue[i].tgc_tasks, gt_list) { From 09c697016bb2d369e2b70d62ae3924866dfc0dfd Mon Sep 17 00:00:00 2001 From: Nathan Whitehorn Date: Wed, 31 Aug 2016 04:03:55 +0000 Subject: [PATCH 45/86] Back out misfired extra file in r305108. --- sys/kern/imgact_elf.c | 3 --- 1 file changed, 3 deletions(-) diff --git a/sys/kern/imgact_elf.c b/sys/kern/imgact_elf.c index 771010f0e3f2..c4aea9b1d702 100644 --- a/sys/kern/imgact_elf.c +++ b/sys/kern/imgact_elf.c @@ -1105,9 +1105,6 @@ __elfN(freebsd_fixup)(register_t **stack_base, struct image_params *imgp) AUXARGS_ENTRY(pos, AT_TIMEKEEP, imgp->sysent->sv_timekeep_base); } -#ifdef AT_HWCAP - AUXARGS_ENTRY(pos, AT_HWCAP, cpu_features); -#endif AUXARGS_ENTRY(pos, AT_STACKPROT, imgp->sysent->sv_shared_page_obj != NULL && imgp->stack_prot != 0 ? imgp->stack_prot : imgp->sysent->sv_stackprot); From cf38cf1b7a319bda912134248ca4ea009a14c73d Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Wed, 31 Aug 2016 05:27:30 +0000 Subject: [PATCH 46/86] hyperv/hn: Consolidate NVS transaction execution. MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7704 --- sys/dev/hyperv/netvsc/hv_net_vsc.c | 82 ++++++++++++------------- sys/dev/hyperv/netvsc/hv_rndis_filter.c | 16 +---- sys/dev/hyperv/netvsc/if_hnvar.h | 2 +- 3 files changed, 42 insertions(+), 58 deletions(-) diff --git a/sys/dev/hyperv/netvsc/hv_net_vsc.c b/sys/dev/hyperv/netvsc/hv_net_vsc.c index 27e52f55351b..66e45b687aef 100644 --- a/sys/dev/hyperv/netvsc/hv_net_vsc.c +++ b/sys/dev/hyperv/netvsc/hv_net_vsc.c @@ -107,21 +107,45 @@ hn_chim_alloc(struct hn_softc *sc) const void * hn_nvs_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, - void *req, int reqlen, size_t *resp_len) + void *req, int reqlen, size_t *resplen0, uint32_t type) { struct hn_send_ctx sndc; + size_t resplen, min_resplen = *resplen0; + const struct hn_nvs_hdr *hdr; int error; - hn_send_ctx_init_simple(&sndc, hn_nvs_sent_xact, xact); - vmbus_xact_activate(xact); + KASSERT(min_resplen >= sizeof(*hdr), + ("invalid minimum response len %zu", min_resplen)); + /* + * Execute the xact setup by the caller. + */ + hn_send_ctx_init_simple(&sndc, hn_nvs_sent_xact, xact); + + vmbus_xact_activate(xact); error = hn_nvs_send(sc->hn_prichan, VMBUS_CHANPKT_FLAG_RC, req, reqlen, &sndc); if (error) { vmbus_xact_deactivate(xact); - return NULL; + return (NULL); } - return (vmbus_xact_wait(xact, resp_len)); + hdr = vmbus_xact_wait(xact, &resplen); + + /* + * Check this NVS response message. + */ + if (resplen < min_resplen) { + if_printf(sc->hn_ifp, "invalid NVS resp len %zu\n", resplen); + return (NULL); + } + if (hdr->nvs_type != type) { + if_printf(sc->hn_ifp, "unexpected NVS resp 0x%08x, " + "expect 0x%08x\n", hdr->nvs_type, type); + return (NULL); + } + /* All pass! */ + *resplen0 = resplen; + return (hdr); } static __inline int @@ -181,24 +205,14 @@ hv_nv_init_rx_buffer_with_net_vsp(struct hn_softc *sc, int rxbuf_size) conn->nvs_gpadl = sc->hn_rxbuf_gpadl; conn->nvs_sig = HN_NVS_RXBUF_SIG; - resp = hn_nvs_xact_execute(sc, xact, conn, sizeof(*conn), &resp_len); + resp_len = sizeof(*resp); + resp = hn_nvs_xact_execute(sc, xact, conn, sizeof(*conn), &resp_len, + HN_NVS_TYPE_RXBUF_CONNRESP); if (resp == NULL) { if_printf(sc->hn_ifp, "exec rxbuf conn failed\n"); error = EIO; goto cleanup; } - if (resp_len < sizeof(*resp)) { - if_printf(sc->hn_ifp, "invalid rxbuf conn resp length %zu\n", - resp_len); - error = EINVAL; - goto cleanup; - } - if (resp->nvs_type != HN_NVS_TYPE_RXBUF_CONNRESP) { - if_printf(sc->hn_ifp, "not rxbuf conn resp, type %u\n", - resp->nvs_type); - error = EINVAL; - goto cleanup; - } status = resp->nvs_status; vmbus_xact_put(xact); @@ -264,24 +278,14 @@ hv_nv_init_send_buffer_with_net_vsp(struct hn_softc *sc) chim->nvs_gpadl = sc->hn_chim_gpadl; chim->nvs_sig = HN_NVS_CHIM_SIG; - resp = hn_nvs_xact_execute(sc, xact, chim, sizeof(*chim), &resp_len); + resp_len = sizeof(*resp); + resp = hn_nvs_xact_execute(sc, xact, chim, sizeof(*chim), &resp_len, + HN_NVS_TYPE_CHIM_CONNRESP); if (resp == NULL) { if_printf(sc->hn_ifp, "exec chim conn failed\n"); error = EIO; goto cleanup; } - if (resp_len < sizeof(*resp)) { - if_printf(sc->hn_ifp, "invalid chim conn resp length %zu\n", - resp_len); - error = EINVAL; - goto cleanup; - } - if (resp->nvs_type != HN_NVS_TYPE_CHIM_CONNRESP) { - if_printf(sc->hn_ifp, "not chim conn resp, type %u\n", - resp->nvs_type); - error = EINVAL; - goto cleanup; - } status = resp->nvs_status; sectsz = resp->nvs_sectsz; @@ -442,24 +446,14 @@ hv_nv_negotiate_nvsp_protocol(struct hn_softc *sc, uint32_t nvs_ver) init->nvs_ver_min = nvs_ver; init->nvs_ver_max = nvs_ver; - resp = hn_nvs_xact_execute(sc, xact, init, sizeof(*init), &resp_len); + resp_len = sizeof(*resp); + resp = hn_nvs_xact_execute(sc, xact, init, sizeof(*init), &resp_len, + HN_NVS_TYPE_INIT_RESP); if (resp == NULL) { if_printf(sc->hn_ifp, "exec init failed\n"); vmbus_xact_put(xact); return (EIO); } - if (resp_len < sizeof(*resp)) { - if_printf(sc->hn_ifp, "invalid init resp length %zu\n", - resp_len); - vmbus_xact_put(xact); - return (EINVAL); - } - if (resp->nvs_type != HN_NVS_TYPE_INIT_RESP) { - if_printf(sc->hn_ifp, "not init resp, type %u\n", - resp->nvs_type); - vmbus_xact_put(xact); - return (EINVAL); - } status = resp->nvs_status; vmbus_xact_put(xact); diff --git a/sys/dev/hyperv/netvsc/hv_rndis_filter.c b/sys/dev/hyperv/netvsc/hv_rndis_filter.c index 5c81740ba2c8..64d27bacc8af 100644 --- a/sys/dev/hyperv/netvsc/hv_rndis_filter.c +++ b/sys/dev/hyperv/netvsc/hv_rndis_filter.c @@ -970,24 +970,14 @@ hv_rf_on_device_add(struct hn_softc *sc, void *additl_info, req->nvs_op = HN_NVS_SUBCH_OP_ALLOC; req->nvs_nsubch = nchan - 1; - resp = hn_nvs_xact_execute(sc, xact, req, sizeof(*req), &resp_len); + resp_len = sizeof(*resp); + resp = hn_nvs_xact_execute(sc, xact, req, sizeof(*req), &resp_len, + HN_NVS_TYPE_SUBCH_RESP); if (resp == NULL) { if_printf(sc->hn_ifp, "exec subch failed\n"); ret = EIO; goto out; } - if (resp_len < sizeof(*resp)) { - if_printf(sc->hn_ifp, "invalid subch resp length %zu\n", - resp_len); - ret = EINVAL; - goto out; - } - if (resp->nvs_type != HN_NVS_TYPE_SUBCH_RESP) { - if_printf(sc->hn_ifp, "not subch resp, type %u\n", - resp->nvs_type); - ret = EINVAL; - goto out; - } status = resp->nvs_status; nsubch = resp->nvs_nsubch; diff --git a/sys/dev/hyperv/netvsc/if_hnvar.h b/sys/dev/hyperv/netvsc/if_hnvar.h index 90fc00b7e43e..f307856ec539 100644 --- a/sys/dev/hyperv/netvsc/if_hnvar.h +++ b/sys/dev/hyperv/netvsc/if_hnvar.h @@ -111,7 +111,7 @@ struct vmbus_xact; const void *hn_nvs_xact_execute(struct hn_softc *sc, struct vmbus_xact *xact, void *req, int reqlen, - size_t *resp_len); + size_t *resp_len, uint32_t type); void hn_nvs_sent_xact(struct hn_send_ctx *sndc, struct hn_softc *sc, struct vmbus_channel *chan, const void *data, int dlen); uint32_t hn_chim_alloc(struct hn_softc *sc); From 4bddf0c813f02b40169a406b308415d3bb8a86a9 Mon Sep 17 00:00:00 2001 From: Sepherosa Ziehau Date: Wed, 31 Aug 2016 06:00:20 +0000 Subject: [PATCH 47/86] hyperv/timesync: Rework time adjustment policy - By default, adjust time upon SYNC request. It can be disabled through hw.hvtimesync.ignore_sync_req. SYNC request will be sent by hypervisor the host is resumed, rebooted, etc. - By default, adjust time upon SAMPLE request, if there is 100ms difference between VM time and hypervisor time. This can be disabled through hw.hvtimesync.sample_drift. And nuke the unnecessary task, since channel callback is running in a Hyper-V taskqueue nowadays. Submitted by: YanZhe Chen Discussed with: Dexuan Cui , Hongjiang Zhang , sephe MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D7707 --- sys/dev/hyperv/utilities/hv_timesync.c | 119 +++++++++++++------------ 1 file changed, 64 insertions(+), 55 deletions(-) diff --git a/sys/dev/hyperv/utilities/hv_timesync.c b/sys/dev/hyperv/utilities/hv_timesync.c index 632a45e65960..93dee2562167 100644 --- a/sys/dev/hyperv/utilities/hv_timesync.c +++ b/sys/dev/hyperv/utilities/hv_timesync.c @@ -39,7 +39,7 @@ #include #include #include -#include +#include #include #include @@ -52,11 +52,7 @@ #define HV_ICTIMESYNCFLAG_SYNC 1 #define HV_ICTIMESYNCFLAG_SAMPLE 2 #define HV_NANO_SEC_PER_SEC 1000000000 - -/* Time Sync data */ -typedef struct { - uint64_t data; -} time_sync_data; +#define HV_NANO_SEC_PER_MILLI_SEC 1000000 static const struct vmbus_ic_desc vmbus_timesync_descs[] = { { @@ -75,41 +71,26 @@ struct hv_ictimesync_data { uint8_t flags; } __packed; -typedef struct hv_timesync_sc { - hv_util_sc util_sc; - struct task task; - time_sync_data time_msg; -} hv_timesync_sc; - -/** - * Set host time based on time sync message from host +/* + * Globals */ -static void -hv_set_host_time(void *context, int pending) -{ - hv_timesync_sc *softc = (hv_timesync_sc*)context; - uint64_t hosttime = softc->time_msg.data; - struct timespec guest_ts, host_ts; - uint64_t host_tns; - int64_t diff; - int error; +SYSCTL_NODE(_hw, OID_AUTO, hvtimesync, CTLFLAG_RW | CTLFLAG_MPSAFE, NULL, + "Hyper-V timesync interface"); - host_tns = (hosttime - HV_WLTIMEDELTA) * 100; - host_ts.tv_sec = (time_t)(host_tns/HV_NANO_SEC_PER_SEC); - host_ts.tv_nsec = (long)(host_tns%HV_NANO_SEC_PER_SEC); +/* Ignore the sync request when set to 1. */ +static int ignore_sync_req = 0; +SYSCTL_INT(_hw_hvtimesync, OID_AUTO, ignore_sync_req, CTLFLAG_RWTUN, + &ignore_sync_req, 0, + "Ignore the sync request when set to 1."); - nanotime(&guest_ts); - - diff = (int64_t)host_ts.tv_sec - (int64_t)guest_ts.tv_sec; - - /* - * If host differs by 5 seconds then make the guest catch up - */ - if (diff > 5 || diff < -5) { - error = kern_clock_settime(curthread, CLOCK_REALTIME, - &host_ts); - } -} +/* + * Trigger sample sync when drift exceeds threshold (ms). + * Ignore the sample request when set to 0. + */ +static int sample_drift = 100; +SYSCTL_INT(_hw_hvtimesync, OID_AUTO, sample_drift, CTLFLAG_RWTUN, + &sample_drift, 0, + "Threshold that makes sample request trigger the sync."); /** * @brief Synchronize time with host after reboot, restore, etc. @@ -123,13 +104,47 @@ hv_set_host_time(void *context, int pending) * use the first 50 time samples for initial system time setting. */ static inline -void hv_adj_guesttime(hv_timesync_sc *sc, uint64_t hosttime, uint8_t flags) +void hv_adj_guesttime(hv_util_sc *sc, uint64_t hosttime, uint8_t flags) { - sc->time_msg.data = hosttime; + struct timespec guest_ts, host_ts; + uint64_t host_tns, guest_tns; + int64_t diff; + int error; - if (((flags & HV_ICTIMESYNCFLAG_SYNC) != 0) || - ((flags & HV_ICTIMESYNCFLAG_SAMPLE) != 0)) { - taskqueue_enqueue(taskqueue_thread, &sc->task); + host_tns = (hosttime - HV_WLTIMEDELTA) * 100; + host_ts.tv_sec = (time_t)(host_tns/HV_NANO_SEC_PER_SEC); + host_ts.tv_nsec = (long)(host_tns%HV_NANO_SEC_PER_SEC); + + nanotime(&guest_ts); + guest_tns = guest_ts.tv_sec * HV_NANO_SEC_PER_SEC + guest_ts.tv_nsec; + + if ((flags & HV_ICTIMESYNCFLAG_SYNC) != 0 && ignore_sync_req == 0) { + if (bootverbose) { + device_printf(sc->ic_dev, "handle sync request " + "{host: %ju, guest: %ju}\n", + (uintmax_t)host_tns, (uintmax_t)guest_tns); + } + + error = kern_clock_settime(curthread, CLOCK_REALTIME, + &host_ts); + return; + } + + if ((flags & HV_ICTIMESYNCFLAG_SAMPLE) != 0 && sample_drift != 0) { + if (bootverbose) { + device_printf(sc->ic_dev, "handle sample request " + "{host: %ju, guest: %ju}\n", + (uintmax_t)host_tns, (uintmax_t)guest_tns); + } + + diff = (int64_t)(host_tns - guest_tns) / HV_NANO_SEC_PER_MILLI_SEC; + if (diff > sample_drift || diff < -sample_drift) { + error = kern_clock_settime(curthread, CLOCK_REALTIME, + &host_ts); + if (bootverbose) + device_printf(sc->ic_dev, "trigger sample sync"); + } + return; } } @@ -145,12 +160,12 @@ hv_timesync_cb(struct vmbus_channel *channel, void *context) int ret; uint8_t* time_buf; struct hv_ictimesync_data* timedatap; - hv_timesync_sc *softc; + hv_util_sc *softc; - softc = (hv_timesync_sc*)context; - time_buf = softc->util_sc.receive_buffer; + softc = (hv_util_sc*)context; + time_buf = softc->receive_buffer; - recvlen = softc->util_sc.ic_buflen; + recvlen = softc->ic_buflen; ret = vmbus_chan_recv(channel, time_buf, &recvlen, &requestId); KASSERT(ret != ENOBUFS, ("hvtimesync recvbuf is not large enough")); /* XXX check recvlen to make sure that it contains enough data */ @@ -162,7 +177,7 @@ hv_timesync_cb(struct vmbus_channel *channel, void *context) if (icmsghdrp->icmsgtype == HV_ICMSGTYPE_NEGOTIATE) { int error; - error = vmbus_ic_negomsg(&softc->util_sc, time_buf, &recvlen); + error = vmbus_ic_negomsg(softc, time_buf, &recvlen); if (error) return; } else { @@ -190,18 +205,12 @@ hv_timesync_probe(device_t dev) static int hv_timesync_attach(device_t dev) { - hv_timesync_sc *softc = device_get_softc(dev); - - TASK_INIT(&softc->task, 1, hv_set_host_time, softc); return hv_util_attach(dev, hv_timesync_cb); } static int hv_timesync_detach(device_t dev) { - hv_timesync_sc *softc = device_get_softc(dev); - - taskqueue_drain(taskqueue_thread, &softc->task); return hv_util_detach(dev); } @@ -213,7 +222,7 @@ static device_method_t timesync_methods[] = { { 0, 0 } }; -static driver_t timesync_driver = { "hvtimesync", timesync_methods, sizeof(hv_timesync_sc)}; +static driver_t timesync_driver = { "hvtimesync", timesync_methods, sizeof(hv_util_sc)}; static devclass_t timesync_devclass; From a089112fdf4030b3af2ba961eb20da971ed5f7ee Mon Sep 17 00:00:00 2001 From: Luiz Otavio O Souza Date: Wed, 31 Aug 2016 06:46:47 +0000 Subject: [PATCH 48/86] Replace a magic number with the proper register name. Sponsored by: Rubicon Communications, LLC (Netgate) --- sys/arm/ti/am335x/am335x_prcm.c | 7 +++---- sys/arm/ti/am335x/am335x_scm.h | 1 + 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/sys/arm/ti/am335x/am335x_prcm.c b/sys/arm/ti/am335x/am335x_prcm.c index f72bb543c4ff..6da5dc85b665 100644 --- a/sys/arm/ti/am335x/am335x_prcm.c +++ b/sys/arm/ti/am335x/am335x_prcm.c @@ -619,10 +619,9 @@ am335x_clk_get_sysclk_freq(struct ti_clock_dev *clkdev, unsigned int *freq) { uint32_t ctrl_status; - /* Read the input clock freq from the control module */ - /* control_status reg (0x40) */ - if (ti_scm_reg_read_4(0x40, &ctrl_status)) - return ENXIO; + /* Read the input clock freq from the control module. */ + if (ti_scm_reg_read_4(SCM_CTRL_STATUS, &ctrl_status)) + return (ENXIO); switch ((ctrl_status>>22) & 0x3) { case 0x0: diff --git a/sys/arm/ti/am335x/am335x_scm.h b/sys/arm/ti/am335x/am335x_scm.h index bfb4cd251454..9ea82044c4fe 100644 --- a/sys/arm/ti/am335x/am335x_scm.h +++ b/sys/arm/ti/am335x/am335x_scm.h @@ -29,6 +29,7 @@ #define __AM335X_SCM_H__ /* AM335x-specific registers for control module (scm) */ +#define SCM_CTRL_STATUS 0x40 #define SCM_USB_CTRL0 0x620 #define SCM_USB_STS0 0x624 #define SCM_USB_CTRL1 0x628 From 0ba9f0ab1b66c0f505e25ed5c672895959723343 Mon Sep 17 00:00:00 2001 From: Luiz Otavio O Souza Date: Wed, 31 Aug 2016 07:03:06 +0000 Subject: [PATCH 49/86] Replace more magic numbers with the proper register names. Sponsored by: Rubicon Communications, LLC (Netgate) --- sys/arm/ti/am335x/am335x_scm.h | 2 ++ sys/arm/ti/cpsw/if_cpsw.c | 4 ++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/sys/arm/ti/am335x/am335x_scm.h b/sys/arm/ti/am335x/am335x_scm.h index 9ea82044c4fe..4a01f827dd57 100644 --- a/sys/arm/ti/am335x/am335x_scm.h +++ b/sys/arm/ti/am335x/am335x_scm.h @@ -34,6 +34,8 @@ #define SCM_USB_STS0 0x624 #define SCM_USB_CTRL1 0x628 #define SCM_USB_STS1 0x62C +#define SCM_MAC_ID0_LO 0x630 +#define SCM_MAC_ID0_HI 0x634 #define SCM_PWMSS_CTRL 0x664 #endif /* __AM335X_SCM_H__ */ diff --git a/sys/arm/ti/cpsw/if_cpsw.c b/sys/arm/ti/cpsw/if_cpsw.c index 70204c03c225..a6eada48d209 100644 --- a/sys/arm/ti/cpsw/if_cpsw.c +++ b/sys/arm/ti/cpsw/if_cpsw.c @@ -1019,14 +1019,14 @@ cpswp_attach(device_t dev) IFQ_SET_READY(&ifp->if_snd); /* Get high part of MAC address from control module (mac_id[0|1]_hi) */ - ti_scm_reg_read_4(0x634 + sc->unit * 8, ®); + ti_scm_reg_read_4(SCM_MAC_ID0_HI + sc->unit * 8, ®); mac_addr[0] = reg & 0xFF; mac_addr[1] = (reg >> 8) & 0xFF; mac_addr[2] = (reg >> 16) & 0xFF; mac_addr[3] = (reg >> 24) & 0xFF; /* Get low part of MAC address from control module (mac_id[0|1]_lo) */ - ti_scm_reg_read_4(0x630 + sc->unit * 8, ®); + ti_scm_reg_read_4(SCM_MAC_ID0_LO + sc->unit * 8, ®); mac_addr[4] = reg & 0xFF; mac_addr[5] = (reg >> 8) & 0xFF; From 73e69441643efc9c05f2b2293f5a22576690f40f Mon Sep 17 00:00:00 2001 From: Luiz Otavio O Souza Date: Wed, 31 Aug 2016 07:22:14 +0000 Subject: [PATCH 50/86] Allow the use of control module extensions to cope with specific platform features. Sponsored by: Rubicon Communications, LLC (Netgate) --- sys/arm/ti/ti_scm.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/sys/arm/ti/ti_scm.c b/sys/arm/ti/ti_scm.c index 56082654d427..5a6b097c99c0 100644 --- a/sys/arm/ti/ti_scm.c +++ b/sys/arm/ti/ti_scm.c @@ -131,7 +131,11 @@ ti_scm_attach(device_t dev) ti_scm_sc = sc; - return (0); + /* Attach platform extensions, if any. */ + bus_generic_probe(dev); + bus_enumerate_hinted_children(dev); + + return (bus_generic_attach(dev)); } int From bf77189f92d8fa049088af38e472d0c00f51e8a5 Mon Sep 17 00:00:00 2001 From: Luiz Otavio O Souza Date: Wed, 31 Aug 2016 07:42:46 +0000 Subject: [PATCH 51/86] Add a driver for the AM335x bandgap sensor, an on-die temperature sensor as part of the AM335x control module extension. TI says that the bandgap sensor is not very accurate on AM335x, but in our tests it seems to be a good reference for the SoC temperature. TI details: http://processors.wiki.ti.com/index.php/AM335x_Thermal_Considerations#Measuring_Case_Temperature Sponsored by: Rubicon Communications, LLC (Netgate) --- sys/arm/ti/am335x/am335x_scm.c | 169 +++++++++++++++++++++++++++++++++ sys/arm/ti/am335x/am335x_scm.h | 8 ++ sys/arm/ti/am335x/files.am335x | 1 + 3 files changed, 178 insertions(+) create mode 100644 sys/arm/ti/am335x/am335x_scm.c diff --git a/sys/arm/ti/am335x/am335x_scm.c b/sys/arm/ti/am335x/am335x_scm.c new file mode 100644 index 000000000000..3d0dff4d6b14 --- /dev/null +++ b/sys/arm/ti/am335x/am335x_scm.c @@ -0,0 +1,169 @@ +/*- + * Copyright (c) 2016 Rubicon Communications, LLC (Netgate) + * 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. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 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. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include +#include + +#include + +#include +#include +#include + +#define TZ_ZEROC 2731 + +struct am335x_scm_softc { + int sc_last_temp; + struct sysctl_oid *sc_temp_oid; +}; + +static int +am335x_scm_temp_sysctl(SYSCTL_HANDLER_ARGS) +{ + device_t dev; + int i, temp; + struct am335x_scm_softc *sc; + uint32_t reg; + + dev = (device_t)arg1; + sc = device_get_softc(dev); + + /* Read the temperature and convert to Kelvin. */ + for(i = 50; i > 0; i--) { + ti_scm_reg_read_4(SCM_BGAP_CTRL, ®); + if ((reg & SCM_BGAP_EOCZ) == 0) + break; + DELAY(50); + } + if ((reg & SCM_BGAP_EOCZ) == 0) { + sc->sc_last_temp = + (reg >> SCM_BGAP_TEMP_SHIFT) & SCM_BGAP_TEMP_MASK; + sc->sc_last_temp *= 10; + } + temp = sc->sc_last_temp + TZ_ZEROC; + + return (sysctl_handle_int(oidp, &temp, 0, req)); +} + +static void +am335x_scm_identify(driver_t *driver, device_t parent) +{ + device_t child; + + /* AM335x only. */ + if (ti_chip() != CHIP_AM335X) + return; + + /* Make sure we attach only once. */ + if (device_find_child(parent, "am335x_scm", -1) != NULL) + return; + + child = device_add_child(parent, "am335x_scm", -1); + if (child == NULL) + device_printf(parent, "cannot add ti_scm child\n"); +} + +static int +am335x_scm_probe(device_t dev) +{ + + device_set_desc(dev, "AM335x Control Module Extension"); + + return (BUS_PROBE_DEFAULT); +} + +static int +am335x_scm_attach(device_t dev) +{ + struct am335x_scm_softc *sc; + struct sysctl_ctx_list *ctx; + struct sysctl_oid_list *tree; + uint32_t reg; + + /* Set ADC to continous mode, clear output reset. */ + reg = SCM_BGAP_CLRZ | SCM_BGAP_CONTCONV; + ti_scm_reg_write_4(SCM_BGAP_CTRL, reg); + /* Flush write. */ + ti_scm_reg_read_4(SCM_BGAP_CTRL, ®); + /* Start the ADC conversion. */ + reg = SCM_BGAP_CLRZ | SCM_BGAP_CONTCONV | SCM_BGAP_SOC; + ti_scm_reg_write_4(SCM_BGAP_CTRL, reg); + + /* Temperature sysctl. */ + sc = device_get_softc(dev); + ctx = device_get_sysctl_ctx(dev); + tree = SYSCTL_CHILDREN(device_get_sysctl_tree(dev)); + sc->sc_temp_oid = SYSCTL_ADD_PROC(ctx, tree, OID_AUTO, + "temperature", CTLTYPE_INT | CTLFLAG_RD | CTLFLAG_MPSAFE, + dev, 0, am335x_scm_temp_sysctl, "IK", "Current temperature"); + + return (0); +} + +static int +am335x_scm_detach(device_t dev) +{ + struct am335x_scm_softc *sc; + + sc = device_get_softc(dev); + + /* Remove temperature sysctl. */ + if (sc->sc_temp_oid != NULL) + sysctl_remove_oid(sc->sc_temp_oid, 1, 0); + + /* Stop the bandgap ADC. */ + ti_scm_reg_write_4(SCM_BGAP_CTRL, SCM_BGAP_BGOFF); + + return (0); +} + +static device_method_t am335x_scm_methods[] = { + DEVMETHOD(device_identify, am335x_scm_identify), + DEVMETHOD(device_probe, am335x_scm_probe), + DEVMETHOD(device_attach, am335x_scm_attach), + DEVMETHOD(device_detach, am335x_scm_detach), + + DEVMETHOD_END +}; + +static driver_t am335x_scm_driver = { + "am335x_scm", + am335x_scm_methods, + sizeof(struct am335x_scm_softc), +}; + +static devclass_t am335x_scm_devclass; + +DRIVER_MODULE(am335x_scm, ti_scm, am335x_scm_driver, am335x_scm_devclass, 0, 0); +MODULE_VERSION(am335x_scm, 1); +MODULE_DEPEND(am335x_scm, ti_scm, 1, 1, 1); diff --git a/sys/arm/ti/am335x/am335x_scm.h b/sys/arm/ti/am335x/am335x_scm.h index 4a01f827dd57..6116be063adf 100644 --- a/sys/arm/ti/am335x/am335x_scm.h +++ b/sys/arm/ti/am335x/am335x_scm.h @@ -30,6 +30,14 @@ /* AM335x-specific registers for control module (scm) */ #define SCM_CTRL_STATUS 0x40 +#define SCM_BGAP_CTRL 0x448 +#define SCM_BGAP_TEMP_MASK 0xff +#define SCM_BGAP_TEMP_SHIFT 8 +#define SCM_BGAP_BGOFF (1 << 6) +#define SCM_BGAP_SOC (1 << 4) +#define SCM_BGAP_CLRZ (1 << 3) +#define SCM_BGAP_CONTCONV (1 << 2) +#define SCM_BGAP_EOCZ (1 << 1) #define SCM_USB_CTRL0 0x620 #define SCM_USB_STS0 0x624 #define SCM_USB_CTRL1 0x628 diff --git a/sys/arm/ti/am335x/files.am335x b/sys/arm/ti/am335x/files.am335x index cc876593fbf7..a7282117b7d8 100644 --- a/sys/arm/ti/am335x/files.am335x +++ b/sys/arm/ti/am335x/files.am335x @@ -13,6 +13,7 @@ arm/ti/am335x/am335x_pwmss.c standard arm/ti/am335x/am335x_ehrpwm.c standard arm/ti/am335x/am335x_ecap.c standard arm/ti/am335x/am335x_rtc.c optional am335x_rtc +arm/ti/am335x/am335x_scm.c standard arm/ti/am335x/am335x_scm_padconf.c standard arm/ti/am335x/am335x_usbss.c optional musb fdt arm/ti/am335x/am335x_musb.c optional musb fdt From 9edcae95e4896f1dad4ce7661a199eff413f7a00 Mon Sep 17 00:00:00 2001 From: Toomas Soome Date: Wed, 31 Aug 2016 09:23:09 +0000 Subject: [PATCH 52/86] recvtftp() is broken for large files, report file size The tftp download for large files will cause internal block id to wrap to 0 as the data type is unsigned short. Also provide file size information for stat. PR: 200500 Reported by: tsoome Reviewed by: allanjude Approved by: allanjude (mentor) Differential Revision: https://reviews.freebsd.org/D7660 --- lib/libstand/tftp.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/lib/libstand/tftp.c b/lib/libstand/tftp.c index 001cbfd6d1f0..cb84970910f9 100644 --- a/lib/libstand/tftp.c +++ b/lib/libstand/tftp.c @@ -200,7 +200,7 @@ recvtftp(struct tftp_handle *h, void *pkt, ssize_t len, time_t tleft, case DATA: { int got; - if (htons(t->th_block) != d->xid) { + if (htons(t->th_block) != (u_short) d->xid) { /* * Expected block? */ @@ -560,7 +560,7 @@ tftp_stat(struct open_file *f, struct stat *sb) sb->st_nlink = 1; sb->st_uid = 0; sb->st_gid = 0; - sb->st_size = -1; + sb->st_size = (off_t) tftpfile->tftp_tsize; return (0); } @@ -731,6 +731,8 @@ tftp_parse_oack(struct tftp_handle *h, char *buf, size_t len) } else if (strcasecmp(tftp_options[i], "tsize") == 0) { if (i + 1 < option_idx) tsize = strtol(tftp_options[i + 1], (char **)NULL, 10); + if (tsize != 0) + h->tftp_tsize = tsize; } else { /* Do not allow any options we did not expect to be ACKed. */ printf("unexpected tftp option '%s'\n", tftp_options[i]); From 4c0e176d9c449cc2ce4b652fc8e3ef9430a9f902 Mon Sep 17 00:00:00 2001 From: "Bjoern A. Zeeb" Date: Wed, 31 Aug 2016 10:45:33 +0000 Subject: [PATCH 53/86] After r305113, try to properly replace the magic numbers with proper #defines for this driver (not using the wrong header). --- sys/arm/ti/am335x/am335x_scm.h | 2 -- sys/arm/ti/cpsw/if_cpsw.c | 4 ++-- sys/arm/ti/cpsw/if_cpswreg.h | 3 +++ 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/sys/arm/ti/am335x/am335x_scm.h b/sys/arm/ti/am335x/am335x_scm.h index 6116be063adf..642620881f70 100644 --- a/sys/arm/ti/am335x/am335x_scm.h +++ b/sys/arm/ti/am335x/am335x_scm.h @@ -42,8 +42,6 @@ #define SCM_USB_STS0 0x624 #define SCM_USB_CTRL1 0x628 #define SCM_USB_STS1 0x62C -#define SCM_MAC_ID0_LO 0x630 -#define SCM_MAC_ID0_HI 0x634 #define SCM_PWMSS_CTRL 0x664 #endif /* __AM335X_SCM_H__ */ diff --git a/sys/arm/ti/cpsw/if_cpsw.c b/sys/arm/ti/cpsw/if_cpsw.c index a6eada48d209..038d2d2089c1 100644 --- a/sys/arm/ti/cpsw/if_cpsw.c +++ b/sys/arm/ti/cpsw/if_cpsw.c @@ -1019,14 +1019,14 @@ cpswp_attach(device_t dev) IFQ_SET_READY(&ifp->if_snd); /* Get high part of MAC address from control module (mac_id[0|1]_hi) */ - ti_scm_reg_read_4(SCM_MAC_ID0_HI + sc->unit * 8, ®); + ti_scm_reg_read_4(CPSW_MAC_ID0_HI + sc->unit * 8, ®); mac_addr[0] = reg & 0xFF; mac_addr[1] = (reg >> 8) & 0xFF; mac_addr[2] = (reg >> 16) & 0xFF; mac_addr[3] = (reg >> 24) & 0xFF; /* Get low part of MAC address from control module (mac_id[0|1]_lo) */ - ti_scm_reg_read_4(SCM_MAC_ID0_LO + sc->unit * 8, ®); + ti_scm_reg_read_4(CPSW_MAC_ID0_LO + sc->unit * 8, ®); mac_addr[4] = reg & 0xFF; mac_addr[5] = (reg >> 8) & 0xFF; diff --git a/sys/arm/ti/cpsw/if_cpswreg.h b/sys/arm/ti/cpsw/if_cpswreg.h index bea6f1904e3c..c6f3e89c4254 100644 --- a/sys/arm/ti/cpsw/if_cpswreg.h +++ b/sys/arm/ti/cpsw/if_cpswreg.h @@ -46,6 +46,9 @@ #define CPSW_PORT_P_SA_LO(p) (CPSW_PORT_OFFSET + 0x120 + ((p-1) * 0x100)) #define CPSW_PORT_P_SA_HI(p) (CPSW_PORT_OFFSET + 0x124 + ((p-1) * 0x100)) +#define CPSW_MAC_ID0_LO 0x0630 +#define CPSW_MAC_ID0_HI 0x0634 + #define CPSW_CPDMA_OFFSET 0x0800 #define CPSW_CPDMA_TX_CONTROL (CPSW_CPDMA_OFFSET + 0x04) #define CPSW_CPDMA_TX_TEARDOWN (CPSW_CPDMA_OFFSET + 0x08) From 63dc81d861300d66d9a004954202e39e92a136f0 Mon Sep 17 00:00:00 2001 From: Jared McNeill Date: Wed, 31 Aug 2016 10:45:53 +0000 Subject: [PATCH 54/86] Add support for Allwinner A64 USB PHY. Reviewed by: manu --- sys/arm/allwinner/aw_usbphy.c | 86 ++++++++++++++++++++++++++++++++--- 1 file changed, 80 insertions(+), 6 deletions(-) diff --git a/sys/arm/allwinner/aw_usbphy.c b/sys/arm/allwinner/aw_usbphy.c index 221b2cc8f335..0c99728d4c81 100644 --- a/sys/arm/allwinner/aw_usbphy.c +++ b/sys/arm/allwinner/aw_usbphy.c @@ -40,6 +40,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #include #include @@ -53,25 +54,89 @@ __FBSDID("$FreeBSD$"); #include "phy_if.h" #define USBPHY_NPHYS 4 +#define USBPHY_NRES USBPHY_NPHYS + +enum awusbphy_type { + AWUSBPHY_TYPE_A10 = 1, + AWUSBPHY_TYPE_A13, + AWUSBPHY_TYPE_A20, + AWUSBPHY_TYPE_A31, + AWUSBPHY_TYPE_A83T, + AWUSBPHY_TYPE_H3, + AWUSBPHY_TYPE_A64 +}; static struct ofw_compat_data compat_data[] = { - { "allwinner,sun4i-a10-usb-phy", 1 }, - { "allwinner,sun5i-a13-usb-phy", 1 }, - { "allwinner,sun6i-a31-usb-phy", 1 }, - { "allwinner,sun7i-a20-usb-phy", 1 }, - { "allwinner,sun8i-a83t-usb-phy", 1 }, - { "allwinner,sun8i-h3-usb-phy", 1 }, + { "allwinner,sun4i-a10-usb-phy", AWUSBPHY_TYPE_A10 }, + { "allwinner,sun5i-a13-usb-phy", AWUSBPHY_TYPE_A13 }, + { "allwinner,sun6i-a31-usb-phy", AWUSBPHY_TYPE_A31 }, + { "allwinner,sun7i-a20-usb-phy", AWUSBPHY_TYPE_A20 }, + { "allwinner,sun8i-a83t-usb-phy", AWUSBPHY_TYPE_A83T }, + { "allwinner,sun8i-h3-usb-phy", AWUSBPHY_TYPE_H3 }, + { "allwinner,sun50i-a64-usb-phy", AWUSBPHY_TYPE_A64 }, { NULL, 0 } }; struct awusbphy_softc { + struct resource * res[USBPHY_NRES]; regulator_t reg[USBPHY_NPHYS]; gpio_pin_t id_det_pin; int id_det_valid; gpio_pin_t vbus_det_pin; int vbus_det_valid; + enum awusbphy_type phy_type; }; +static struct resource_spec awusbphy_spec[] = { + { SYS_RES_MEMORY, 0, RF_ACTIVE }, + { SYS_RES_MEMORY, 1, RF_ACTIVE }, + { SYS_RES_MEMORY, 2, RF_ACTIVE | RF_OPTIONAL }, + { SYS_RES_MEMORY, 3, RF_ACTIVE | RF_OPTIONAL }, + { -1, 0 } +}; + +#define RD4(sc, i, o) bus_read_4((sc)->res[(i)], (o)) +#define WR4(sc, i, o, v) bus_write_4((sc)->res[(i)], (o), (v)) +#define CLR4(sc, i, o, m) WR4(sc, i, o, RD4(sc, i, o) & ~(m)) +#define SET4(sc, i, o, m) WR4(sc, i, o, RD4(sc, i, o) | (m)) + +#define OTG_PHY_CFG 0x20 +#define OTG_PHY_ROUTE_OTG (1 << 0) +#define PMU_IRQ_ENABLE 0x00 +#define PMU_AHB_INCR8 (1 << 10) +#define PMU_AHB_INCR4 (1 << 9) +#define PMU_AHB_INCRX_ALIGN (1 << 8) +#define PMU_ULPI_BYPASS (1 << 0) +#define PMU_UNK_H3 0x10 +#define PMU_UNK_H3_CLR 0x2 + +static void +awusbphy_configure(device_t dev, int phyno) +{ + struct awusbphy_softc *sc; + + sc = device_get_softc(dev); + + if (sc->res[phyno] == NULL) + return; + + if (sc->phy_type == AWUSBPHY_TYPE_A64) { + CLR4(sc, phyno, PMU_UNK_H3, PMU_UNK_H3_CLR); + + /* EHCI0 and OTG share a PHY */ + if (phyno == 0) + SET4(sc, 0, OTG_PHY_CFG, OTG_PHY_ROUTE_OTG); + else if (phyno == 1) + CLR4(sc, 0, OTG_PHY_CFG, OTG_PHY_ROUTE_OTG); + } + + if (phyno > 0) { + /* Enable passby */ + SET4(sc, phyno, PMU_IRQ_ENABLE, PMU_ULPI_BYPASS | + PMU_AHB_INCR8 | PMU_AHB_INCR4 | PMU_AHB_INCRX_ALIGN); + } +} + static int awusbphy_init(device_t dev) { @@ -86,6 +151,8 @@ awusbphy_init(device_t dev) sc = device_get_softc(dev); node = ofw_bus_get_node(dev); + sc->phy_type = ofw_bus_search_compatible(dev, compat_data)->ocd_data; + /* Enable clocks */ for (off = 0; clk_get_by_ofw_index(dev, 0, off, &clk) == 0; off++) { error = clk_enable(clk); @@ -123,6 +190,10 @@ awusbphy_init(device_t dev) if (error == 0) sc->vbus_det_valid = 1; + /* Allocate resources */ + if (bus_alloc_resources(dev, awusbphy_spec, sc->res) != 0) + device_printf(dev, "couldn't allocate resources\n"); + return (0); } @@ -159,6 +230,9 @@ awusbphy_phy_enable(device_t dev, intptr_t phy, bool enable) sc = device_get_softc(dev); + /* Configure PHY */ + awusbphy_configure(dev, phy); + /* Regulators are optional. If not found, return success. */ reg = sc->reg[phy]; if (reg == NULL) From a95582c6fdf5c116d8a113272474dd7604e68cad Mon Sep 17 00:00:00 2001 From: Bruce Evans Date: Wed, 31 Aug 2016 11:10:39 +0000 Subject: [PATCH 55/86] Add some locking to sc_cngetc(). Keyboard input needs Giant locking, and that is not possible to do correctly here. Use mtx_trylock() and proceed unlocked as before if we can't acquire Giant (non-recursively), except in kdb mode don't even try to acquire Giant. Everything here is a hack, but it often works. Even if mtx_trylock() succeeds, this might be a LOR. Keyboard input also needs screen locking, to handle screen updates and switches. Add this, using the same simplistic screen locking as for sc_cnputc(). Giant must be acquired before the screen lock, and the screen lock must be dropped when calling the keyboard driver (else it would get a harmless LOR if it tries to acquire Giant). It was intended that sc cn open/close hide the locking calls, and they do for i/o functions functions except for this complication. Non-console keyboard input is still only Giant-locked, with screen locking in some called functions. This is correct for the keyboard parts only. When Giant cannot be acquired properly, atkbd and kbdmux tend to race and work (they assume that the caller acquired Giant properly and don't try to acquire it again or check that it has been acquired, and the races rarely matter), while ukbd tends to deadlock or panic (since it does the opposite, and has other usb threads to deadlock with). The keyboard (Giant) locking here does very little, but the screen locking completes screen locking for console mode except for not detecting or handling deadlock. --- sys/dev/syscons/syscons.c | 44 +++++++++++++++++++++++++++++++++++---- sys/dev/syscons/syscons.h | 1 + 2 files changed, 41 insertions(+), 4 deletions(-) diff --git a/sys/dev/syscons/syscons.c b/sys/dev/syscons/syscons.c index e4906cf4ac3b..7333b3c7c1ce 100644 --- a/sys/dev/syscons/syscons.c +++ b/sys/dev/syscons/syscons.c @@ -1649,10 +1649,32 @@ sc_cnterm(struct consdev *cp) static void sccnclose(sc_softc_t *sc, struct sc_cnstate *sp); static int sc_cngetc_locked(struct sc_cnstate *sp); +static void sccnkbdlock(sc_softc_t *sc, struct sc_cnstate *sp); +static void sccnkbdunlock(sc_softc_t *sc, struct sc_cnstate *sp); static void sccnopen(sc_softc_t *sc, struct sc_cnstate *sp, int flags); static void sccnscrlock(sc_softc_t *sc, struct sc_cnstate *sp); static void sccnscrunlock(sc_softc_t *sc, struct sc_cnstate *sp); +static void +sccnkbdlock(sc_softc_t *sc, struct sc_cnstate *sp) +{ + /* + * Locking method: hope for the best. + * The keyboard is supposed to be Giant locked. We can't handle that + * in general. The kdb_active case here is not safe, and we will + * proceed without the lock in all cases. + */ + sp->kbd_locked = !kdb_active && mtx_trylock(&Giant); +} + +static void +sccnkbdunlock(sc_softc_t *sc, struct sc_cnstate *sp) +{ + if (sp->kbd_locked) + mtx_unlock(&Giant); + sp->kbd_locked = FALSE; +} + static void sccnscrlock(sc_softc_t *sc, struct sc_cnstate *sp) { @@ -1674,11 +1696,14 @@ sccnopen(sc_softc_t *sc, struct sc_cnstate *sp, int flags) sp->kbd_opened = FALSE; sp->scr_opened = FALSE; + sp->kbd_locked = FALSE; /* Opening the keyboard is optional. */ if (!(flags & 1) || sc->kbd == NULL) goto over_keyboard; + sccnkbdlock(sc, sp); + /* * Make sure the keyboard is accessible even when the kbd device * driver is disabled. @@ -1726,6 +1751,7 @@ sccnclose(sc_softc_t *sc, struct sc_cnstate *sp) kbdd_disable(sc->kbd); sp->kbd_opened = FALSE; + sccnkbdunlock(sc, sp); } /* @@ -1751,6 +1777,7 @@ sc_cngrab(struct consdev *cp) if (lev >= 0 && lev < 2) { sccnopen(sc, &sc->grab_state[lev], 1 | 2); sccnscrunlock(sc, &sc->grab_state[lev]); + sccnkbdunlock(sc, &sc->grab_state[lev]); } } @@ -1763,6 +1790,7 @@ sc_cnungrab(struct consdev *cp) sc = sc_console->sc; lev = atomic_load_acq_int(&sc->grab_level) - 1; if (lev >= 0 && lev < 2) { + sccnkbdlock(sc, &sc->grab_state[lev]); sccnscrlock(sc, &sc->grab_state[lev]); sccnclose(sc, &sc->grab_state[lev]); } @@ -1825,16 +1853,20 @@ sc_cnputc(struct consdev *cd, int c) static int sc_cngetc(struct consdev *cd) { + struct sc_cnstate st; int c, s; /* assert(sc_console != NULL) */ + sccnopen(sc_console->sc, &st, 1); s = spltty(); /* block sckbdevent and scrn_timer while we poll */ - if (sc_console->sc->kbd == NULL) { + if (!st.kbd_opened) { splx(s); - return -1; + sccnclose(sc_console->sc, &st); + return -1; /* means no keyboard since we fudged the locking */ } - c = sc_cngetc_locked(NULL); + c = sc_cngetc_locked(&st); splx(s); + sccnclose(sc_console->sc, &st); return c; } @@ -1858,7 +1890,7 @@ sc_cngetc_locked(struct sc_cnstate *sp) if (fkeycp < fkey.len) return fkey.str[fkeycp++]; - c = scgetc(scp->sc, SCGETC_CN | SCGETC_NONBLOCK, NULL); + c = scgetc(scp->sc, SCGETC_CN | SCGETC_NONBLOCK, sp); switch (KEYFLAGS(c)) { case 0: /* normal char */ @@ -3464,7 +3496,11 @@ scgetc(sc_softc_t *sc, u_int flags, struct sc_cnstate *sp) scp = sc->cur_scp; /* first see if there is something in the keyboard port */ for (;;) { + if (flags & SCGETC_CN) + sccnscrunlock(sc, sp); c = kbdd_read_char(sc->kbd, !(flags & SCGETC_NONBLOCK)); + if (flags & SCGETC_CN) + sccnscrlock(sc, sp); if (c == ERRKEY) { if (!(flags & SCGETC_CN)) sc_bell(scp, bios_value.bell_pitch, BELL_DURATION); diff --git a/sys/dev/syscons/syscons.h b/sys/dev/syscons/syscons.h index f507be549210..8d8e5ca85f27 100644 --- a/sys/dev/syscons/syscons.h +++ b/sys/dev/syscons/syscons.h @@ -190,6 +190,7 @@ struct scr_stat; struct tty; struct sc_cnstate { + u_char kbd_locked; u_char kbd_opened; u_char scr_opened; }; From 0c127808dd64741edafbc4e9c5a05b604338e09a Mon Sep 17 00:00:00 2001 From: "Andrey V. Elsukov" Date: Wed, 31 Aug 2016 11:51:52 +0000 Subject: [PATCH 56/86] Remove redundant sanity checks from ipsec[46]_common_input_cb(). This check already has been done in the each protocol callback. --- sys/netipsec/ipsec_input.c | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/sys/netipsec/ipsec_input.c b/sys/netipsec/ipsec_input.c index 063096fb53c6..0ec07d8424ac 100644 --- a/sys/netipsec/ipsec_input.c +++ b/sys/netipsec/ipsec_input.c @@ -334,14 +334,6 @@ ipsec4_common_input_cb(struct mbuf *m, struct secasvar *sav, int skip, sproto == IPPROTO_IPCOMP, ("unexpected security protocol %u", sproto)); - /* Sanity check */ - if (m == NULL) { - DPRINTF(("%s: null mbuf", __func__)); - IPSEC_ISTAT(sproto, badkcr); - KEY_FREESAV(&sav); - return EINVAL; - } - if (skip != 0) { /* * Fix IPv4 header @@ -615,14 +607,6 @@ ipsec6_common_input_cb(struct mbuf *m, struct secasvar *sav, int skip, sproto == IPPROTO_IPCOMP, ("unexpected security protocol %u", sproto)); - /* Sanity check */ - if (m == NULL) { - DPRINTF(("%s: null mbuf", __func__)); - IPSEC_ISTAT(sproto, badkcr); - error = EINVAL; - goto bad; - } - /* Fix IPv6 header */ if (m->m_len < sizeof(struct ip6_hdr) && (m = m_pullup(m, sizeof(struct ip6_hdr))) == NULL) { From 9007a8679addebf0853c54474318f5cfa1e2e1ef Mon Sep 17 00:00:00 2001 From: Alexander Motin Date: Wed, 31 Aug 2016 11:55:31 +0000 Subject: [PATCH 57/86] Fix kernel panic when inheriting properties without default. There are two writable hidden properties "iscsioptions" and "stmf_sbd_lu", that have no default string value. Attempt to unset them or replicate caused kernel panic. This simple bandaid seems fixes the problem nicely. MFC after: 2 weeks --- sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_prop.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_prop.c b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_prop.c index 8586cb6232e0..25a7d969b5d4 100644 --- a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_prop.c +++ b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/dsl_prop.c @@ -54,6 +54,8 @@ dodefault(zfs_prop_t prop, int intsz, int numints, void *buf) return (SET_ERROR(ENOENT)); if (zfs_prop_get_type(prop) == PROP_TYPE_STRING) { + if (zfs_prop_default_string(prop) == NULL) + return (SET_ERROR(ENOENT)); if (intsz != 1) return (SET_ERROR(EOVERFLOW)); (void) strncpy(buf, zfs_prop_default_string(prop), From 44feca2360533cab5b809763dffec79922eaf633 Mon Sep 17 00:00:00 2001 From: Mateusz Guzik Date: Wed, 31 Aug 2016 12:29:04 +0000 Subject: [PATCH 58/86] fd: effectively revert r305091 Turns out fd_lastfile can survive being -1 for some processes, giving incorrect results with the cast. Noted by: cem --- sys/sys/filedesc.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sys/sys/filedesc.h b/sys/sys/filedesc.h index bdb42460c9c4..869a6c681cfd 100644 --- a/sys/sys/filedesc.h +++ b/sys/sys/filedesc.h @@ -201,7 +201,7 @@ fget_locked(struct filedesc *fdp, int fd) FILEDESC_LOCK_ASSERT(fdp); - if ((u_int)fd > fdp->fd_lastfile) + if (fd < 0 || fd > fdp->fd_lastfile) return (NULL); return (fdp->fd_ofiles[fd].fde_file); @@ -213,7 +213,7 @@ fdeget_locked(struct filedesc *fdp, int fd) FILEDESC_LOCK_ASSERT(fdp); - if ((u_int)fd > fdp->fd_lastfile) + if (fd < 0 || fd > fdp->fd_lastfile) return (NULL); return (&fdp->fd_ofiles[fd]); From 6a695123b06105c58dcbf8afd2754714f300a12d Mon Sep 17 00:00:00 2001 From: Baptiste Daroussin Date: Wed, 31 Aug 2016 13:16:40 +0000 Subject: [PATCH 59/86] Netboot: allow both tftpfs and nfs in both pxeboot and loader.efi Add a new 'netproto' variable which can be set for now to NET_TFTP or NET_NFS (default to NET_NONE) From the dhcp options if one sets the root-path option to: "ip:path", the loader will consider it is booting over NFS (meaning same behaviour as the default current behaviour) if the dhcp option "tftp server address" is set (option 150) the loader will consider it is booting over tftpfs, it will then consider the root-path options with 2 possible case 1. "path" then the IP of the tftp server will be the one passed by the option 150, and the files will be retrieved under "path" on the tftp server 2. "ip:path" then the IP of the tftp server will be the one passed in the option "overwritting the IP from the option 150. We could not "abuse" the rootpath option in the form or tftp://ip:path because this is already used for other purpose by iPXE preventing any chainload from iPXE to the FreeBSD loader. Given at each open(), the loader loops over all available filesystems and keep the "best" error, we needed to prevent tftpfs to fallback on nfs and vice versa. the tftpfs and nfs implementation in libstand now return EINVAL early if 'netproto' for that purpose. Reviewed by: tsoome Relnotes: yes Sponsored by: Gandi.net Differential Revision: https://reviews.freebsd.org/D7628 --- lib/libstand/bootp.c | 4 ++++ lib/libstand/bootp.h | 1 + lib/libstand/globals.c | 2 ++ lib/libstand/net.h | 11 +++++++++++ lib/libstand/nfs.c | 6 ++++++ lib/libstand/tftp.c | 3 +++ sys/boot/common/dev_net.c | 27 ++++++++++++++++++--------- sys/boot/efi/libefi/Makefile | 4 ---- sys/boot/efi/loader/Makefile | 4 ---- sys/boot/efi/loader/conf.c | 3 --- sys/boot/i386/libi386/pxe.c | 35 +++++++++++++++++++---------------- sys/boot/i386/loader/conf.c | 4 ---- sys/boot/pc98/loader/conf.c | 4 ---- 13 files changed, 64 insertions(+), 44 deletions(-) diff --git a/lib/libstand/bootp.c b/lib/libstand/bootp.c index f3bc81697911..7474f8f971d5 100644 --- a/lib/libstand/bootp.c +++ b/lib/libstand/bootp.c @@ -411,6 +411,10 @@ vend_rfc1048(cp, len) bcopy(cp, &dhcp_serverip.s_addr, sizeof(dhcp_serverip.s_addr)); } + if (tag == TAG_TFTP_SERVER) { + bcopy(cp, &tftpip.s_addr, + sizeof(tftpip.s_addr)); + } #endif cp += size; } diff --git a/lib/libstand/bootp.h b/lib/libstand/bootp.h index 47e5649ce9a0..9f4d4139a5b1 100644 --- a/lib/libstand/bootp.h +++ b/lib/libstand/bootp.h @@ -106,6 +106,7 @@ struct bootp { #define TAG_T2 ((unsigned char) 59) #define TAG_CLASSID ((unsigned char) 60) #define TAG_CLIENTID ((unsigned char) 61) +#define TAG_TFTP_SERVER ((unsigned char) 150) #endif #define TAG_END ((unsigned char) 255) diff --git a/lib/libstand/globals.c b/lib/libstand/globals.c index f2c624083c27..83b9f777a857 100644 --- a/lib/libstand/globals.c +++ b/lib/libstand/globals.c @@ -25,12 +25,14 @@ char hostname[FNAME_SIZE]; /* our hostname */ int hostnamelen; char domainname[FNAME_SIZE]; /* our DNS domain */ int domainnamelen; +int netproto = NET_NONE; /* Network prototol */ char ifname[IFNAME_SIZE]; /* name of interface (e.g. "le0") */ struct in_addr myip; /* my ip address */ struct in_addr nameip; /* DNS server ip address */ struct in_addr rootip; /* root ip address */ struct in_addr swapip; /* swap ip address */ struct in_addr gateip; /* gateway ip address */ +struct in_addr tftpip; /* TFTP ip address */ n_long netmask = 0xffffff00; /* subnet or net mask */ u_int intf_mtu; /* interface mtu from bootp/dhcp */ int errno; /* our old friend */ diff --git a/lib/libstand/net.h b/lib/libstand/net.h index ce7df49f2de2..ba37473595ac 100644 --- a/lib/libstand/net.h +++ b/lib/libstand/net.h @@ -36,6 +36,8 @@ * $FreeBSD$ */ +#ifndef _STAND_NET_H +#define _STAND_NET_H #ifndef _KERNEL /* XXX - see */ #undef __IPADDR #define __IPADDR(x) htonl((u_int32_t)(x)) @@ -45,6 +47,12 @@ #define BA { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff } +enum net_proto { + NET_NONE, + NET_NFS, + NET_TFTP +}; + /* Returns true if n_long's on the same net */ #define SAMENET(a1, a2, m) ((a1.s_addr & m) == (a2.s_addr & m)) @@ -74,6 +82,7 @@ extern char hostname[FNAME_SIZE]; extern int hostnamelen; extern char domainname[FNAME_SIZE]; extern int domainnamelen; +extern int netproto; extern char ifname[IFNAME_SIZE]; /* All of these are in network order. */ @@ -82,6 +91,7 @@ extern struct in_addr rootip; extern struct in_addr swapip; extern struct in_addr gateip; extern struct in_addr nameip; +extern struct in_addr tftpip; extern n_long netmask; extern u_int intf_mtu; @@ -120,3 +130,4 @@ n_long inet_addr(char *); /* Machine-dependent functions: */ time_t getsecs(void); +#endif diff --git a/lib/libstand/nfs.c b/lib/libstand/nfs.c index 222b2f50af4d..29f8ecf514b9 100644 --- a/lib/libstand/nfs.c +++ b/lib/libstand/nfs.c @@ -458,6 +458,9 @@ nfs_open(const char *upath, struct open_file *f) int error; char *path; + if (netproto != NET_NFS) + return (EINVAL); + #ifdef NFS_DEBUG if (debug) printf("nfs_open: %s (rootpath=%s)\n", upath, rootpath); @@ -1100,6 +1103,9 @@ nfs_open(const char *upath, struct open_file *f) int error; char *path; + if (netproto != NET_NFS) + return (EINVAL); + #ifdef NFS_DEBUG if (debug) printf("nfs_open: %s (rootpath=%s)\n", upath, rootpath); diff --git a/lib/libstand/tftp.c b/lib/libstand/tftp.c index cb84970910f9..b3d2da7b0ed9 100644 --- a/lib/libstand/tftp.c +++ b/lib/libstand/tftp.c @@ -402,6 +402,9 @@ tftp_open(const char *path, struct open_file *f) size_t pathsize; const char *extraslash; + if (netproto != NET_TFTP) + return (EINVAL); + if (strcmp(f->f_dev->dv_name, "net") != 0) { #ifdef __i386__ if (strcmp(f->f_dev->dv_name, "pxe") != 0) diff --git a/sys/boot/common/dev_net.c b/sys/boot/common/dev_net.c index 733e3c327f12..d0f2690ecd2b 100644 --- a/sys/boot/common/dev_net.c +++ b/sys/boot/common/dev_net.c @@ -167,13 +167,14 @@ net_open(struct open_file *f, ...) setenv("boot.netif.ip", inet_ntoa(myip), 1); setenv("boot.netif.netmask", intoa(netmask), 1); setenv("boot.netif.gateway", inet_ntoa(gateip), 1); -#ifdef LOADER_TFTP_SUPPORT - setenv("boot.tftproot.server", inet_ntoa(rootip), 1); - setenv("boot.tftproot.path", rootpath, 1); -#else - setenv("boot.nfsroot.server", inet_ntoa(rootip), 1); - setenv("boot.nfsroot.path", rootpath, 1); -#endif + setenv("boot.netif.server", inet_ntoa(rootip), 1); + if (netproto == NET_TFTP) { + setenv("boot.tftproot.server", inet_ntoa(rootip), 1); + setenv("boot.tftproot.path", rootpath, 1); + } else if (netproto == NET_NFS) { + setenv("boot.nfsroot.server", inet_ntoa(rootip), 1); + setenv("boot.nfsroot.path", rootpath, 1); + } if (intf_mtu != 0) { char mtu[16]; sprintf(mtu, "%u", intf_mtu); @@ -367,16 +368,24 @@ net_print(int verbose) uint32_t net_parse_rootpath() { - int i; + int i, ipstart; n_long addr = INADDR_NONE; + netproto = NET_NFS; + + if (tftpip.s_addr != 0) { + netproto = NET_TFTP; + addr = tftpip.s_addr; + } + for (i = 0; rootpath[i] != '\0' && i < FNAME_SIZE; i++) if (rootpath[i] == ':') break; if (i && i != FNAME_SIZE && rootpath[i] == ':') { rootpath[i++] = '\0'; - addr = inet_addr(&rootpath[0]); + addr = inet_addr(&rootpath[ipstart]); bcopy(&rootpath[i], rootpath, strlen(&rootpath[i])+1); } + return (addr); } diff --git a/sys/boot/efi/libefi/Makefile b/sys/boot/efi/libefi/Makefile index 058a86cbb50c..9ea2c3333366 100644 --- a/sys/boot/efi/libefi/Makefile +++ b/sys/boot/efi/libefi/Makefile @@ -13,10 +13,6 @@ SRCS+= time.c SRCS+= time_event.c .endif -.if defined(LOADER_TFTP_SUPPORT) -CFLAGS+= -DLOADER_TFTP_SUPPORT -DNETIF_OPEN_CLOSE_ONCE -.endif - # We implement a slightly non-standard %S in that it always takes a # CHAR16 that's common in UEFI-land instead of a wchar_t. This only # seems to matter on arm64 where wchar_t defaults to an int instead diff --git a/sys/boot/efi/loader/Makefile b/sys/boot/efi/loader/Makefile index 5e193596badb..07c7af17212e 100644 --- a/sys/boot/efi/loader/Makefile +++ b/sys/boot/efi/loader/Makefile @@ -21,10 +21,6 @@ SRCS= autoload.c \ smbios.c \ vers.c -.if defined(LOADER_TFTP_SUPPORT) -CFLAGS+= -DLOADER_TFTP_SUPPORT -DNETIF_OPEN_CLOSE_ONCE -.endif - .if ${MK_ZFS} != "no" SRCS+= zfs.c .PATH: ${.CURDIR}/../../zfs diff --git a/sys/boot/efi/loader/conf.c b/sys/boot/efi/loader/conf.c index 91d4c714718e..3596a6360c3b 100644 --- a/sys/boot/efi/loader/conf.c +++ b/sys/boot/efi/loader/conf.c @@ -51,11 +51,8 @@ struct fs_ops *file_system[] = { &dosfs_fsops, &ufs_fsops, &cd9660_fsops, -#ifdef LOADER_TFTP_SUPPORT &tftp_fsops, -#else &nfs_fsops, -#endif &gzipfs_fsops, &bzipfs_fsops, NULL diff --git a/sys/boot/i386/libi386/pxe.c b/sys/boot/i386/libi386/pxe.c index 096ebc4d58a2..28046f3ba1d1 100644 --- a/sys/boot/i386/libi386/pxe.c +++ b/sys/boot/i386/libi386/pxe.c @@ -288,10 +288,15 @@ pxe_open(struct open_file *f, ...) bootp(pxe_sock, BOOTP_PXE); if (rootip.s_addr == 0) rootip.s_addr = bootplayer.sip; -#ifdef LOADER_NFS_SUPPORT - if (!rootpath[0]) + + netproto = NET_NFS; + if (tftpip.s_addr != 0) { + netproto = NET_TFTP; + rootip.s_addr = tftpip.s_addr; + } + + if (netproto == NET_NFS && !rootpath[0]) strcpy(rootpath, PXENFSROOTPATH); -#endif for (i = 0; rootpath[i] != '\0' && i < FNAME_SIZE; i++) if (rootpath[i] == ':') @@ -315,17 +320,17 @@ pxe_open(struct open_file *f, ...) sprintf(mtu, "%u", intf_mtu); setenv("boot.netif.mtu", mtu, 1); } -#ifdef LOADER_NFS_SUPPORT printf("pxe_open: server addr: %s\n", inet_ntoa(rootip)); printf("pxe_open: server path: %s\n", rootpath); printf("pxe_open: gateway ip: %s\n", inet_ntoa(gateip)); - setenv("boot.nfsroot.server", inet_ntoa(rootip), 1); - setenv("boot.nfsroot.path", rootpath, 1); -#else - setenv("boot.netif.server", inet_ntoa(rootip), 1); - setenv("boot.tftproot.path", rootpath, 1); -#endif + if (netproto == NET_NFS) { + setenv("boot.nfsroot.server", inet_ntoa(rootip), 1); + setenv("boot.nfsroot.path", rootpath, 1); + } else if (netproto == NET_TFTP) { + setenv("boot.netif.server", inet_ntoa(rootip), 1); + setenv("boot.tftproot.path", rootpath, 1); + } setenv("dhcp.host-name", hostname, 1); setenv("pxeboot.ip", inet_ntoa(myip), 1); @@ -359,10 +364,10 @@ pxe_close(struct open_file *f) if (pxe_opens > 0) return(0); -#ifdef LOADER_NFS_SUPPORT - /* get an NFS filehandle for our root filesystem */ - pxe_setnfshandle(rootpath); -#endif + if (netproto == NET_NFS) { + /* get an NFS filehandle for our root filesystem */ + pxe_setnfshandle(rootpath); + } if (pxe_sock >= 0) { @@ -422,7 +427,6 @@ pxe_perror(int err) return; } -#ifdef LOADER_NFS_SUPPORT /* * Reach inside the libstand NFS code and dig out an NFS handle * for the root filesystem. @@ -533,7 +537,6 @@ pxe_setnfshandle(char *rootpath) setenv("boot.nfsroot.nfshandlelen", buf, 1); } #endif /* OLD_NFSV2 */ -#endif /* LOADER_NFS_SUPPORT */ void pxenv_call(int func) diff --git a/sys/boot/i386/loader/conf.c b/sys/boot/i386/loader/conf.c index 38df74d18be0..29ce1e332605 100644 --- a/sys/boot/i386/loader/conf.c +++ b/sys/boot/i386/loader/conf.c @@ -45,10 +45,6 @@ __FBSDID("$FreeBSD$"); * XXX as libi386 and biosboot merge, some of these can become linker sets. */ -#if defined(LOADER_NFS_SUPPORT) && defined(LOADER_TFTP_SUPPORT) -#error "Cannot have both tftp and nfs support yet." -#endif - #if defined(LOADER_FIREWIRE_SUPPORT) extern struct devsw fwohci; #endif diff --git a/sys/boot/pc98/loader/conf.c b/sys/boot/pc98/loader/conf.c index d05cd13f9b20..695c2604c03a 100644 --- a/sys/boot/pc98/loader/conf.c +++ b/sys/boot/pc98/loader/conf.c @@ -42,10 +42,6 @@ __FBSDID("$FreeBSD$"); * XXX as libi386 and biosboot merge, some of these can become linker sets. */ -#if defined(LOADER_NFS_SUPPORT) && defined(LOADER_TFTP_SUPPORT) -#error "Cannot have both tftp and nfs support yet." -#endif - /* Exported for libstand */ struct devsw *devsw[] = { &bioscd, From 665a3a9a7974db933528226e33ee6852fb764c5f Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Wed, 31 Aug 2016 13:50:23 +0000 Subject: [PATCH 60/86] Import ELF Tool Chain snapshot at revision 3490 From http://svn.code.sf.net/p/elftoolchain/code/ --- common/elfdefinitions.h | 7 ++- elfcopy/archive.c | 7 ++- elfcopy/ascii.c | 3 +- elfcopy/pe.c | 7 ++- elfdump/elfdump.c | 4 +- libelf/elf_flagdata.3 | 5 +- libelftc/Makefile | 3 +- libelftc/elftc_bfd_find_target.3 | 3 +- libelftc/elftc_reloc_type_str.c | 3 + libelftc/elftc_timestamp.3 | 79 ++++++++++++++++++++++++ libelftc/elftc_timestamp.c | 55 +++++++++++++++++ libelftc/libelftc.h | 3 +- libelftc/libelftc_bfdtarget.c | 10 +++- libelftc/libelftc_dem_gnu3.c | 4 +- readelf/readelf.1 | 4 +- readelf/readelf.c | 100 ++++++++++++++++++++++++++----- 16 files changed, 263 insertions(+), 34 deletions(-) create mode 100644 libelftc/elftc_timestamp.3 create mode 100644 libelftc/elftc_timestamp.c diff --git a/common/elfdefinitions.h b/common/elfdefinitions.h index ec22528c6eab..7460bb68443f 100644 --- a/common/elfdefinitions.h +++ b/common/elfdefinitions.h @@ -23,7 +23,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $Id: elfdefinitions.h 3455 2016-05-09 13:47:29Z emaste $ + * $Id: elfdefinitions.h 3485 2016-08-18 13:38:52Z emaste $ */ /* @@ -2091,7 +2091,10 @@ _ELF_DEFINE_RELOC(R_RISCV_GNU_VTINHERIT, 41) \ _ELF_DEFINE_RELOC(R_RISCV_GNU_VTENTRY, 42) \ _ELF_DEFINE_RELOC(R_RISCV_ALIGN, 43) \ _ELF_DEFINE_RELOC(R_RISCV_RVC_BRANCH, 44) \ -_ELF_DEFINE_RELOC(R_RISCV_RVC_JUMP, 45) +_ELF_DEFINE_RELOC(R_RISCV_RVC_JUMP, 45) \ +_ELF_DEFINE_RELOC(R_RISCV_RVC_LUI, 46) \ +_ELF_DEFINE_RELOC(R_RISCV_GPREL_I, 47) \ +_ELF_DEFINE_RELOC(R_RISCV_GPREL_S, 48) #define _ELF_DEFINE_SPARC_RELOCATIONS() \ _ELF_DEFINE_RELOC(R_SPARC_NONE, 0) \ diff --git a/elfcopy/archive.c b/elfcopy/archive.c index 97e2498a66ff..efdde7263766 100644 --- a/elfcopy/archive.c +++ b/elfcopy/archive.c @@ -38,7 +38,7 @@ #include "elfcopy.h" -ELFTC_VCSID("$Id: archive.c 3287 2015-12-31 16:58:48Z emaste $"); +ELFTC_VCSID("$Id: archive.c 3490 2016-08-31 00:12:22Z emaste $"); #define _ARMAG_LEN 8 /* length of ar magic string */ #define _ARHDR_LEN 60 /* length of ar header */ @@ -440,6 +440,7 @@ ac_write_objs(struct elfcopy *ecp, int ofd) struct archive *a; struct archive_entry *entry; struct ar_obj *obj; + time_t timestamp; int nr; if ((a = archive_write_new()) == NULL) @@ -450,7 +451,9 @@ ac_write_objs(struct elfcopy *ecp, int ofd) /* Write the archive symbol table, even if it's empty. */ entry = archive_entry_new(); archive_entry_copy_pathname(entry, "/"); - archive_entry_set_mtime(entry, time(NULL), 0); + if (elftc_timestamp(×tamp) != 0) + err(EXIT_FAILURE, "elftc_timestamp"); + archive_entry_set_mtime(entry, timestamp, 0); archive_entry_set_size(entry, (ecp->s_cnt + 1) * sizeof(uint32_t) + ecp->s_sn_sz); AC(archive_write_header(a, entry)); diff --git a/elfcopy/ascii.c b/elfcopy/ascii.c index fb1edb3cce46..4ba05c427d9e 100644 --- a/elfcopy/ascii.c +++ b/elfcopy/ascii.c @@ -36,7 +36,7 @@ #include "elfcopy.h" -ELFTC_VCSID("$Id: ascii.c 3446 2016-05-03 01:31:17Z emaste $"); +ELFTC_VCSID("$Id: ascii.c 3487 2016-08-24 18:12:08Z emaste $"); static void append_data(struct section *s, const void *buf, size_t sz); static char hex_digit(uint8_t n); @@ -251,6 +251,7 @@ create_elf_from_srec(struct elfcopy *ecp, int ifd) sec_index = 1; sec_addr = entry = 0; while (fgets(line, _LINE_BUFSZ, ifp) != NULL) { + sz = 0; if (line[0] == '\r' || line[0] == '\n') continue; if (line[0] == '$' && line[1] == '$') { diff --git a/elfcopy/pe.c b/elfcopy/pe.c index 586b21a74095..8deb80918553 100644 --- a/elfcopy/pe.c +++ b/elfcopy/pe.c @@ -34,7 +34,7 @@ #include "elfcopy.h" -ELFTC_VCSID("$Id: pe.c 3477 2016-05-25 20:00:42Z kaiwang27 $"); +ELFTC_VCSID("$Id: pe.c 3490 2016-08-31 00:12:22Z emaste $"); /* Convert ELF object to Portable Executable (PE). */ void @@ -54,6 +54,7 @@ create_pe(struct elfcopy *ecp, int ifd, int ofd) PE_Buffer *pb; const char *name; size_t indx; + time_t timestamp; int elferr; if (ecp->otf == ETF_EFI || ecp->oem == EM_X86_64) @@ -89,7 +90,9 @@ create_pe(struct elfcopy *ecp, int ifd, int ofd) pch.ch_machine = IMAGE_FILE_MACHINE_UNKNOWN; break; } - pch.ch_timestamp = (uint32_t) time(NULL); + if (elftc_timestamp(×tamp) != 0) + err(EXIT_FAILURE, "elftc_timestamp"); + pch.ch_timestamp = (uint32_t) timestamp; if (pe_update_coff_header(pe, &pch) < 0) err(EXIT_FAILURE, "pe_update_coff_header() failed"); diff --git a/elfdump/elfdump.c b/elfdump/elfdump.c index cf27ea6b9a94..2ce9469f8367 100644 --- a/elfdump/elfdump.c +++ b/elfdump/elfdump.c @@ -50,7 +50,7 @@ #include "_elftc.h" -ELFTC_VCSID("$Id: elfdump.c 3474 2016-05-17 20:44:53Z emaste $"); +ELFTC_VCSID("$Id: elfdump.c 3482 2016-08-02 18:47:00Z emaste $"); #if defined(ELFTC_NEED_ELF_NOTE_DEFINITION) #include "native-elf-format.h" @@ -332,6 +332,8 @@ static const char *ei_abis[256] = { "ELFOSABI_IRIX", "ELFOSABI_FREEBSD", "ELFOSABI_TRU64", "ELFOSABI_MODESTO", "ELFOSABI_OPENBSD", [17] = "ELFOSABI_CLOUDABI", + [64] = "ELFOSABI_ARM_AEABI", + [97] = "ELFOSABI_ARM", [255] = "ELFOSABI_STANDALONE" }; diff --git a/libelf/elf_flagdata.3 b/libelf/elf_flagdata.3 index fc27109a746e..de3cfd973160 100644 --- a/libelf/elf_flagdata.3 +++ b/libelf/elf_flagdata.3 @@ -21,7 +21,7 @@ .\" out of the use of this software, even if advised of the possibility of .\" such damage. .\" -.\" $Id: elf_flagdata.3 2884 2013-01-11 02:03:46Z jkoshy $ +.\" $Id: elf_flagdata.3 3479 2016-06-25 20:44:33Z jkoshy $ .\" .Dd December 3, 2011 .Os @@ -208,16 +208,13 @@ was called without a program header being allocated. .Xr elf 3 , .Xr elf32_newehdr 3 , .Xr elf32_newphdr 3 , -.Xr elf32_newshdr 3 , .Xr elf64_newehdr 3 , .Xr elf64_newphdr 3 , -.Xr elf64_newshdr 3 , .Xr elf_newdata 3 , .Xr elf_update 3 , .Xr gelf 3 , .Xr gelf_newehdr 3 , .Xr gelf_newphdr 3 , -.Xr gelf_newshdr 3 , .Xr gelf_update_dyn 3 , .Xr gelf_update_move 3 , .Xr gelf_update_rel 3 , diff --git a/libelftc/Makefile b/libelftc/Makefile index 6e38a8732be4..910bbdbbb20e 100644 --- a/libelftc/Makefile +++ b/libelftc/Makefile @@ -1,4 +1,4 @@ -# $Id: Makefile 3418 2016-02-19 20:04:42Z emaste $ +# $Id: Makefile 3489 2016-08-31 00:12:15Z emaste $ TOP= ${.CURDIR}/.. @@ -10,6 +10,7 @@ SRCS= elftc_bfdtarget.c \ elftc_reloc_type_str.c \ elftc_set_timestamps.c \ elftc_string_table.c \ + elftc_timestamp.c \ elftc_version.c \ libelftc_bfdtarget.c \ libelftc_dem_arm.c \ diff --git a/libelftc/elftc_bfd_find_target.3 b/libelftc/elftc_bfd_find_target.3 index 20dea3cb97d9..2e4dbaac8362 100644 --- a/libelftc/elftc_bfd_find_target.3 +++ b/libelftc/elftc_bfd_find_target.3 @@ -21,7 +21,7 @@ .\" out of the use of this software, even if advised of the possibility of .\" such damage. .\" -.\" $Id: elftc_bfd_find_target.3 3348 2016-01-18 14:18:50Z emaste $ +.\" $Id: elftc_bfd_find_target.3 3488 2016-08-24 18:15:57Z emaste $ .\" .Dd November 30, 2011 .Os @@ -89,6 +89,7 @@ Known descriptor names and their properties include: .It Li elf64-ia64-big Ta ELF Ta MSB Ta 64 .It Li elf64-ia64-little Ta ELF Ta LSB Ta 64 .It Li elf64-little Ta ELF Ta LSB Ta 64 +.It Li elf64-littleaarch64 Ta ELF Ta LSB Ta 64 .It Li elf64-littlemips Ta ELF Ta LSB Ta 64 .It Li elf64-powerpc Ta ELF Ta MSB Ta 64 .It Li elf64-powerpcle Ta ELF Ta LSB Ta 64 diff --git a/libelftc/elftc_reloc_type_str.c b/libelftc/elftc_reloc_type_str.c index a22a1be7655b..19b23ad52904 100644 --- a/libelftc/elftc_reloc_type_str.c +++ b/libelftc/elftc_reloc_type_str.c @@ -545,6 +545,9 @@ elftc_reloc_type_str(unsigned int mach, unsigned int type) case 43: return "R_RISCV_ALIGN"; case 44: return "R_RISCV_RVC_BRANCH"; case 45: return "R_RISCV_RVC_JUMP"; + case 46: return "R_RISCV_RVC_LUI"; + case 47: return "R_RISCV_GPREL_I"; + case 48: return "R_RISCV_GPREL_S"; } break; case EM_SPARC: diff --git a/libelftc/elftc_timestamp.3 b/libelftc/elftc_timestamp.3 new file mode 100644 index 000000000000..3c56f2fe5b9e --- /dev/null +++ b/libelftc/elftc_timestamp.3 @@ -0,0 +1,79 @@ +.\" Copyright (c) 2016 The FreeBSD Foundation. All rights reserved. +.\" +.\" This documentation was written by Ed Maste under sponsorship of +.\" the FreeBSD Foundation. +.\" +.\" 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. +.\" +.\" This software is provided by the author 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 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. +.\" +.\" $Id$ +.\" +.Dd August 24, 2016 +.Os +.Dt ELFTC_TIMESTAMP 3 +.Sh NAME +.Nm elftc_timestamp +.Nd return the current or environment-provided timestamp +.Sh LIBRARY +.Lb libelftc +.Sh SYNOPSIS +.In libelftc.h +.Ft int +.Fo elftc_timestamp +.Fa "time_t *timestamp" +.Fc +.Sh DESCRIPTION +The +.Fn elftc_timestamp +function returns a timestamp supplied by the +.Ev SOURCE_DATE_EPOCH +environment variable, or the current time provided by +.Xr time 3 +if the environment variable is not set. +.Pp +The +.Ar timestamp +argument specifies a pointer to the location where the timestamp will be +stored. +.Sh RETURN VALUE +Function +.Fn elftc_timestamp +returns 0 on success, and -1 in the event of an error. +.Sh ERRORS +The +.Fn elftc_timestamp +function may fail with the following errors: +.Bl -tag -width ".Bq Er ERANGE" +.It Bq Er EINVAL +.Ev SOURCE_DATE_EPOCH +contains invalid characters. +.It Bq Er ERANGE +.Ev SOURCE_DATE_EPOCH +specifies a negative value or a value that cannot be stored in a +time_t. +.El +The +.Fn elftc_timestamp +function may also fail for any of the reasons described in +.Xr strtoll 3 . +.Sh SEE ALSO +.Xr strtoll 3 , +.Xr time 3 diff --git a/libelftc/elftc_timestamp.c b/libelftc/elftc_timestamp.c new file mode 100644 index 000000000000..ccf482f27676 --- /dev/null +++ b/libelftc/elftc_timestamp.c @@ -0,0 +1,55 @@ +/*- + * Copyright (c) 2016 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Ed Maste under sponsorship + * of the FreeBSD Foundation. + * + * 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. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 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. + */ + +#include +#include +#include +#include + +int +elftc_timestamp(time_t *timestamp) +{ + long long source_date_epoch; + char *env, *eptr; + + if ((env = getenv("SOURCE_DATE_EPOCH")) != NULL) { + errno = 0; + source_date_epoch = strtoll(env, &eptr, 10); + if (*eptr != '\0') + errno = EINVAL; + if (source_date_epoch < 0) + errno = ERANGE; + if (errno != 0) + return (-1); + *timestamp = source_date_epoch; + return (0); + } + *timestamp = time(NULL); + return (0); +} diff --git a/libelftc/libelftc.h b/libelftc/libelftc.h index 6c2b57a4b680..a235097e6910 100644 --- a/libelftc/libelftc.h +++ b/libelftc/libelftc.h @@ -24,7 +24,7 @@ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: users/kaiwang27/elftc/libelftc.h 392 2009-05-31 19:17:46Z kaiwang27 $ - * $Id: libelftc.h 3418 2016-02-19 20:04:42Z emaste $ + * $Id: libelftc.h 3489 2016-08-31 00:12:15Z emaste $ */ #ifndef _LIBELFTC_H_ @@ -91,6 +91,7 @@ int elftc_string_table_remove(Elftc_String_Table *_table, const char *_string); const char *elftc_string_table_to_string(Elftc_String_Table *_table, size_t offset); +int elftc_timestamp(time_t *_timestamp); const char *elftc_version(void); #ifdef __cplusplus } diff --git a/libelftc/libelftc_bfdtarget.c b/libelftc/libelftc_bfdtarget.c index 88f3220df0b0..d87d4d8b445d 100644 --- a/libelftc/libelftc_bfdtarget.c +++ b/libelftc/libelftc_bfdtarget.c @@ -30,7 +30,7 @@ #include "_libelftc.h" -ELFTC_VCSID("$Id: libelftc_bfdtarget.c 3309 2016-01-10 09:10:51Z kaiwang27 $"); +ELFTC_VCSID("$Id: libelftc_bfdtarget.c 3488 2016-08-24 18:15:57Z emaste $"); struct _Elftc_Bfd_Target _libelftc_targets[] = { @@ -249,6 +249,14 @@ struct _Elftc_Bfd_Target _libelftc_targets[] = { .bt_elfclass = ELFCLASS64, }, + { + .bt_name = "elf64-littleaarch64", + .bt_type = ETF_ELF, + .bt_byteorder = ELFDATA2LSB, + .bt_elfclass = ELFCLASS64, + .bt_machine = EM_AARCH64, + }, + { .bt_name = "elf64-littlemips", .bt_type = ETF_ELF, diff --git a/libelftc/libelftc_dem_gnu3.c b/libelftc/libelftc_dem_gnu3.c index 7409363f73ee..c3d3f4b7f594 100644 --- a/libelftc/libelftc_dem_gnu3.c +++ b/libelftc/libelftc_dem_gnu3.c @@ -36,7 +36,7 @@ #include "_libelftc.h" -ELFTC_VCSID("$Id: libelftc_dem_gnu3.c 3447 2016-05-03 13:32:23Z emaste $"); +ELFTC_VCSID("$Id: libelftc_dem_gnu3.c 3480 2016-07-24 23:38:41Z emaste $"); /** * @file cpp_demangle.c @@ -2551,7 +2551,7 @@ cpp_demangle_read_type(struct cpp_demangle_data *ddata, int delimit) case 'w': /* wchar_t */ - if (!cpp_demangle_push_str(ddata, "wchar_t", 6)) + if (!cpp_demangle_push_str(ddata, "wchar_t", 7)) goto clean; ++ddata->cur; goto rtn; diff --git a/readelf/readelf.1 b/readelf/readelf.1 index 701d50089515..0741238c9261 100644 --- a/readelf/readelf.1 +++ b/readelf/readelf.1 @@ -22,7 +22,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.\" $Id: readelf.1 3219 2015-05-24 23:42:34Z kaiwang27 $ +.\" $Id: readelf.1 3486 2016-08-22 14:10:05Z emaste $ .\" .Dd September 13, 2012 .Os @@ -43,12 +43,12 @@ .Op Fl p Ar section | Fl -string-dump Ns = Ns Ar section .Op Fl r | Fl -relocs .Op Fl t | Fl -section-details -.Op Fl x Ar section | Fl -hex-dump Ns = Ns Ar section .Op Fl v | Fl -version .Oo .Fl w Ns Oo Ns Ar afilmoprsFLR Ns Oc | .Fl -debug-dump Ns Op Ns = Ns Ar long-option-name , Ns ... .Oc +.Op Fl x Ar section | Fl -hex-dump Ns = Ns Ar section .Op Fl A | Fl -arch-specific .Op Fl D | Fl -use-dynamic .Op Fl H | Fl -help diff --git a/readelf/readelf.c b/readelf/readelf.c index b8bb4a11b137..6da2ed28e05f 100644 --- a/readelf/readelf.c +++ b/readelf/readelf.c @@ -47,7 +47,7 @@ #include "_elftc.h" -ELFTC_VCSID("$Id: readelf.c 3469 2016-05-15 23:16:09Z emaste $"); +ELFTC_VCSID("$Id: readelf.c 3484 2016-08-03 13:36:49Z emaste $"); /* * readelf(1) options. @@ -334,7 +334,7 @@ static const char *note_type_openbsd(unsigned int nt); static const char *note_type_unknown(unsigned int nt); static const char *note_type_xen(unsigned int nt); static const char *option_kind(uint8_t kind); -static const char *phdr_type(unsigned int ptype); +static const char *phdr_type(unsigned int mach, unsigned int ptype); static const char *ppc_abi_fp(uint64_t fp); static const char *ppc_abi_vector(uint64_t vec); static void readelf_usage(int status); @@ -431,6 +431,7 @@ elf_osabi(unsigned int abi) case ELFOSABI_OPENVMS: return "OpenVMS"; case ELFOSABI_NSK: return "NSK"; case ELFOSABI_CLOUDABI: return "CloudABI"; + case ELFOSABI_ARM_AEABI: return "ARM EABI"; case ELFOSABI_ARM: return "ARM"; case ELFOSABI_STANDALONE: return "StandAlone"; default: @@ -613,10 +614,24 @@ elf_ver(unsigned int ver) } static const char * -phdr_type(unsigned int ptype) +phdr_type(unsigned int mach, unsigned int ptype) { static char s_ptype[32]; + if (ptype >= PT_LOPROC && ptype <= PT_HIPROC) { + switch (mach) { + case EM_ARM: + switch (ptype) { + case PT_ARM_ARCHEXT: return "ARM_ARCHEXT"; + case PT_ARM_EXIDX: return "ARM_EXIDX"; + } + break; + } + snprintf(s_ptype, sizeof(s_ptype), "LOPROC+%#x", + ptype - PT_LOPROC); + return (s_ptype); + } + switch (ptype) { case PT_NULL: return "NULL"; case PT_LOAD: return "LOAD"; @@ -630,10 +645,7 @@ phdr_type(unsigned int ptype) case PT_GNU_STACK: return "GNU_STACK"; case PT_GNU_RELRO: return "GNU_RELRO"; default: - if (ptype >= PT_LOPROC && ptype <= PT_HIPROC) - snprintf(s_ptype, sizeof(s_ptype), "LOPROC+%#x", - ptype - PT_LOPROC); - else if (ptype >= PT_LOOS && ptype <= PT_HIOS) + if (ptype >= PT_LOOS && ptype <= PT_HIOS) snprintf(s_ptype, sizeof(s_ptype), "LOOS+%#x", ptype - PT_LOOS); else @@ -650,6 +662,15 @@ section_type(unsigned int mach, unsigned int stype) if (stype >= SHT_LOPROC && stype <= SHT_HIPROC) { switch (mach) { + case EM_ARM: + switch (stype) { + case SHT_ARM_EXIDX: return "ARM_EXIDX"; + case SHT_ARM_PREEMPTMAP: return "ARM_PREEMPTMAP"; + case SHT_ARM_ATTRIBUTES: return "ARM_ATTRIBUTES"; + case SHT_ARM_DEBUGOVERLAY: return "ARM_DEBUGOVERLAY"; + case SHT_ARM_OVERLAYSECTION: return "ARM_OVERLAYSECTION"; + } + break; case EM_X86_64: switch (stype) { case SHT_X86_64_UNWIND: return "X86_64_UNWIND"; @@ -2264,9 +2285,10 @@ dump_phdr(struct readelf *re) #define PH_HDR "Type", "Offset", "VirtAddr", "PhysAddr", "FileSiz", \ "MemSiz", "Flg", "Align" -#define PH_CT phdr_type(phdr.p_type), (uintmax_t)phdr.p_offset, \ - (uintmax_t)phdr.p_vaddr, (uintmax_t)phdr.p_paddr, \ - (uintmax_t)phdr.p_filesz, (uintmax_t)phdr.p_memsz, \ +#define PH_CT phdr_type(re->ehdr.e_machine, phdr.p_type), \ + (uintmax_t)phdr.p_offset, (uintmax_t)phdr.p_vaddr, \ + (uintmax_t)phdr.p_paddr, (uintmax_t)phdr.p_filesz, \ + (uintmax_t)phdr.p_memsz, \ phdr.p_flags & PF_R ? 'R' : ' ', \ phdr.p_flags & PF_W ? 'W' : ' ', \ phdr.p_flags & PF_X ? 'E' : ' ', \ @@ -2757,6 +2779,8 @@ dump_rel(struct readelf *re, struct section *s, Elf_Data *d) const char *symname; uint64_t symval; int i, len; + uint32_t type; + uint8_t type2, type3; if (s->link >= re->shnum) return; @@ -2766,8 +2790,8 @@ dump_rel(struct readelf *re, struct section *s, Elf_Data *d) elftc_reloc_type_str(re->ehdr.e_machine, \ ELF32_R_TYPE(r.r_info)), (uintmax_t)symval, symname #define REL_CT64 (uintmax_t)r.r_offset, (uintmax_t)r.r_info, \ - elftc_reloc_type_str(re->ehdr.e_machine, \ - ELF64_R_TYPE(r.r_info)), (uintmax_t)symval, symname + elftc_reloc_type_str(re->ehdr.e_machine, type), \ + (uintmax_t)symval, symname printf("\nRelocation section (%s):\n", s->name); if (re->ec == ELFCLASS32) @@ -2793,12 +2817,35 @@ dump_rel(struct readelf *re, struct section *s, Elf_Data *d) ELF64_R_TYPE(r.r_info)); printf("%8.8jx %8.8jx %-19.19s %8.8jx %s\n", REL_CT32); } else { + type = ELF64_R_TYPE(r.r_info); + if (re->ehdr.e_machine == EM_MIPS) { + type2 = (type >> 8) & 0xFF; + type3 = (type >> 16) & 0xFF; + type = type & 0xFF; + } if (re->options & RE_WW) printf("%16.16jx %16.16jx %-24.24s" " %16.16jx %s\n", REL_CT64); else printf("%12.12jx %12.12jx %-19.19s" " %16.16jx %s\n", REL_CT64); + if (re->ehdr.e_machine == EM_MIPS) { + if (re->options & RE_WW) { + printf("%32s: %s\n", "Type2", + elftc_reloc_type_str(EM_MIPS, + type2)); + printf("%32s: %s\n", "Type3", + elftc_reloc_type_str(EM_MIPS, + type3)); + } else { + printf("%24s: %s\n", "Type2", + elftc_reloc_type_str(EM_MIPS, + type2)); + printf("%24s: %s\n", "Type3", + elftc_reloc_type_str(EM_MIPS, + type3)); + } + } } } @@ -2813,6 +2860,8 @@ dump_rela(struct readelf *re, struct section *s, Elf_Data *d) const char *symname; uint64_t symval; int i, len; + uint32_t type; + uint8_t type2, type3; if (s->link >= re->shnum) return; @@ -2823,8 +2872,8 @@ dump_rela(struct readelf *re, struct section *s, Elf_Data *d) elftc_reloc_type_str(re->ehdr.e_machine, \ ELF32_R_TYPE(r.r_info)), (uintmax_t)symval, symname #define RELA_CT64 (uintmax_t)r.r_offset, (uintmax_t)r.r_info, \ - elftc_reloc_type_str(re->ehdr.e_machine, \ - ELF64_R_TYPE(r.r_info)), (uintmax_t)symval, symname + elftc_reloc_type_str(re->ehdr.e_machine, type), \ + (uintmax_t)symval, symname printf("\nRelocation section with addend (%s):\n", s->name); if (re->ec == ELFCLASS32) @@ -2851,6 +2900,12 @@ dump_rela(struct readelf *re, struct section *s, Elf_Data *d) printf("%8.8jx %8.8jx %-19.19s %8.8jx %s", RELA_CT32); printf(" + %x\n", (uint32_t) r.r_addend); } else { + type = ELF64_R_TYPE(r.r_info); + if (re->ehdr.e_machine == EM_MIPS) { + type2 = (type >> 8) & 0xFF; + type3 = (type >> 16) & 0xFF; + type = type & 0xFF; + } if (re->options & RE_WW) printf("%16.16jx %16.16jx %-24.24s" " %16.16jx %s", RELA_CT64); @@ -2858,6 +2913,23 @@ dump_rela(struct readelf *re, struct section *s, Elf_Data *d) printf("%12.12jx %12.12jx %-19.19s" " %16.16jx %s", RELA_CT64); printf(" + %jx\n", (uintmax_t) r.r_addend); + if (re->ehdr.e_machine == EM_MIPS) { + if (re->options & RE_WW) { + printf("%32s: %s\n", "Type2", + elftc_reloc_type_str(EM_MIPS, + type2)); + printf("%32s: %s\n", "Type3", + elftc_reloc_type_str(EM_MIPS, + type3)); + } else { + printf("%24s: %s\n", "Type2", + elftc_reloc_type_str(EM_MIPS, + type2)); + printf("%24s: %s\n", "Type3", + elftc_reloc_type_str(EM_MIPS, + type3)); + } + } } } From d953ec322213f434585620c7a37b102c130576b3 Mon Sep 17 00:00:00 2001 From: Andrew Turner Date: Wed, 31 Aug 2016 13:58:32 +0000 Subject: [PATCH 61/86] Also handle instruction traps. We might hit these when the page we are executing is being promoted to a superpage. Obtained from: ABT Systems Ltd MFC after: 1 month Sponsored by: The FreeBSD Foundation --- sys/arm64/arm64/trap.c | 1 + 1 file changed, 1 insertion(+) diff --git a/sys/arm64/arm64/trap.c b/sys/arm64/arm64/trap.c index a126d04582d6..b2ca455ea749 100644 --- a/sys/arm64/arm64/trap.c +++ b/sys/arm64/arm64/trap.c @@ -285,6 +285,7 @@ do_el1h_sync(struct trapframe *frame) print_registers(frame); printf(" esr: %.8lx\n", esr); panic("VFP exception in the kernel"); + case EXCP_INSN_ABORT: case EXCP_DATA_ABORT: far = READ_SPECIALREG(far_el1); intr_enable(); From 98150664256fba6a20fe89610c800ea31b08a17f Mon Sep 17 00:00:00 2001 From: Konstantin Belousov Date: Wed, 31 Aug 2016 14:49:58 +0000 Subject: [PATCH 62/86] Make swapoff reliable. The swap_pager_swapoff() function uses trylock for the object lock before pagein, which means that either i/o to md(4) over swap, or intensive page faults over swap pager objects might prevent swapoff() from making any progress. Then the retry < 100 check fails and machine panics. If trylock fails, acquire the object lock in the blockable way and restart the hash bucket walk. Keep retries logic for now. Reported and tested by: pho Reviewed by: alc, markj Sponsored by: The FreeBSD Foundation MFC after: 2 weeks Differential revision: https://reviews.freebsd.org/D7688 --- sys/vm/swap_pager.c | 31 ++++++++++++++++++++++--------- 1 file changed, 22 insertions(+), 9 deletions(-) diff --git a/sys/vm/swap_pager.c b/sys/vm/swap_pager.c index b797f46037cf..dc3d6f2b9849 100644 --- a/sys/vm/swap_pager.c +++ b/sys/vm/swap_pager.c @@ -1688,36 +1688,49 @@ static void swap_pager_swapoff(struct swdevt *sp) { struct swblock *swap; + vm_object_t locked_obj, object; + vm_pindex_t pindex; int i, j, retries; sx_assert(&swdev_syscall_lock, SA_XLOCKED); retries = 0; + locked_obj = NULL; full_rescan: mtx_lock(&swhash_mtx); for (i = 0; i <= swhash_mask; i++) { /* '<=' is correct here */ restart: for (swap = swhash[i]; swap != NULL; swap = swap->swb_hnext) { - vm_object_t object = swap->swb_object; - vm_pindex_t pindex = swap->swb_index; + object = swap->swb_object; + pindex = swap->swb_index; for (j = 0; j < SWAP_META_PAGES; ++j) { - if (swp_pager_isondev(swap->swb_pages[j], sp)) { - /* avoid deadlock */ + if (!swp_pager_isondev(swap->swb_pages[j], sp)) + continue; + if (locked_obj != object) { + if (locked_obj != NULL) + VM_OBJECT_WUNLOCK(locked_obj); + locked_obj = object; if (!VM_OBJECT_TRYWLOCK(object)) { - break; - } else { mtx_unlock(&swhash_mtx); - swp_pager_force_pagein(object, - pindex + j); - VM_OBJECT_WUNLOCK(object); + /* Depends on type-stability. */ + VM_OBJECT_WLOCK(object); mtx_lock(&swhash_mtx); goto restart; } } + MPASS(locked_obj == object); + mtx_unlock(&swhash_mtx); + swp_pager_force_pagein(object, pindex + j); + mtx_lock(&swhash_mtx); + goto restart; } } } mtx_unlock(&swhash_mtx); + if (locked_obj != NULL) { + VM_OBJECT_WUNLOCK(locked_obj); + locked_obj = NULL; + } if (sp->sw_used) { /* * Objects may be locked or paging to the device being From 32286efee1b500fc38dd186f87cc81be1fb03125 Mon Sep 17 00:00:00 2001 From: Warner Losh Date: Wed, 31 Aug 2016 15:32:52 +0000 Subject: [PATCH 63/86] Remove accidentally committed stray comment. Noticed by: dteske@ --- sys/boot/forth/loader.4th | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/sys/boot/forth/loader.4th b/sys/boot/forth/loader.4th index bbacf2b08609..6c2f7b378f6b 100644 --- a/sys/boot/forth/loader.4th +++ b/sys/boot/forth/loader.4th @@ -167,8 +167,7 @@ only forth definitions also support-functions \ \ Overrides support.4th initialization word with one that does \ everything start one does, short of loading the kernel and -\ modules. Returns a flag. Unsure why we don't just have start -\ call this... +\ modules. Returns a flag. : initialize ( -- flag ) s" /boot/defaults/loader.conf" initialize From af98aa6e21690513ecaef602c676755385f0bc9b Mon Sep 17 00:00:00 2001 From: "Andrey A. Chernov" Date: Wed, 31 Aug 2016 15:47:58 +0000 Subject: [PATCH 64/86] Apply the same qsort() usage fix as in r304911 getaddrinfo.c qsort() can't be stabilized with just return(-1) alone. MFC after: 3 days --- lib/libc/net/name6.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/lib/libc/net/name6.c b/lib/libc/net/name6.c index 90b4562823bd..7e52a5150194 100644 --- a/lib/libc/net/name6.c +++ b/lib/libc/net/name6.c @@ -185,6 +185,7 @@ struct hp_order { #define aio_sa aio_un.aiou_sa int aio_matchlen; char *aio_h_addr; + int aio_initial_sequence; }; static struct hostent *_hpcopy(struct hostent *, int *); @@ -711,6 +712,7 @@ _hpreorder(struct hostent *hp) aio[i].aio_dstscope = gai_addr2scopetype(sa); aio[i].aio_dstpolicy = match_addrselectpolicy(sa, &policyhead); set_source(&aio[i], &policyhead); + aio[i].aio_initial_sequence = i; } /* perform sorting. */ @@ -1045,6 +1047,23 @@ comp_dst(const void *arg1, const void *arg2) } /* Rule 10: Otherwise, leave the order unchanged. */ + + /* + * Note that qsort is unstable; so, we can't return zero and + * expect the order to be unchanged. + * That also means we can't depend on the current position of + * dst2 being after dst1. We must enforce the initial order + * with an explicit compare on the original position. + * The qsort specification requires that "When the same objects + * (consisting of width bytes, irrespective of their current + * positions in the array) are passed more than once to the + * comparison function, the results shall be consistent with one + * another." + * In other words, If A < B, then we must also return B > A. + */ + if (dst2->aio_initial_sequence < dst1->aio_initial_sequence) + return(1); + return(-1); } From cc14fb4c2eb866be196115eaf040caebe13dbc0f Mon Sep 17 00:00:00 2001 From: Jared McNeill Date: Wed, 31 Aug 2016 16:56:54 +0000 Subject: [PATCH 65/86] Add Allwinner A64 (sun50i) and Pine64 dts files. Reviewed by: andrew, imp, manu, wca Differential Revision: https://reviews.freebsd.org/D7169 --- sys/boot/fdt/dts/Makefile | 2 +- sys/boot/fdt/dts/arm64/Makefile | 7 + sys/boot/fdt/dts/arm64/a64.dtsi | 151 ++++ sys/boot/fdt/dts/arm64/pine64_plus.dts | 89 +++ .../dts/arm64/sun50i-a64-pine64-common.dtsi | 82 +++ .../fdt/dts/arm64/sun50i-a64-pine64-plus.dts | 73 ++ sys/boot/fdt/dts/arm64/sun50i-a64-pine64.dts | 72 ++ sys/boot/fdt/dts/arm64/sun50i-a64.dtsi | 661 ++++++++++++++++++ 8 files changed, 1136 insertions(+), 1 deletion(-) create mode 100644 sys/boot/fdt/dts/arm64/Makefile create mode 100644 sys/boot/fdt/dts/arm64/a64.dtsi create mode 100644 sys/boot/fdt/dts/arm64/pine64_plus.dts create mode 100644 sys/boot/fdt/dts/arm64/sun50i-a64-pine64-common.dtsi create mode 100644 sys/boot/fdt/dts/arm64/sun50i-a64-pine64-plus.dts create mode 100644 sys/boot/fdt/dts/arm64/sun50i-a64-pine64.dts create mode 100644 sys/boot/fdt/dts/arm64/sun50i-a64.dtsi diff --git a/sys/boot/fdt/dts/Makefile b/sys/boot/fdt/dts/Makefile index 66f65a712fe4..9025c04ba4a6 100644 --- a/sys/boot/fdt/dts/Makefile +++ b/sys/boot/fdt/dts/Makefile @@ -1,5 +1,5 @@ # $FreeBSD$ -SUBDIR=arm mips powerpc +SUBDIR=arm arm64 mips powerpc .include diff --git a/sys/boot/fdt/dts/arm64/Makefile b/sys/boot/fdt/dts/arm64/Makefile new file mode 100644 index 000000000000..03d156d94770 --- /dev/null +++ b/sys/boot/fdt/dts/arm64/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +DTS!=ls *.dts + +all: test-dts + +.include diff --git a/sys/boot/fdt/dts/arm64/a64.dtsi b/sys/boot/fdt/dts/arm64/a64.dtsi new file mode 100644 index 000000000000..6735ff5f6fc2 --- /dev/null +++ b/sys/boot/fdt/dts/arm64/a64.dtsi @@ -0,0 +1,151 @@ +/*- + * Copyright (c) 2016 Jared McNeill + * 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. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 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. + * + * $FreeBSD$ + */ + +/ { + clocks { + pll_hsic: clk@01c20044 { + #clock-cells = <0>; + compatible = "allwinner,sun50i-a64-pllhsic-clk"; + reg = <0x01c20044 0x4>; + clocks = <&osc24M>; + clock-output-names = "pll_hsic"; + }; + + usb_clk: clk@01c200cc { + #clock-cells = <1>; + #reset-cells = <1>; + compatible = "allwinner,sun8i-a83t-usb-clk"; + reg = <0x01c200cc 0x4>; + clocks = <&osc24M>, <&pll_hsic>; + clock-indices = <8>, <9>, + <10>, <11>, + <16>, <17>; + clock-output-names = "usb_phy0", "usb_phy1", + "usb_hsic_pll", "usb_hsic_12m", + "usb_otg_ohci", "usb_ohci0"; + }; + }; + + soc { + watchdog: watchdog@01c20ca0 { + compatible = "allwinner,sun6i-a31-wdt"; + reg = <0x01c20ca0 0x20>; + interrupts = ; + clocks = <&osc24M>; + }; + + nmi_intc: interrupt-controller@01f00c0c { + compatible = "allwinner,sun6i-a31-sc-nmi"; + interrupt-controller; + #interrupt-cells = <2>; + reg = <0x01f00c0c 0x38>; + interrupts = ; + }; + + r_rsb: i2c@01f03400 { + compatible = "allwinner,sun8i-a23-rsb"; + reg = <0x01f03400 0x400>; + interrupts = ; + clock-frequency = <3000000>; + pinctrl-names = "default"; + pinctrl-0 = <&r_rsb_pins>; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + usbphy: phy@01c19400 { + compatible = "allwinner,sun50i-a64-usb-phy"; + reg = <0x01c19400 0x24 0x01c1a800 0x4 0x01c1b800 0x4>; + reg-names = "phy_ctrl", "pmu1", "pmu2"; + clocks = <&usb_clk 8>, + <&usb_clk 9>; + clock-names = "usb0_phy", + "usb1_phy"; + resets = <&usb_clk 0>, + <&usb_clk 1>; + reset-names = "usb0_reset", + "usb1_reset"; + status = "disabled"; + #phy-cells = <1>; + }; + + ohci0: usb@01c1a400 { + compatible = "generic-ohci"; + reg = <0x01c1a400 0x100>; + interrupts = ; + clocks = <&bus_gates 28>, <&usb_clk 16>, <&usb_clk 17>; + resets = <&ahb_rst 28>; + phys = <&usbphy 1>; + phy-names = "usb"; + status = "disabled"; + }; + + ehci0: usb@01c1a000 { + compatible = "allwinner,sun8i-a83t-ehci", "generic-ehci"; + reg = <0x01c1a000 0x100>; + interrupts = ; + clocks = <&bus_gates 24>; + resets = <&ahb_rst 24>; + phys = <&usbphy 1>; + phy-names = "usb"; + status = "disabled"; + }; + + ohci1: usb@01c1b400 { + compatible = "generic-ohci"; + reg = <0x01c1b400 0x100>; + interrupts = ; + clocks = <&bus_gates 29>, <&usb_clk 16>, <&usb_clk 17>; + resets = <&ahb_rst 29>; + phys = <&usbphy 2>; + phy-names = "usb"; + status = "disabled"; + }; + + ehci1: usb@01c1b000 { + compatible = "allwinner,sun8i-a83t-ehci", "generic-ehci"; + reg = <0x01c1b000 0x100>; + interrupts = ; + clocks = <&bus_gates 25>; + resets = <&ahb_rst 25>; + phys = <&usbphy 2>; + phy-names = "usb"; + status = "disabled"; + }; + }; +}; + +&pio { + r_rsb_pins: r_rsb { + allwinner,pins = "PL0", "PL1"; + allwinner,function = "s_rsb"; + allwinner,drive = ; + allwinner,pull = ; + }; +}; diff --git a/sys/boot/fdt/dts/arm64/pine64_plus.dts b/sys/boot/fdt/dts/arm64/pine64_plus.dts new file mode 100644 index 000000000000..3cc54c125348 --- /dev/null +++ b/sys/boot/fdt/dts/arm64/pine64_plus.dts @@ -0,0 +1,89 @@ +/*- + * Copyright (c) 2016 Jared McNeill + * 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. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 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. + * + * $FreeBSD$ + */ + +#include "sun50i-a64-pine64-plus.dts" +#include "a64.dtsi" + +#include + +&pio { + emac_phy_reset_pin_pine64_plus: emac_phy_reset_pin@0 { + allwinner,pins = "PD14"; + allwinner,function = "gpio_out"; + allwinner,drive = ; + allwinner,pull = ; + }; +}; + +&emac { + pinctrl-names = "default"; + pinctrl-0 = <&rgmii_pins>, <&emac_phy_reset_pin_pine64_plus>; + phy-supply = <®_dc1dc>; + allwinner,reset-gpio = <&pio 3 14 GPIO_ACTIVE_HIGH>; + allwinner,reset-active-low; + allwinner,reset-delays-us = <0 10000 30000>; +}; + +&r_rsb { + status = "okay"; + + axp81x: pmic@3a3 { + compatible = "x-powers,axp813"; + reg = <0x3a3>; + interrupt-parent = <&nmi_intc>; + interrupts = <0 IRQ_TYPE_LEVEL_LOW>; + gpio-controller; + #gpio-cells = <1>; + + regulators { + reg_dc1dc: dc1sw { + regulator-name = "dc1sw"; + }; + }; + }; +}; + +&usbphy { + status = "okay"; +}; + +&ehci0 { + status = "okay"; +}; + +&ohci0 { + status = "okay"; +}; + +&ehci1 { + status = "okay"; +}; + +&ohci1 { + status = "okay"; +}; diff --git a/sys/boot/fdt/dts/arm64/sun50i-a64-pine64-common.dtsi b/sys/boot/fdt/dts/arm64/sun50i-a64-pine64-common.dtsi new file mode 100644 index 000000000000..d4de80aedcba --- /dev/null +++ b/sys/boot/fdt/dts/arm64/sun50i-a64-pine64-common.dtsi @@ -0,0 +1,82 @@ +/* + * Copyright (c) 2016 ARM Ltd. + * + * This file is dual-licensed: you can use it either under the terms + * of the GPL or the X11 license, at your option. Note that this dual + * licensing only applies to this file, and not this project as a + * whole. + * + * a) This library 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 library 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. + * + * Or, alternatively, + * + * b) 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", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * $FreeBSD$ + */ + +#include "sun50i-a64.dtsi" + +/ { + + aliases { + serial0 = &uart0; + }; + + soc { + reg_vcc3v3: vcc3v3 { + compatible = "regulator-fixed"; + regulator-name = "vcc3v3"; + regulator-min-microvolt = <3300000>; + regulator-max-microvolt = <3300000>; + }; + }; +}; + +&mmc0 { + pinctrl-names = "default"; + pinctrl-0 = <&mmc0_pins>, <&mmc0_default_cd_pin>; + vmmc-supply = <®_vcc3v3>; + cd-gpios = <&pio 5 6 0>; + cd-inverted; + status = "okay"; +}; + +&uart0 { + pinctrl-names = "default"; + pinctrl-0 = <&uart0_pins_a>; + status = "okay"; +}; + +&i2c1 { + pinctrl-names = "default"; + pinctrl-0 = <&i2c1_pins>; + status = "okay"; +}; diff --git a/sys/boot/fdt/dts/arm64/sun50i-a64-pine64-plus.dts b/sys/boot/fdt/dts/arm64/sun50i-a64-pine64-plus.dts new file mode 100644 index 000000000000..1b9eefaa4757 --- /dev/null +++ b/sys/boot/fdt/dts/arm64/sun50i-a64-pine64-plus.dts @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2016 ARM Ltd. + * + * This file is dual-licensed: you can use it either under the terms + * of the GPL or the X11 license, at your option. Note that this dual + * licensing only applies to this file, and not this project as a + * whole. + * + * a) This library 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 library 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. + * + * Or, alternatively, + * + * b) 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", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * $FreeBSD$ + */ + +/dts-v1/; + +#include "sun50i-a64-pine64-common.dtsi" + +/ { + model = "Pine64+"; + compatible = "pine64,pine64-plus", "allwinner,sun50i-a64"; + + chosen { + stdout-path = "serial0:115200n8"; + }; + + /* There is a model with 2GB of DRAM, but U-Boot fixes this for us. */ + memory { + reg = <0x40000000 0x40000000>; + }; +}; + +&emac { + pinctrl-names = "default"; + pinctrl-0 = <&rgmii_pins>; + phy-mode = "rgmii"; + phy = <&phy1>; + status = "okay"; + + phy1: ethernet-phy@1 { + reg = <1>; + }; +}; diff --git a/sys/boot/fdt/dts/arm64/sun50i-a64-pine64.dts b/sys/boot/fdt/dts/arm64/sun50i-a64-pine64.dts new file mode 100644 index 000000000000..4ec68bcf593c --- /dev/null +++ b/sys/boot/fdt/dts/arm64/sun50i-a64-pine64.dts @@ -0,0 +1,72 @@ +/* + * Copyright (c) 2016 ARM Ltd. + * + * This file is dual-licensed: you can use it either under the terms + * of the GPL or the X11 license, at your option. Note that this dual + * licensing only applies to this file, and not this project as a + * whole. + * + * a) This library 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 library 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. + * + * Or, alternatively, + * + * b) 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", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * $FreeBSD$ + */ + +/dts-v1/; + +#include "sun50i-a64-pine64-common.dtsi" + +/ { + model = "Pine64"; + compatible = "pine64,pine64", "allwinner,sun50i-a64"; + + chosen { + stdout-path = "serial0:115200n8"; + }; + + memory { + reg = <0x40000000 0x20000000>; + }; +}; + +&emac { + pinctrl-names = "default"; + pinctrl-0 = <&rmii_pins>; + phy-mode = "rmii"; + phy = <&phy1>; + status = "okay"; + + phy1: ethernet-phy@1 { + reg = <1>; + }; +}; diff --git a/sys/boot/fdt/dts/arm64/sun50i-a64.dtsi b/sys/boot/fdt/dts/arm64/sun50i-a64.dtsi new file mode 100644 index 000000000000..fe187575e5ac --- /dev/null +++ b/sys/boot/fdt/dts/arm64/sun50i-a64.dtsi @@ -0,0 +1,661 @@ +/* + * Copyright (C) 2016 ARM Ltd. + * based on the Allwinner H3 dtsi: + * Copyright (C) 2015 Jens Kuske + * + * This file is dual-licensed: you can use it either under the terms + * of the GPL or the X11 license, at your option. Note that this dual + * licensing only applies to this file, and not this project as a + * whole. + * + * a) This file 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 file 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. + * + * Or, alternatively, + * + * b) 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", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * $FreeBSD$ + */ + +#include +#include + +/ { + interrupt-parent = <&gic>; + #address-cells = <1>; + #size-cells = <1>; + + cpus { + #address-cells = <1>; + #size-cells = <0>; + + cpu@0 { + compatible = "arm,cortex-a53", "arm,armv8"; + device_type = "cpu"; + reg = <0>; + enable-method = "psci"; + }; + + cpu@1 { + compatible = "arm,cortex-a53", "arm,armv8"; + device_type = "cpu"; + reg = <1>; + enable-method = "psci"; + }; + + cpu@2 { + compatible = "arm,cortex-a53", "arm,armv8"; + device_type = "cpu"; + reg = <2>; + enable-method = "psci"; + }; + + cpu@3 { + compatible = "arm,cortex-a53", "arm,armv8"; + device_type = "cpu"; + reg = <3>; + enable-method = "psci"; + }; + }; + + psci { + compatible = "arm,psci-0.2"; + method = "smc"; + }; + + memory { + device_type = "memory"; + reg = <0x40000000 0>; + }; + + gic: interrupt-controller@1c81000 { + compatible = "arm,gic-400"; + interrupt-controller; + #interrupt-cells = <3>; + #address-cells = <0>; + + reg = <0x01c81000 0x1000>, + <0x01c82000 0x2000>, + <0x01c84000 0x2000>, + <0x01c86000 0x2000>; + interrupts = ; + }; + + timer { + compatible = "arm,armv8-timer"; + interrupts = , + , + , + ; + }; + + clocks { + #address-cells = <1>; + #size-cells = <1>; + ranges; + + osc24M: osc24M_clk { + #clock-cells = <0>; + compatible = "fixed-clock"; + clock-frequency = <24000000>; + clock-output-names = "osc24M"; + }; + + osc32k: osc32k_clk { + #clock-cells = <0>; + compatible = "fixed-clock"; + clock-frequency = <32768>; + clock-output-names = "osc32k"; + }; + + cpux: clk@1c20000 { + #clock-cells = <0>; + compatible = "allwinner,sun8i-a23-pll1-clk"; + reg = <0x01c20000 0x4>; + clocks = <&osc24M>; + clock-output-names = "cpux"; + }; + + periph0: clk@1c20028 { + #clock-cells = <1>; + compatible = "allwinner,sun6i-a31-pll6-clk"; + reg = <0x01c20028 0x4>; + clocks = <&osc24M>; + clock-output-names = "periph0", "periph0x2"; + }; + + periph0d2: periph0d2_clk { + #clock-cells = <0>; + compatible = "fixed-factor-clock"; + clock-div = <2>; + clock-mult = <1>; + clocks = <&periph0 0>; + clock-output-names = "periph0d2"; + }; + + periph1: clk@1c2002c { + #clock-cells = <1>; + compatible = "allwinner,sun6i-a31-pll6-clk"; + reg = <0x01c2002c 0x4>; + clocks = <&osc24M>; + clock-output-names = "periph1", "periph1x2"; + }; + + cpu: cpu_clk@1c20050 { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-cpu-clk"; + reg = <0x01c20050 0x4>; + clocks = <&osc32k>, <&osc24M>, <&cpux>, <&cpux>; + clock-output-names = "cpu"; + critical-clocks = <0>; + }; + + axi: axi_clk@1c20050 { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-axi-clk"; + reg = <0x01c20050 0x4>; + clocks = <&cpu>; + clock-output-names = "axi"; + }; + + ahb1: ahb1_clk@1c20054 { + #clock-cells = <0>; + compatible = "allwinner,sun6i-a31-ahb1-clk"; + reg = <0x01c20054 0x4>; + clocks = <&osc32k>, <&osc24M>, <&axi>, <&periph0 0>; + clock-output-names = "ahb1"; + }; + + ahb2: ahb2_clk@1c2005c { + #clock-cells = <0>; + compatible = "allwinner,sun8i-h3-ahb2-clk"; + reg = <0x01c2005c 0x4>; + clocks = <&ahb1>, <&periph0d2>; + clock-output-names = "ahb2"; + }; + + apb1: apb1_clk@1c20054 { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-apb0-clk"; + reg = <0x01c20054 0x4>; + clocks = <&ahb1>; + clock-output-names = "apb1"; + }; + + apb2: apb2_clk@1c20058 { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-apb1-clk"; + reg = <0x01c20058 0x4>; + clocks = <&osc32k>, <&osc24M>, + <&periph0 1>, <&periph0 1>; + clock-output-names = "apb2"; + }; + + bus_gates: bus_gates_clk@1c20060 { + #clock-cells = <1>; + compatible = "allwinner,sun50i-a64-bus-gates-clk", + "allwinner,sunxi-multi-bus-gates-clk"; + reg = <0x01c20060 0x14>; + ahb1_parent { + clocks = <&ahb1>; + clock-indices = <1>, <5>, + <6>, <8>, + <9>, <10>, + <13>, <14>, + <18>, <19>, + <20>, <21>, + <23>, <24>, + <25>, <28>, + <32>, <35>, + <36>, <37>, + <40>, <43>, + <44>, <52>, + <53>, <54>, + <135>; + clock-output-names = "bus_mipidsi", "bus_ce", + "bus_dma", "bus_mmc0", + "bus_mmc1", "bus_mmc2", + "bus_nand", "bus_sdram", + "bus_ts", "bus_hstimer", + "bus_spi0", "bus_spi1", + "bus_otg", "bus_otg_ehci0", + "bus_ehci0", "bus_otg_ohci0", + "bus_ve", "bus_lcd0", + "bus_lcd1", "bus_deint", + "bus_csi", "bus_hdmi", + "bus_de", "bus_gpu", + "bus_msgbox", "bus_spinlock", + "bus_dbg"; + }; + ahb2_parent { + clocks = <&ahb2>; + clock-indices = <17>, <29>; + clock-output-names = "bus_gmac", "bus_ohci0"; + }; + apb1_parent { + clocks = <&apb1>; + clock-indices = <64>, <65>, + <69>, <72>, + <76>, <77>, + <78>; + clock-output-names = "bus_codec", "bus_spdif", + "bus_pio", "bus_ths", + "bus_i2s0", "bus_i2s1", + "bus_i2s2"; + }; + abp2_parent { + clocks = <&apb2>; + clock-indices = <96>, <97>, + <98>, <101>, + <112>, <113>, + <114>, <115>, + <116>; + clock-output-names = "bus_i2c0", "bus_i2c1", + "bus_i2c2", "bus_scr", + "bus_uart0", "bus_uart1", + "bus_uart2", "bus_uart3", + "bus_uart4"; + }; + }; + + mmc0_clk: mmc0_clk@1c20088 { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-mod0-clk"; + reg = <0x01c20088 0x4>; + clocks = <&osc24M>, <&periph0 1>, <&periph1 1>; + clock-output-names = "mmc0"; + }; + + mmc1_clk: mmc1_clk@1c2008c { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-mod0-clk"; + reg = <0x01c2008c 0x4>; + clocks = <&osc24M>, <&periph0 1>, <&periph1 1>; + clock-output-names = "mmc1"; + }; + + mmc2_clk: mmc2_clk@1c20090 { + #clock-cells = <0>; + compatible = "allwinner,sun4i-a10-mod0-clk"; + reg = <0x01c20090 0x4>; + clocks = <&osc24M>, <&periph0 1>, <&periph1 1>; + clock-output-names = "mmc2"; + }; + }; + + soc { + compatible = "simple-bus"; + #address-cells = <1>; + #size-cells = <1>; + ranges; + + mmc0: mmc@1c0f000 { + compatible = "allwinner,sun50i-a64-mmc", + "allwinner,sun5i-a13-mmc"; + reg = <0x01c0f000 0x1000>; + clocks = <&bus_gates 8>, <&mmc0_clk>, + <&mmc0_clk>, <&mmc0_clk>; + clock-names = "ahb", "mmc", + "output", "sample"; + resets = <&ahb_rst 8>; + reset-names = "ahb"; + interrupts = ; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + mmc1: mmc@1c10000 { + compatible = "allwinner,sun50i-a64-mmc", + "allwinner,sun5i-a13-mmc"; + reg = <0x01c10000 0x1000>; + clocks = <&bus_gates 9>, <&mmc1_clk>, + <&mmc1_clk>, <&mmc1_clk>; + clock-names = "ahb", "mmc", + "output", "sample"; + resets = <&ahb_rst 9>; + reset-names = "ahb"; + interrupts = ; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + mmc2: mmc@1c11000 { + compatible = "allwinner,sun50i-a64-mmc", + "allwinner,sun5i-a13-mmc"; + reg = <0x01c11000 0x1000>; + clocks = <&bus_gates 10>, <&mmc2_clk>, + <&mmc2_clk>, <&mmc2_clk>; + clock-names = "ahb", "mmc", + "output", "sample"; + resets = <&ahb_rst 10>; + reset-names = "ahb"; + interrupts = ; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + pio: pinctrl@1c20800 { + compatible = "allwinner,sun50i-a64-pinctrl"; + reg = <0x01c20800 0x400>; + interrupts = , + , + ; + clocks = <&bus_gates 69>; + gpio-controller; + #gpio-cells = <3>; + interrupt-controller; + #interrupt-cells = <2>; + + uart0_pins_a: uart0@0 { + allwinner,pins = "PB8", "PB9"; + allwinner,function = "uart0"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart0_pins_b: uart0@1 { + allwinner,pins = "PF2", "PF3"; + allwinner,function = "uart0"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart1_2pins: uart1_2@0 { + allwinner,pins = "PG6", "PG7"; + allwinner,function = "uart1"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart1_4pins: uart1_4@0 { + allwinner,pins = "PG6", "PG7", "PG8", "PG9"; + allwinner,function = "uart1"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart2_2pins: uart2_2@0 { + allwinner,pins = "PB0", "PB1"; + allwinner,function = "uart2"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart2_4pins: uart2_4@0 { + allwinner,pins = "PB0", "PB1", "PB2", "PB3"; + allwinner,function = "uart2"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart3_pins_a: uart3@0 { + allwinner,pins = "PD0", "PD1"; + allwinner,function = "uart3"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart3_2pins_b: uart3_2@1 { + allwinner,pins = "PH4", "PH5"; + allwinner,function = "uart3"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart3_4pins_b: uart3_4@1 { + allwinner,pins = "PH4", "PH5", "PH6", "PH7"; + allwinner,function = "uart3"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart4_2pins: uart4_2@0 { + allwinner,pins = "PD2", "PD3"; + allwinner,function = "uart4"; + allwinner,drive = ; + allwinner,pull = ; + }; + + uart4_4pins: uart4_4@0 { + allwinner,pins = "PD2", "PD3", "PD4", "PD5"; + allwinner,function = "uart4"; + allwinner,drive = ; + allwinner,pull = ; + }; + + mmc0_pins: mmc0@0 { + allwinner,pins = "PF0", "PF1", "PF2", "PF3", + "PF4", "PF5"; + allwinner,function = "mmc0"; + allwinner,drive = ; + allwinner,pull = ; + }; + + mmc0_default_cd_pin: mmc0_cd_pin@0 { + allwinner,pins = "PF6"; + allwinner,function = "gpio_in"; + allwinner,drive = ; + allwinner,pull = ; + }; + + mmc1_pins: mmc1@0 { + allwinner,pins = "PG0", "PG1", "PG2", "PG3", + "PG4", "PG5"; + allwinner,function = "mmc1"; + allwinner,drive = ; + allwinner,pull = ; + }; + + mmc2_pins: mmc2@0 { + allwinner,pins = "PC1", "PC5", "PC6", "PC8", + "PC9", "PC10"; + allwinner,function = "mmc2"; + allwinner,drive = ; + allwinner,pull = ; + }; + + i2c0_pins: i2c0_pins { + allwinner,pins = "PH0", "PH1"; + allwinner,function = "i2c0"; + allwinner,drive = ; + allwinner,pull = ; + }; + + i2c1_pins: i2c1_pins { + allwinner,pins = "PH2", "PH3"; + allwinner,function = "i2c1"; + allwinner,drive = ; + allwinner,pull = ; + }; + + i2c2_pins: i2c2_pins { + allwinner,pins = "PE14", "PE15"; + allwinner,function = "i2c2"; + allwinner,drive = ; + allwinner,pull = ; + }; + + rmii_pins: rmii_pins { + allwinner,pins = "PD10", "PD11", "PD13", "PD14", + "PD17", "PD18", "PD19", "PD20", + "PD22", "PD23"; + allwinner,function = "emac"; + allwinner,drive = ; + allwinner,pull = ; + }; + + rgmii_pins: rgmii_pins { + allwinner,pins = "PD8", "PD9", "PD10", "PD11", + "PD12", "PD13", "PD15", + "PD16", "PD17", "PD18", "PD19", + "PD20", "PD21", "PD22", "PD23"; + allwinner,function = "emac"; + allwinner,drive = ; + allwinner,pull = ; + }; + }; + + ahb_rst: reset@1c202c0 { + #reset-cells = <1>; + compatible = "allwinner,sun6i-a31-clock-reset"; + reg = <0x01c202c0 0xc>; + }; + + apb1_rst: reset@1c202d0 { + #reset-cells = <1>; + compatible = "allwinner,sun6i-a31-clock-reset"; + reg = <0x01c202d0 0x4>; + }; + + apb2_rst: reset@1c202d8 { + #reset-cells = <1>; + compatible = "allwinner,sun6i-a31-clock-reset"; + reg = <0x01c202d8 0x4>; + }; + + uart0: serial@1c28000 { + compatible = "snps,dw-apb-uart"; + reg = <0x01c28000 0x400>; + interrupts = ; + reg-shift = <2>; + reg-io-width = <4>; + clocks = <&bus_gates 112>; + resets = <&apb2_rst 16>; + status = "disabled"; + }; + + uart1: serial@1c28400 { + compatible = "snps,dw-apb-uart"; + reg = <0x01c28400 0x400>; + interrupts = ; + reg-shift = <2>; + reg-io-width = <4>; + clocks = <&bus_gates 113>; + resets = <&apb2_rst 17>; + status = "disabled"; + }; + + uart2: serial@1c28800 { + compatible = "snps,dw-apb-uart"; + reg = <0x01c28800 0x400>; + interrupts = ; + reg-shift = <2>; + reg-io-width = <4>; + clocks = <&bus_gates 114>; + resets = <&apb2_rst 18>; + status = "disabled"; + }; + + uart3: serial@1c28c00 { + compatible = "snps,dw-apb-uart"; + reg = <0x01c28c00 0x400>; + interrupts = ; + reg-shift = <2>; + reg-io-width = <4>; + clocks = <&bus_gates 115>; + resets = <&apb2_rst 19>; + status = "disabled"; + }; + + uart4: serial@1c29000 { + compatible = "snps,dw-apb-uart"; + reg = <0x01c29000 0x400>; + interrupts = ; + reg-shift = <2>; + reg-io-width = <4>; + clocks = <&bus_gates 116>; + resets = <&apb2_rst 20>; + status = "disabled"; + }; + + rtc: rtc@1f00000 { + compatible = "allwinner,sun6i-a31-rtc"; + reg = <0x01f00000 0x54>; + interrupts = , + ; + }; + + i2c0: i2c@1c2ac00 { + compatible = "allwinner,sun6i-a31-i2c"; + reg = <0x01c2ac00 0x400>; + interrupts = ; + clocks = <&bus_gates 96>; + resets = <&apb2_rst 0>; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + i2c1: i2c@1c2b000 { + compatible = "allwinner,sun6i-a31-i2c"; + reg = <0x01c2b000 0x400>; + interrupts = ; + clocks = <&bus_gates 97>; + resets = <&apb2_rst 1>; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + i2c2: i2c@1c2b400 { + compatible = "allwinner,sun6i-a31-i2c"; + reg = <0x01c2b400 0x400>; + interrupts = ; + clocks = <&bus_gates 98>; + resets = <&apb2_rst 2>; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + + emac: ethernet@1c30000 { + compatible = "allwinner,sun50i-a64-emac", + "allwinner,sun8i-h3-emac"; + reg = <0x01c30000 0x100>, <0x01c00030 0x4>; + reg-names = "emac", "syscon"; + interrupts = ; + resets = <&ahb_rst 17>; + reset-names = "ahb"; + clocks = <&bus_gates 17>; + clock-names = "ahb"; + status = "disabled"; + #address-cells = <1>; + #size-cells = <0>; + }; + }; +}; From 61bd7ae0ecbaeb41faaab7280703af2ac2af7e9a Mon Sep 17 00:00:00 2001 From: Allan Jude Date: Wed, 31 Aug 2016 17:52:11 +0000 Subject: [PATCH 66/86] Eliminate unnecessary loop in _cap_check() Calling cap_rights_contains() several times with the same inputs is not going to produce a different output. The variable being iterated, i, is never used inside the for loop. The loop is actually done in cap_rights_contains() Submitted by: Ryan Moeller Reviewed by: oshogbo, ed MFC after: 1 month Differential Revision: https://reviews.freebsd.org/D7369 --- sys/kern/sys_capability.c | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/sys/kern/sys_capability.c b/sys/kern/sys_capability.c index e87f0b1445ac..b8ac5dd315d9 100644 --- a/sys/kern/sys_capability.c +++ b/sys/kern/sys_capability.c @@ -150,16 +150,13 @@ static inline int _cap_check(const cap_rights_t *havep, const cap_rights_t *needp, enum ktr_cap_fail_type type) { - int i; - for (i = 0; i < nitems(havep->cr_rights); i++) { - if (!cap_rights_contains(havep, needp)) { + if (!cap_rights_contains(havep, needp)) { #ifdef KTRACE - if (KTRPOINT(curthread, KTR_CAPFAIL)) - ktrcapfail(type, needp, havep); + if (KTRPOINT(curthread, KTR_CAPFAIL)) + ktrcapfail(type, needp, havep); #endif - return (ENOTCAPABLE); - } + return (ENOTCAPABLE); } return (0); } From 246ef54f1560932d0f7ef10a89cab3a521a1c8c2 Mon Sep 17 00:00:00 2001 From: Conrad Meyer Date: Wed, 31 Aug 2016 18:10:41 +0000 Subject: [PATCH 67/86] df(1): Allow duplicate -l flags gracefully Rather than producing a misleading error message when duplicate -l flags are provided to df(1), simply ignore extra flags and proceed as if only one was specified. This seems most reasonable given the usage for -l: -l Only display information about locally-mounted file systems. l and t flags still conflict, as before. PR: 208169 Reported by: by at reorigin.com Reviewed by: allanjude --- bin/df/df.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/bin/df/df.c b/bin/df/df.c index f8d43bf95f59..1bcf40d21118 100644 --- a/bin/df/df.c +++ b/bin/df/df.c @@ -166,6 +166,9 @@ main(int argc, char *argv[]) hflag = 0; break; case 'l': + /* Ignore duplicate -l */ + if (lflag) + break; if (vfslist != NULL) xo_errx(1, "-l and -t are mutually exclusive."); vfslist = makevfslist(makenetvfslist()); From ca380195ab2bc34160fbbcff22090ba417ddb8ff Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Wed, 31 Aug 2016 18:33:15 +0000 Subject: [PATCH 68/86] Allow getdtablesize in capability mode getdtablesize is "trivial global state" and is similar to getrlimit(RLIMIT_NOFILE), so should be permitted in capability mode. Reviewed by: oshogbo MFC after: 1 week Sponsored by: The FreeBSD Foundation Differential Revision: https://reviews.freebsd.org/D7719 --- sys/kern/capabilities.conf | 1 + 1 file changed, 1 insertion(+) diff --git a/sys/kern/capabilities.conf b/sys/kern/capabilities.conf index 51cdafdd2cc1..37a03f620de2 100644 --- a/sys/kern/capabilities.conf +++ b/sys/kern/capabilities.conf @@ -248,6 +248,7 @@ getdirentries ## Allow querying certain trivial global state. ## getdomainname +getdtablesize ## ## Allow querying current process credential state. From eff30e9149f1cc6af14623d1923cb062887093a5 Mon Sep 17 00:00:00 2001 From: Luiz Otavio O Souza Date: Wed, 31 Aug 2016 18:35:41 +0000 Subject: [PATCH 69/86] Fix the build. Works better when the file with the #define is actually included... --- sys/arm/ti/am335x/am335x_prcm.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sys/arm/ti/am335x/am335x_prcm.c b/sys/arm/ti/am335x/am335x_prcm.c index 6da5dc85b665..f7934328e354 100644 --- a/sys/arm/ti/am335x/am335x_prcm.c +++ b/sys/arm/ti/am335x/am335x_prcm.c @@ -52,6 +52,8 @@ __FBSDID("$FreeBSD$"); #include +#include "am335x_scm.h" + #define CM_PER 0 #define CM_PER_L4LS_CLKSTCTRL (CM_PER + 0x000) #define CM_PER_L3S_CLKSTCTRL (CM_PER + 0x004) From bce38b9f353d43db86ef77438e1b874173ad12c7 Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Wed, 31 Aug 2016 18:37:51 +0000 Subject: [PATCH 70/86] Regnerate after r305140, getdtablesize in capability mode Sponsored by: The FreeBSD Foundation --- sys/kern/init_sysent.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sys/kern/init_sysent.c b/sys/kern/init_sysent.c index 6be4769cfb27..907d3ea6cadc 100644 --- a/sys/kern/init_sysent.c +++ b/sys/kern/init_sysent.c @@ -135,7 +135,7 @@ struct sysent sysent[] = { { AS(getitimer_args), (sy_call_t *)sys_getitimer, AUE_GETITIMER, NULL, 0, 0, SYF_CAPENABLED, SY_THR_STATIC }, /* 86 = getitimer */ { compat(AS(gethostname_args),gethostname), AUE_SYSCTL, NULL, 0, 0, SYF_CAPENABLED, SY_THR_STATIC }, /* 87 = old gethostname */ { compat(AS(sethostname_args),sethostname), AUE_SYSCTL, NULL, 0, 0, 0, SY_THR_STATIC }, /* 88 = old sethostname */ - { 0, (sy_call_t *)sys_getdtablesize, AUE_GETDTABLESIZE, NULL, 0, 0, 0, SY_THR_STATIC }, /* 89 = getdtablesize */ + { 0, (sy_call_t *)sys_getdtablesize, AUE_GETDTABLESIZE, NULL, 0, 0, SYF_CAPENABLED, SY_THR_STATIC }, /* 89 = getdtablesize */ { AS(dup2_args), (sy_call_t *)sys_dup2, AUE_DUP2, NULL, 0, 0, SYF_CAPENABLED, SY_THR_STATIC }, /* 90 = dup2 */ { 0, (sy_call_t *)nosys, AUE_NULL, NULL, 0, 0, 0, SY_THR_ABSENT }, /* 91 = getdopt */ { AS(fcntl_args), (sy_call_t *)sys_fcntl, AUE_FCNTL, NULL, 0, 0, SYF_CAPENABLED, SY_THR_STATIC }, /* 92 = fcntl */ From e1ec67bbc99a3c01ed02f565483cef06ccb11166 Mon Sep 17 00:00:00 2001 From: "Andrey A. Chernov" Date: Wed, 31 Aug 2016 18:49:50 +0000 Subject: [PATCH 71/86] 'addrlen' does not matter when we need to find the first non-zero bit in the byte from the left and 'addrlen' already counted in 'lim'. PR: 212121 Submitted by: Herbie.Robinson@stratus.com MFC after: 7 days --- lib/libc/net/getaddrinfo.c | 2 +- lib/libc/net/name6.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/libc/net/getaddrinfo.c b/lib/libc/net/getaddrinfo.c index 0d86fe54bb08..f5271c6d5a3b 100644 --- a/lib/libc/net/getaddrinfo.c +++ b/lib/libc/net/getaddrinfo.c @@ -949,7 +949,7 @@ matchlen(struct sockaddr *src, struct sockaddr *dst) while (s < lim) if ((r = (*d++ ^ *s++)) != 0) { - while (r < addrlen * 8) { + while ((r & 0x80) == 0) { match++; r <<= 1; } diff --git a/lib/libc/net/name6.c b/lib/libc/net/name6.c index 7e52a5150194..b0970786dd8c 100644 --- a/lib/libc/net/name6.c +++ b/lib/libc/net/name6.c @@ -930,7 +930,7 @@ matchlen(struct sockaddr *src, struct sockaddr *dst) while (s < lim) if ((r = (*d++ ^ *s++)) != 0) { - while (r < addrlen * 8) { + while ((r & 0x80) == 0) { match++; r <<= 1; } From 790ba09ec61dd78b46bb2175eba0e1db198eaf6e Mon Sep 17 00:00:00 2001 From: Bryan Drewery Date: Wed, 31 Aug 2016 19:30:00 +0000 Subject: [PATCH 72/86] DIRDEPS_BUILD: Avoid cyclic dependency with libc++. The DIRDEPS_BUILD does not have a 'make includes' phase, so it would otherwise want libc++ to be fully built/staged before building libgcc. Using the header directly works. MFC after: 3 days Sponsored by: EMC / Isilon Storage Division --- gnu/lib/libgcc/Makefile | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/gnu/lib/libgcc/Makefile b/gnu/lib/libgcc/Makefile index a47bd3389420..d9837cc3a7cd 100644 --- a/gnu/lib/libgcc/Makefile +++ b/gnu/lib/libgcc/Makefile @@ -95,6 +95,10 @@ CXXFLAGS+= -std=c++11 .endif CXXFLAGS+= -fno-rtti STATIC_CXXFLAGS+= -fvisibility=hidden -fPIC +.if ${MK_DIRDEPS_BUILD} == "yes" +# Avoid dependency on lib/libc++ +CFLAGS+= -I${SRCTOP}/contrib/libc++/include +.endif .else # MK_LLVM_LIBUNWIND From 776d5e11e9516b6297db6bb659602ce782cd1df1 Mon Sep 17 00:00:00 2001 From: Bryan Drewery Date: Wed, 31 Aug 2016 19:30:46 +0000 Subject: [PATCH 73/86] DIRDEPS_BUILD: Update dependencies. Sponsored by: EMC / Isilon Storage Division --- cddl/usr.sbin/dtrace/Makefile.depend | 2 ++ cddl/usr.sbin/lockstat/Makefile.depend | 2 ++ cddl/usr.sbin/plockstat/Makefile.depend | 2 ++ lib/clang/libclangformat/Makefile.depend | 1 + lib/clang/libclangtoolingcore/Makefile.depend | 1 + lib/libc/tests/stdlib/Makefile.depend | 3 ++- lib/libproc/Makefile.depend | 1 + lib/libproc/tests/Makefile.depend | 2 ++ lib/librtld_db/Makefile.depend | 1 + secure/usr.bin/ssh/Makefile.depend | 2 -- usr.bin/nfsstat/Makefile.depend | 3 +++ usr.bin/tar/tests/Makefile.depend | 6 ++++++ usr.sbin/bhyve/Makefile.depend | 2 ++ usr.sbin/pw/tests/Makefile.depend | 7 +++++++ 14 files changed, 32 insertions(+), 3 deletions(-) diff --git a/cddl/usr.sbin/dtrace/Makefile.depend b/cddl/usr.sbin/dtrace/Makefile.depend index 819706986006..db4aafd0a282 100644 --- a/cddl/usr.sbin/dtrace/Makefile.depend +++ b/cddl/usr.sbin/dtrace/Makefile.depend @@ -13,7 +13,9 @@ DIRDEPS = \ lib/libcompiler_rt \ lib/libcxxrt \ lib/libelf \ + lib/libkvm \ lib/libproc \ + lib/libprocstat \ lib/librtld_db \ lib/libthr \ lib/libutil \ diff --git a/cddl/usr.sbin/lockstat/Makefile.depend b/cddl/usr.sbin/lockstat/Makefile.depend index 70f0672dba3c..18ce380c1380 100644 --- a/cddl/usr.sbin/lockstat/Makefile.depend +++ b/cddl/usr.sbin/lockstat/Makefile.depend @@ -13,7 +13,9 @@ DIRDEPS = \ lib/libcompiler_rt \ lib/libcxxrt \ lib/libelf \ + lib/libkvm \ lib/libproc \ + lib/libprocstat \ lib/librt \ lib/librtld_db \ lib/libthr \ diff --git a/cddl/usr.sbin/plockstat/Makefile.depend b/cddl/usr.sbin/plockstat/Makefile.depend index 819706986006..db4aafd0a282 100644 --- a/cddl/usr.sbin/plockstat/Makefile.depend +++ b/cddl/usr.sbin/plockstat/Makefile.depend @@ -13,7 +13,9 @@ DIRDEPS = \ lib/libcompiler_rt \ lib/libcxxrt \ lib/libelf \ + lib/libkvm \ lib/libproc \ + lib/libprocstat \ lib/librtld_db \ lib/libthr \ lib/libutil \ diff --git a/lib/clang/libclangformat/Makefile.depend b/lib/clang/libclangformat/Makefile.depend index 3e7f3f5e7165..264ede1c30ce 100644 --- a/lib/clang/libclangformat/Makefile.depend +++ b/lib/clang/libclangformat/Makefile.depend @@ -6,6 +6,7 @@ DIRDEPS = \ include/xlocale \ lib/libc++ \ lib/msun \ + usr.bin/clang/clang-tblgen.host \ .include diff --git a/lib/clang/libclangtoolingcore/Makefile.depend b/lib/clang/libclangtoolingcore/Makefile.depend index 3e7f3f5e7165..264ede1c30ce 100644 --- a/lib/clang/libclangtoolingcore/Makefile.depend +++ b/lib/clang/libclangtoolingcore/Makefile.depend @@ -6,6 +6,7 @@ DIRDEPS = \ include/xlocale \ lib/libc++ \ lib/msun \ + usr.bin/clang/clang-tblgen.host \ .include diff --git a/lib/libc/tests/stdlib/Makefile.depend b/lib/libc/tests/stdlib/Makefile.depend index 1ee1d19d8e77..1ace922e7b2a 100644 --- a/lib/libc/tests/stdlib/Makefile.depend +++ b/lib/libc/tests/stdlib/Makefile.depend @@ -11,9 +11,10 @@ DIRDEPS = \ lib/atf/libatf-c++ \ lib/libc \ lib/libc++ \ - lib/libthr \ lib/libcompiler_rt \ + lib/libcxxrt \ lib/libnetbsd \ + lib/libthr \ lib/libutil \ lib/msun \ diff --git a/lib/libproc/Makefile.depend b/lib/libproc/Makefile.depend index 33b871f6a055..89b67c997f30 100644 --- a/lib/libproc/Makefile.depend +++ b/lib/libproc/Makefile.depend @@ -12,6 +12,7 @@ DIRDEPS = \ lib/libcompiler_rt \ lib/libcxxrt \ lib/libelf \ + lib/libprocstat \ lib/librtld_db \ lib/libutil \ diff --git a/lib/libproc/tests/Makefile.depend b/lib/libproc/tests/Makefile.depend index c61b2341db16..b2fb87a7499a 100644 --- a/lib/libproc/tests/Makefile.depend +++ b/lib/libproc/tests/Makefile.depend @@ -13,7 +13,9 @@ DIRDEPS = \ lib/libcompiler_rt \ lib/libcxxrt \ lib/libelf \ + lib/libkvm \ lib/libproc \ + lib/libprocstat \ lib/librtld_db \ lib/libutil \ lib/libz \ diff --git a/lib/librtld_db/Makefile.depend b/lib/librtld_db/Makefile.depend index 90c66d42d7ae..2170d7ed9ea7 100644 --- a/lib/librtld_db/Makefile.depend +++ b/lib/librtld_db/Makefile.depend @@ -10,6 +10,7 @@ DIRDEPS = \ lib/libc \ lib/libcompiler_rt \ lib/libelf \ + lib/libprocstat \ lib/libutil \ diff --git a/secure/usr.bin/ssh/Makefile.depend b/secure/usr.bin/ssh/Makefile.depend index b8099fd405f2..aa586707742a 100644 --- a/secure/usr.bin/ssh/Makefile.depend +++ b/secure/usr.bin/ssh/Makefile.depend @@ -9,8 +9,6 @@ DIRDEPS = \ include/gssapi \ include/rpc \ include/xlocale \ - kerberos5/lib/libasn1 \ - kerberos5/lib/libkrb5 \ lib/${CSU_DIR} \ lib/libc \ lib/libcompiler_rt \ diff --git a/usr.bin/nfsstat/Makefile.depend b/usr.bin/nfsstat/Makefile.depend index 3646e2e2b1af..270f59a1f4bb 100644 --- a/usr.bin/nfsstat/Makefile.depend +++ b/usr.bin/nfsstat/Makefile.depend @@ -9,6 +9,9 @@ DIRDEPS = \ lib/${CSU_DIR} \ lib/libc \ lib/libcompiler_rt \ + lib/libdevstat \ + lib/libelf \ + lib/libkvm \ .include diff --git a/usr.bin/tar/tests/Makefile.depend b/usr.bin/tar/tests/Makefile.depend index 860d9752d8ef..4e7906b9d349 100644 --- a/usr.bin/tar/tests/Makefile.depend +++ b/usr.bin/tar/tests/Makefile.depend @@ -8,8 +8,14 @@ DIRDEPS = \ include/xlocale \ lib/${CSU_DIR} \ lib/libarchive \ + lib/libbz2 \ lib/libc \ lib/libcompiler_rt \ + lib/libexpat \ + lib/liblzma \ + lib/libthr \ + lib/libz \ + secure/lib/libcrypto \ .include diff --git a/usr.sbin/bhyve/Makefile.depend b/usr.sbin/bhyve/Makefile.depend index e12ecb91891e..3cc9293cf771 100644 --- a/usr.sbin/bhyve/Makefile.depend +++ b/usr.sbin/bhyve/Makefile.depend @@ -5,6 +5,7 @@ DIRDEPS = \ gnu/lib/csu \ gnu/lib/libgcc \ include \ + include/arpa \ include/xlocale \ lib/${CSU_DIR} \ lib/libc \ @@ -13,6 +14,7 @@ DIRDEPS = \ lib/libthr \ lib/libutil \ lib/libvmmapi \ + lib/libz \ .include diff --git a/usr.sbin/pw/tests/Makefile.depend b/usr.sbin/pw/tests/Makefile.depend index f80275d86ab1..aa053cfb4c50 100644 --- a/usr.sbin/pw/tests/Makefile.depend +++ b/usr.sbin/pw/tests/Makefile.depend @@ -2,6 +2,13 @@ # Autogenerated - do NOT edit! DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libcompiler_rt \ + lib/libcrypt \ .include From 9e2f435fc14b0121dbaa7b87b7841a0dcd209b7b Mon Sep 17 00:00:00 2001 From: Bryan Drewery Date: Wed, 31 Aug 2016 19:30:52 +0000 Subject: [PATCH 74/86] Add a 'make print-dir' that simply traverses all directories and prints them. This is useful for finding connected directories. MFC after: 1 week Sponsored by: EMC / Isilon Storage Division --- Makefile | 9 +++++++-- share/mk/bsd.dep.mk | 6 +++--- share/mk/bsd.init.mk | 2 +- share/mk/bsd.subdir.mk | 18 ++++++++++++++---- share/mk/local.meta.sys.mk | 3 ++- share/mk/sys.mk | 2 +- 6 files changed, 28 insertions(+), 12 deletions(-) diff --git a/Makefile b/Makefile index cf973dcad417..00dbc23bb79c 100644 --- a/Makefile +++ b/Makefile @@ -109,7 +109,8 @@ # Note: we use this awkward construct to be compatible with FreeBSD's # old make used in 10.0 and 9.2 and earlier. -.if defined(MK_DIRDEPS_BUILD) && ${MK_DIRDEPS_BUILD} == "yes" && !make(showconfig) +.if defined(MK_DIRDEPS_BUILD) && ${MK_DIRDEPS_BUILD} == "yes" && \ + !make(showconfig) && !make(print-dir) # targets/Makefile plays the role of top-level .include "targets/Makefile" .else @@ -132,7 +133,7 @@ TGTS= all all-man buildenv buildenvvars buildkernel buildworld \ xdev-links native-xtools stageworld stagekernel stage-packages \ create-world-packages create-kernel-packages create-packages \ packages installconfig real-packages sign-packages package-pkg \ - test-system-compiler + print-dir test-system-compiler # XXX: r156740: This can't work since bsd.subdir.mk is not included ever. # It will only work for SUBDIR_TARGETS in make.conf. @@ -257,6 +258,10 @@ _TARGET_ARCH= ${XDEV_ARCH} _TARGET?= ${MACHINE} _TARGET_ARCH?= ${MACHINE_ARCH} +.if make(print-dir) +.SILENT: +.endif + # # Make sure we have an up-to-date make(1). Only world and buildworld # should do this as those are the initial targets used for upgrades. diff --git a/share/mk/bsd.dep.mk b/share/mk/bsd.dep.mk index f84abaa9f187..e1f35af17c6e 100644 --- a/share/mk/bsd.dep.mk +++ b/share/mk/bsd.dep.mk @@ -82,9 +82,9 @@ _meta_filemon= 1 # since it will track dependencies itself. OBJS_DEPEND_GUESS is still used. .if !empty(.MAKEFLAGS:M-V${_V_READ_DEPEND}) || make(obj) || make(clean*) || \ ${.TARGETS:M*install*} == ${.TARGETS} || \ - make(analyze) || defined(_meta_filemon) + make(analyze) || defined(_meta_filemon) || make(print-dir) _SKIP_READ_DEPEND= 1 -.if ${MK_DIRDEPS_BUILD} == "no" +.if ${MK_DIRDEPS_BUILD} == "no" || make(analyze) || make(print-dir) .MAKE.DEPENDFILE= /dev/null .endif .endif @@ -198,7 +198,7 @@ CFLAGS+= ${DEPEND_CFLAGS} .endif # !defined(_meta_filemon) .endif # defined(SRCS) -.if ${MK_DIRDEPS_BUILD} == "yes" +.if ${MK_DIRDEPS_BUILD} == "yes" && !make(analyze) && !make(print-dir) # Prevent meta.autodep.mk from tracking "local dependencies". .depend: .include diff --git a/share/mk/bsd.init.mk b/share/mk/bsd.init.mk index 25ab7625ec65..b7a45d9ac43a 100644 --- a/share/mk/bsd.init.mk +++ b/share/mk/bsd.init.mk @@ -31,7 +31,7 @@ _SKIP_BUILD = not building at level 0 .if ${MK_META_MODE} == "yes" .if !exists(/dev/filemon) && \ ${UPDATE_DEPENDFILE:Uyes:tl} != "no" && !defined(NO_FILEMON) && \ - !make(showconfig) && ${.MAKEFLAGS:M-V} == "" + !make(showconfig) && !make(print-dir) && ${.MAKEFLAGS:M-V} == "" .warning The filemon module (/dev/filemon) is not loaded. .warning META_MODE is less useful for incremental builds without filemon. .warning 'kldload filemon' or pass -DNO_FILEMON to suppress this warning. diff --git a/share/mk/bsd.subdir.mk b/share/mk/bsd.subdir.mk index dfe0afab577d..786eef1eba9c 100644 --- a/share/mk/bsd.subdir.mk +++ b/share/mk/bsd.subdir.mk @@ -42,15 +42,15 @@ SUBDIR_TARGETS+= \ all all-man analyze buildconfig buildfiles buildincludes \ checkdpadd clean cleandepend cleandir cleanilinks \ cleanobj depend distribute files includes installconfig \ - installfiles installincludes realinstall lint maninstall \ - manlint obj objlink tags \ + installfiles installincludes print-dir realinstall lint \ + maninstall manlint obj objlink tags \ # Described above. STANDALONE_SUBDIR_TARGETS+= \ all-man buildconfig buildfiles buildincludes check checkdpadd \ clean cleandepend cleandir cleanilinks cleanobj files includes \ - installconfig installincludes installfiles maninstall manlint \ - obj objlink \ + installconfig installincludes installfiles print-dir \ + maninstall manlint obj objlink # It is safe to install in parallel when staging. .if defined(NO_ROOT) @@ -59,6 +59,16 @@ STANDALONE_SUBDIR_TARGETS+= realinstall .include +.if make(print-dir) +NEED_SUBDIR= 1 +ECHODIR= : +.SILENT: +.if ${RELDIR:U.} != "." +print-dir: .PHONY + @echo ${RELDIR} +.endif +.endif + .if !defined(NEED_SUBDIR) .if ${.MAKE.LEVEL} == 0 && ${MK_DIRDEPS_BUILD} == "yes" && !empty(SUBDIR) && !(make(clean*) || make(destroy*)) .include diff --git a/share/mk/local.meta.sys.mk b/share/mk/local.meta.sys.mk index b24afd1dc38e..2ac23d613b1f 100644 --- a/share/mk/local.meta.sys.mk +++ b/share/mk/local.meta.sys.mk @@ -214,7 +214,8 @@ CSU_DIR := ${CSU_DIR.${MACHINE_ARCH}} .if !empty(TIME_STAMP) TRACER= ${TIME_STAMP} ${:U} .endif -.if !defined(_RECURSING_PROGS) && !defined(_RECURSING_CRUNCH) +.if !defined(_RECURSING_PROGS) && !defined(_RECURSING_CRUNCH) && \ + !make(print-dir) WITH_META_STATS= t .endif diff --git a/share/mk/sys.mk b/share/mk/sys.mk index 31a302b51047..dbc2fd91e372 100644 --- a/share/mk/sys.mk +++ b/share/mk/sys.mk @@ -97,7 +97,7 @@ META_MODE?= normal # This needs to be done early - before .PATH is computed # Don't do this for 'make showconfig' as it enables all options where meta mode # is not expected. -.if !make(showconfig) +.if !make(showconfig) && !make(print-dir) .sinclude .endif .endif From 1eb4ec9c62957b232338fc4c2f3c155f7109b71c Mon Sep 17 00:00:00 2001 From: Bryan Drewery Date: Wed, 31 Aug 2016 19:30:59 +0000 Subject: [PATCH 75/86] DIRDEPS_BUILD: Add some missing dirctories to the build. Sponsored by: EMC / Isilon Storage Division --- cddl/usr.sbin/zfsd/Makefile.depend | 35 +++++++++++++++++++ .../tests/libpythagoras/Makefile.depend | 18 ++++++++++ libexec/rtld-elf/tests/target/Makefile.depend | 18 ++++++++++ targets/pseudo/tests/Makefile.depend | 7 ++++ targets/pseudo/userland/Makefile.depend | 2 ++ targets/pseudo/userland/cddl/Makefile.depend | 1 + .../pseudo/userland/libexec/Makefile.depend | 9 +++++ tests/sys/pjdfstest/pjdfstest/Makefile.depend | 18 ++++++++++ tests/sys/sys/Makefile.depend | 19 ++++++++++ usr.bin/bsdcat/tests/Makefile.depend | 25 +++++++++++++ usr.bin/sdiff/tests/Makefile.depend | 11 ++++++ usr.bin/xinstall/tests/Makefile.depend | 11 ++++++ usr.sbin/extattr/tests/Makefile.depend | 11 ++++++ usr.sbin/pmcstudy/Makefile.depend | 18 ++++++++++ usr.sbin/ypldap/Makefile.depend | 25 +++++++++++++ 15 files changed, 228 insertions(+) create mode 100644 cddl/usr.sbin/zfsd/Makefile.depend create mode 100644 libexec/rtld-elf/tests/libpythagoras/Makefile.depend create mode 100644 libexec/rtld-elf/tests/target/Makefile.depend create mode 100644 tests/sys/pjdfstest/pjdfstest/Makefile.depend create mode 100644 tests/sys/sys/Makefile.depend create mode 100644 usr.bin/bsdcat/tests/Makefile.depend create mode 100644 usr.bin/sdiff/tests/Makefile.depend create mode 100644 usr.bin/xinstall/tests/Makefile.depend create mode 100644 usr.sbin/extattr/tests/Makefile.depend create mode 100644 usr.sbin/pmcstudy/Makefile.depend create mode 100644 usr.sbin/ypldap/Makefile.depend diff --git a/cddl/usr.sbin/zfsd/Makefile.depend b/cddl/usr.sbin/zfsd/Makefile.depend new file mode 100644 index 000000000000..35e134179446 --- /dev/null +++ b/cddl/usr.sbin/zfsd/Makefile.depend @@ -0,0 +1,35 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + cddl/lib/libavl \ + cddl/lib/libnvpair \ + cddl/lib/libumem \ + cddl/lib/libuutil \ + cddl/lib/libzfs \ + cddl/lib/libzfs_core \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + include/xlocale \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libc++ \ + lib/libcompiler_rt \ + lib/libcxxrt \ + lib/libdevdctl \ + lib/libexpat \ + lib/libgeom \ + lib/libmd \ + lib/libsbuf \ + lib/libthr \ + lib/libutil \ + lib/libz \ + lib/msun \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/libexec/rtld-elf/tests/libpythagoras/Makefile.depend b/libexec/rtld-elf/tests/libpythagoras/Makefile.depend new file mode 100644 index 000000000000..f562646ea727 --- /dev/null +++ b/libexec/rtld-elf/tests/libpythagoras/Makefile.depend @@ -0,0 +1,18 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libcompiler_rt \ + lib/msun \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/libexec/rtld-elf/tests/target/Makefile.depend b/libexec/rtld-elf/tests/target/Makefile.depend new file mode 100644 index 000000000000..d3847252f308 --- /dev/null +++ b/libexec/rtld-elf/tests/target/Makefile.depend @@ -0,0 +1,18 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libcompiler_rt \ + libexec/rtld-elf/tests/libpythagoras \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/targets/pseudo/tests/Makefile.depend b/targets/pseudo/tests/Makefile.depend index 436bf658f4b3..c8d1f83f7fa7 100644 --- a/targets/pseudo/tests/Makefile.depend +++ b/targets/pseudo/tests/Makefile.depend @@ -166,6 +166,8 @@ DIRDEPS= \ libexec/atf/atf-sh/tests \ libexec/atf/tests \ libexec/rtld-elf/tests \ + libexec/rtld-elf/tests/libpythagoras \ + libexec/rtld-elf/tests/target \ libexec/tests \ sbin/devd/tests \ sbin/dhclient/tests \ @@ -213,6 +215,7 @@ DIRDEPS= \ tests/sys/mqueue \ tests/sys/netinet \ tests/sys/opencrypto \ + tests/sys/pjdfstest/pjdfstest \ tests/sys/pjdfstest/tests \ tests/sys/pjdfstest/tests/chflags \ tests/sys/pjdfstest/tests/chmod \ @@ -230,6 +233,7 @@ DIRDEPS= \ tests/sys/pjdfstest/tests/truncate \ tests/sys/pjdfstest/tests/unlink \ tests/sys/posixshm \ + tests/sys/sys \ tests/sys/vfs \ tests/sys/vm \ usr.bin/apply/tests \ @@ -303,6 +307,7 @@ DIRDEPS= \ usr.bin/mkimg/tests \ usr.bin/ncal/tests \ usr.bin/printf/tests \ + usr.bin/sdiff/tests \ usr.bin/sed/tests \ usr.bin/sed/tests/regress.multitest.out \ usr.bin/soelim/tests \ @@ -315,10 +320,12 @@ DIRDEPS= \ usr.bin/uudecode/tests \ usr.bin/uuencode/tests \ usr.bin/xargs/tests \ + usr.bin/xinstall/tests \ usr.bin/xo/tests \ usr.bin/yacc/tests \ usr.sbin/chown/tests \ usr.sbin/etcupdate/tests \ + usr.sbin/extattr/tests \ usr.sbin/fstyp/tests \ usr.sbin/makefs/tests \ usr.sbin/newsyslog/tests \ diff --git a/targets/pseudo/userland/Makefile.depend b/targets/pseudo/userland/Makefile.depend index 80d05d3cdd19..6b9f83c009bb 100644 --- a/targets/pseudo/userland/Makefile.depend +++ b/targets/pseudo/userland/Makefile.depend @@ -701,6 +701,7 @@ DIRDEPS+= \ usr.sbin/pmcannotate \ usr.sbin/pmccontrol \ usr.sbin/pmcstat \ + usr.sbin/pmcstudy \ usr.sbin/portsnap/make_index \ usr.sbin/portsnap/phttpget \ usr.sbin/portsnap/portsnap \ @@ -785,6 +786,7 @@ DIRDEPS+= \ usr.sbin/wpa/wpa_supplicant \ usr.sbin/yp_mkdb \ usr.sbin/ypbind \ + usr.sbin/ypldap \ usr.sbin/yppoll \ usr.sbin/yppush \ usr.sbin/ypserv \ diff --git a/targets/pseudo/userland/cddl/Makefile.depend b/targets/pseudo/userland/cddl/Makefile.depend index 4747c0bf4407..5b4f1a697bc9 100644 --- a/targets/pseudo/userland/cddl/Makefile.depend +++ b/targets/pseudo/userland/cddl/Makefile.depend @@ -21,6 +21,7 @@ DIRDEPS = \ cddl/usr.sbin/dtruss \ cddl/usr.sbin/lockstat \ cddl/usr.sbin/plockstat \ + cddl/usr.sbin/zfsd \ DIRDEPS.ZFS = \ diff --git a/targets/pseudo/userland/libexec/Makefile.depend b/targets/pseudo/userland/libexec/Makefile.depend index 388df8d6926e..4c1e7a118410 100644 --- a/targets/pseudo/userland/libexec/Makefile.depend +++ b/targets/pseudo/userland/libexec/Makefile.depend @@ -45,4 +45,13 @@ DIRDEPS = \ DIRDEPS+= libexec/blacklistd-helper .endif +.if ${MK_DMAGENT} != "no" +DIRDEPS+= libexec/dma/dma-mbox-create +DIRDEPS+= libexec/dma/dmagent +.endif + +.if ${MK_MAN_UTILS} != "no" +DIRDEPS+= libexec/makewhatis.local +.endif + .include diff --git a/tests/sys/pjdfstest/pjdfstest/Makefile.depend b/tests/sys/pjdfstest/pjdfstest/Makefile.depend new file mode 100644 index 000000000000..3646e2e2b1af --- /dev/null +++ b/tests/sys/pjdfstest/pjdfstest/Makefile.depend @@ -0,0 +1,18 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + include/xlocale \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libcompiler_rt \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/tests/sys/sys/Makefile.depend b/tests/sys/sys/Makefile.depend new file mode 100644 index 000000000000..74074b9588ec --- /dev/null +++ b/tests/sys/sys/Makefile.depend @@ -0,0 +1,19 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + include/xlocale \ + lib/${CSU_DIR} \ + lib/atf/libatf-c \ + lib/libc \ + lib/libcompiler_rt \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/usr.bin/bsdcat/tests/Makefile.depend b/usr.bin/bsdcat/tests/Makefile.depend new file mode 100644 index 000000000000..4e7906b9d349 --- /dev/null +++ b/usr.bin/bsdcat/tests/Makefile.depend @@ -0,0 +1,25 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + include/xlocale \ + lib/${CSU_DIR} \ + lib/libarchive \ + lib/libbz2 \ + lib/libc \ + lib/libcompiler_rt \ + lib/libexpat \ + lib/liblzma \ + lib/libthr \ + lib/libz \ + secure/lib/libcrypto \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/usr.bin/sdiff/tests/Makefile.depend b/usr.bin/sdiff/tests/Makefile.depend new file mode 100644 index 000000000000..f80275d86ab1 --- /dev/null +++ b/usr.bin/sdiff/tests/Makefile.depend @@ -0,0 +1,11 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/usr.bin/xinstall/tests/Makefile.depend b/usr.bin/xinstall/tests/Makefile.depend new file mode 100644 index 000000000000..f80275d86ab1 --- /dev/null +++ b/usr.bin/xinstall/tests/Makefile.depend @@ -0,0 +1,11 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/usr.sbin/extattr/tests/Makefile.depend b/usr.sbin/extattr/tests/Makefile.depend new file mode 100644 index 000000000000..f80275d86ab1 --- /dev/null +++ b/usr.sbin/extattr/tests/Makefile.depend @@ -0,0 +1,11 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/usr.sbin/pmcstudy/Makefile.depend b/usr.sbin/pmcstudy/Makefile.depend new file mode 100644 index 000000000000..3646e2e2b1af --- /dev/null +++ b/usr.sbin/pmcstudy/Makefile.depend @@ -0,0 +1,18 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + include/xlocale \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libcompiler_rt \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif diff --git a/usr.sbin/ypldap/Makefile.depend b/usr.sbin/ypldap/Makefile.depend new file mode 100644 index 000000000000..85420e52c7d3 --- /dev/null +++ b/usr.sbin/ypldap/Makefile.depend @@ -0,0 +1,25 @@ +# $FreeBSD$ +# Autogenerated - do NOT edit! + +DIRDEPS = \ + gnu/lib/csu \ + gnu/lib/libgcc \ + include \ + include/arpa \ + include/rpc \ + include/rpcsvc \ + include/xlocale \ + lib/${CSU_DIR} \ + lib/libc \ + lib/libcompiler_rt \ + lib/libevent \ + lib/libopenbsd \ + lib/librpcsvc \ + lib/libutil \ + + +.include + +.if ${DEP_RELDIR} == ${_DEP_RELDIR} +# local dependencies - needed for -jN in clean tree +.endif From 4b360eca4a54ec2ac67bcf57ddf64b91f6834b84 Mon Sep 17 00:00:00 2001 From: Luiz Otavio O Souza Date: Wed, 31 Aug 2016 19:37:10 +0000 Subject: [PATCH 76/86] All the TI platforms are FDT based and it is not necessary to enumerate the hinted children (there wont be any). Spotted by: gonzo --- sys/arm/ti/ti_scm.c | 1 - 1 file changed, 1 deletion(-) diff --git a/sys/arm/ti/ti_scm.c b/sys/arm/ti/ti_scm.c index 5a6b097c99c0..62c85ef280b9 100644 --- a/sys/arm/ti/ti_scm.c +++ b/sys/arm/ti/ti_scm.c @@ -133,7 +133,6 @@ ti_scm_attach(device_t dev) /* Attach platform extensions, if any. */ bus_generic_probe(dev); - bus_enumerate_hinted_children(dev); return (bus_generic_attach(dev)); } From 89688ae7084eda32be959b70e2cb7edf07d5ed9a Mon Sep 17 00:00:00 2001 From: Jilles Tjoelker Date: Wed, 31 Aug 2016 20:38:40 +0000 Subject: [PATCH 77/86] directory(3): Deprecate readdir_r(). Clarify dirent buffers. In existing implementations including FreeBSD, there is no reason to use readdir_r() in the common case where potentially multiple threads each list their own directory. Code using readdir() is simpler. What's more, lthough readdir_r() can safely be used on FreeBSD because NAME_MAX is forced to 255, it cannot be used safely on systems where {NAME_MAX} is not fixed. As a concrete example, FAT/NTFS filenames can be up to 255 UTF-16 code units long, which can be up to 765 UTF-8 bytes. Deprecating readdir_r() in POSIX has been proposed in http://www.austingroupbugs.net/view.php?id=696 and glibc wants to deprecate it as well. Reviewed by: ed, wblock MFC after: 1 week Differential Revision: https://reviews.freebsd.org/D7678 --- lib/libc/gen/directory.3 | 26 ++++++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/lib/libc/gen/directory.3 b/lib/libc/gen/directory.3 index 39198056ebb6..4b6d0a1f2372 100644 --- a/lib/libc/gen/directory.3 +++ b/lib/libc/gen/directory.3 @@ -28,7 +28,7 @@ .\" @(#)directory.3 8.1 (Berkeley) 6/4/93 .\" $FreeBSD$ .\" -.Dd February 19, 2016 +.Dd August 31, 2016 .Dt DIRECTORY 3 .Os .Sh NAME @@ -68,6 +68,15 @@ .Ft int .Fn dirfd "DIR *dirp" .Sh DESCRIPTION +.Bf -symbolic +The +.Fn readdir_r +interface is deprecated +because it cannot be used correctly unless +.Brq Va NAME_MAX +is a fixed value. +.Ef +.Pp The .Fn opendir function @@ -122,7 +131,13 @@ The .Fn readdir function returns a pointer to the next directory entry. -It returns +The directory entry remains valid until the next call to +.Fn readdir +or +.Fn closedir +on the same +.Em directory stream . +The function returns .Dv NULL upon reaching the end of the directory or on error. In the event of an error, @@ -139,6 +154,13 @@ provides the same functionality as but the caller must provide a directory .Fa entry buffer to store the results in. +The buffer must be large enough for a +.Vt struct dirent +with a +.Va d_name +array with +.Brq Va NAME_MAX ++ 1 elements. If the read succeeds, .Fa result is pointed at the From d0bd2dad6f56e642ccb69de65a74e011c52da5a3 Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Wed, 31 Aug 2016 21:04:58 +0000 Subject: [PATCH 78/86] readelf: silence GCC 4.2.1 uninitialized variable warning Sponsored by: The FreeBSD Foundation --- contrib/elftoolchain/readelf/readelf.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/contrib/elftoolchain/readelf/readelf.c b/contrib/elftoolchain/readelf/readelf.c index 2fb6d790728a..2bf668ed22ff 100644 --- a/contrib/elftoolchain/readelf/readelf.c +++ b/contrib/elftoolchain/readelf/readelf.c @@ -2831,6 +2831,8 @@ dump_rel(struct readelf *re, struct section *s, Elf_Data *d) type2 = (type >> 8) & 0xFF; type3 = (type >> 16) & 0xFF; type = type & 0xFF; + } else { + type2 = type3 = 0; } if (re->options & RE_WW) printf("%16.16jx %16.16jx %-24.24s" @@ -2914,6 +2916,8 @@ dump_rela(struct readelf *re, struct section *s, Elf_Data *d) type2 = (type >> 8) & 0xFF; type3 = (type >> 16) & 0xFF; type = type & 0xFF; + } else { + type2 = type3 = 0; } if (re->options & RE_WW) printf("%16.16jx %16.16jx %-24.24s" From d74808dd1afd6d4ef0c667d263d0be4696ce0e24 Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Wed, 31 Aug 2016 21:12:50 +0000 Subject: [PATCH 79/86] users: don't build when we don't have a C++ toolchain (On RISC-V MK_CXX is in BROKEN_OPTIONS, so users remains skipped there.) Reviewed by: bdrewery Differential Revision: https://reviews.freebsd.org/D7725 --- usr.bin/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/usr.bin/Makefile b/usr.bin/Makefile index 1f0c6640d80d..8084c708716d 100644 --- a/usr.bin/Makefile +++ b/usr.bin/Makefile @@ -294,7 +294,7 @@ SUBDIR.${MK_VT}+= vtfontcvt SUBDIR.${MK_USB}+= usbhidaction SUBDIR.${MK_USB}+= usbhidctl SUBDIR.${MK_UTMPX}+= last -.if ${MACHINE_CPUARCH} != "riscv" # RISCVTODO users does not build +.if ${MK_CXX} != "no" SUBDIR.${MK_UTMPX}+= users .endif SUBDIR.${MK_UTMPX}+= who From 5462b0052b175292d659c19553a803317e3e2b96 Mon Sep 17 00:00:00 2001 From: Ed Maste Date: Wed, 31 Aug 2016 21:35:38 +0000 Subject: [PATCH 80/86] Set UEFI boot loader PE/COFF timestamps to known value for reproducible builds Reviewed by: rpokala MFC after: 1 week Sponsored by: The FreeBSD Foundation Differential Revision: https://reviews.freebsd.org/D7633 --- sys/boot/efi/boot1/Makefile | 4 ++++ sys/boot/efi/loader/Makefile | 4 ++++ 2 files changed, 8 insertions(+) diff --git a/sys/boot/efi/boot1/Makefile b/sys/boot/efi/boot1/Makefile index 12144786ed49..5355c3141ec0 100644 --- a/sys/boot/efi/boot1/Makefile +++ b/sys/boot/efi/boot1/Makefile @@ -89,11 +89,15 @@ EFI_TARGET= efi-app-ia32 EFI_TARGET= binary .endif +# Arbitrarily set the PE/COFF header timestamps to 1 Jan 2016 00:00:00 +# for build reproducibility. +SOURCE_DATE_EPOCH?=1451606400 boot1.efi: ${PROG} if ${NM} ${.ALLSRC} | grep ' U '; then \ echo "Undefined symbols in ${.ALLSRC}"; \ exit 1; \ fi + SOURCE_DATE_EPOCH=${SOURCE_DATE_EPOCH} \ ${OBJCOPY} -j .peheader -j .text -j .sdata -j .data \ -j .dynamic -j .dynsym -j .rel.dyn \ -j .rela.dyn -j .reloc -j .eh_frame \ diff --git a/sys/boot/efi/loader/Makefile b/sys/boot/efi/loader/Makefile index 07c7af17212e..7503cc2667c8 100644 --- a/sys/boot/efi/loader/Makefile +++ b/sys/boot/efi/loader/Makefile @@ -131,11 +131,15 @@ EFI_TARGET= efi-app-ia32 EFI_TARGET= binary .endif +# Arbitrarily set the PE/COFF header timestamps to 1 Jan 2016 00:00:00 +# for build reproducibility. +SOURCE_DATE_EPOCH?=1451606400 loader.efi: ${PROG} if ${NM} ${.ALLSRC} | grep ' U '; then \ echo "Undefined symbols in ${.ALLSRC}"; \ exit 1; \ fi + SOURCE_DATE_EPOCH=${SOURCE_DATE_EPOCH} \ ${OBJCOPY} -j .peheader -j .text -j .sdata -j .data \ -j .dynamic -j .dynsym -j .rel.dyn \ -j .rela.dyn -j .reloc -j .eh_frame -j set_Xcommand_set \ From 99ab95db4d0e32b4198a665273426296d9f19b41 Mon Sep 17 00:00:00 2001 From: Mark Johnston Date: Wed, 31 Aug 2016 21:48:22 +0000 Subject: [PATCH 81/86] Rename unp_dispose_so() to unp_dispose(). It implements the dom_dispose method for local socket domain, so its name should match the method name. --- sys/kern/uipc_usrreq.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/sys/kern/uipc_usrreq.c b/sys/kern/uipc_usrreq.c index 8db97fdcc1fd..90e6d48b7d3e 100644 --- a/sys/kern/uipc_usrreq.c +++ b/sys/kern/uipc_usrreq.c @@ -277,8 +277,8 @@ static int unp_connectat(int, struct socket *, struct sockaddr *, struct thread *); static int unp_connect2(struct socket *so, struct socket *so2, int); static void unp_disconnect(struct unpcb *unp, struct unpcb *unp2); -static void unp_dispose(struct mbuf *); -static void unp_dispose_so(struct socket *so); +static void unp_dispose(struct socket *so); +static void unp_dispose_mbuf(struct mbuf *); static void unp_shutdown(struct unpcb *); static void unp_drop(struct unpcb *); static void unp_gc(__unused void *, int); @@ -335,7 +335,7 @@ static struct domain localdomain = { .dom_name = "local", .dom_init = unp_init, .dom_externalize = unp_externalize, - .dom_dispose = unp_dispose_so, + .dom_dispose = unp_dispose, .dom_protosw = localsw, .dom_protoswNPROTOSW = &localsw[nitems(localsw)] }; @@ -1051,7 +1051,7 @@ uipc_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *nam, UNP_LINK_RUNLOCK(); if (control != NULL && error != 0) - unp_dispose(control); + unp_dispose_mbuf(control); release: if (control != NULL) @@ -2352,7 +2352,7 @@ unp_gc(__unused void *arg, int pending) } static void -unp_dispose(struct mbuf *m) +unp_dispose_mbuf(struct mbuf *m) { if (m) @@ -2363,7 +2363,7 @@ unp_dispose(struct mbuf *m) * Synchronize against unp_gc, which can trip over data as we are freeing it. */ static void -unp_dispose_so(struct socket *so) +unp_dispose(struct socket *so) { struct unpcb *unp; @@ -2371,7 +2371,7 @@ unp_dispose_so(struct socket *so) UNP_LIST_LOCK(); unp->unp_gcflag |= UNPGC_IGNORE_RIGHTS; UNP_LIST_UNLOCK(); - unp_dispose(so->so_rcv.sb_mb); + unp_dispose_mbuf(so->so_rcv.sb_mb); } static void From 968267fdb8e2f2d3794650980fc275f1809dbff1 Mon Sep 17 00:00:00 2001 From: Navdeep Parhar Date: Wed, 31 Aug 2016 23:23:46 +0000 Subject: [PATCH 82/86] cxgbe/t4_tom: Add general purpose routines to deal with page pod regions and allocations within them. Switch to these routines to manage the TOE DDP region. Sponsored by: Chelsio Communications --- sys/dev/cxgbe/cxgbei/cxgbei.c | 1 - sys/dev/cxgbe/tom/t4_ddp.c | 227 +++++++++++++++++++--------------- sys/dev/cxgbe/tom/t4_tom.c | 10 +- sys/dev/cxgbe/tom/t4_tom.h | 37 ++++-- 4 files changed, 162 insertions(+), 113 deletions(-) diff --git a/sys/dev/cxgbe/cxgbei/cxgbei.c b/sys/dev/cxgbe/cxgbei/cxgbei.c index 29a4b28d0c60..a246ff80dea9 100644 --- a/sys/dev/cxgbe/cxgbei/cxgbei.c +++ b/sys/dev/cxgbe/cxgbei/cxgbei.c @@ -157,7 +157,6 @@ ulp_mem_io_set_hdr(struct adapter *sc, int tid, struct ulp_mem_io *req, idata->len = htonl(dlen); } -#define PPOD_SIZE sizeof(struct pagepod) #define ULPMEM_IDATA_MAX_NPPODS 1 /* 256/PPOD_SIZE */ #define PCIE_MEMWIN_MAX_NPPODS 16 /* 1024/PPOD_SIZE */ diff --git a/sys/dev/cxgbe/tom/t4_ddp.c b/sys/dev/cxgbe/tom/t4_ddp.c index d70fb5911d39..8201fd14ea3d 100644 --- a/sys/dev/cxgbe/tom/t4_ddp.c +++ b/sys/dev/cxgbe/tom/t4_ddp.c @@ -85,44 +85,11 @@ static void ddp_complete_all(struct toepcb *toep, int error); static void t4_aio_cancel_active(struct kaiocb *job); static void t4_aio_cancel_queued(struct kaiocb *job); -#define PPOD_SZ(n) ((n) * sizeof(struct pagepod)) -#define PPOD_SIZE (PPOD_SZ(1)) - static TAILQ_HEAD(, pageset) ddp_orphan_pagesets; static struct mtx ddp_orphan_pagesets_lock; static struct task ddp_orphan_task; #define MAX_DDP_BUFFER_SIZE (M_TCB_RX_DDP_BUF0_LEN) -static int -alloc_ppods(struct tom_data *td, int n, u_int *ppod_addr) -{ - vmem_addr_t v; - int rc; - - MPASS(n > 0); - - rc = vmem_alloc(td->ppod_arena, PPOD_SZ(n), M_NOWAIT | M_FIRSTFIT, &v); - *ppod_addr = (u_int)v; - - return (rc); -} - -static void -free_ppods(struct tom_data *td, u_int ppod_addr, int n) -{ - - MPASS(n > 0); - - vmem_free(td->ppod_arena, (vmem_addr_t)ppod_addr, PPOD_SZ(n)); -} - -static inline int -pages_to_nppods(int npages, int ddp_pgsz) -{ - int nsegs = npages * PAGE_SIZE / ddp_pgsz; - - return (howmany(nsegs, PPOD_PAGES)); -} /* * A page set holds information about a buffer used for DDP. The page @@ -147,8 +114,8 @@ free_pageset(struct tom_data *td, struct pageset *ps) vm_page_t p; int i; - if (ps->nppods > 0) - free_ppods(td, ps->ppod_addr, ps->nppods); + if (ps->prsv.prsv_nppods > 0) + t4_free_page_pods(&ps->prsv); if (ps->flags & PS_WIRED) { for (i = 0; i < ps->npages; i++) { @@ -483,7 +450,7 @@ mk_update_tcb_for_ddp(struct adapter *sc, struct toepcb *toep, int db_idx, ulpmc = mk_set_tcb_field_ulp(ulpmc, toep, W_TCB_RX_DDP_BUF0_TAG + db_idx, V_TCB_RX_DDP_BUF0_TAG(M_TCB_RX_DDP_BUF0_TAG), - V_TCB_RX_DDP_BUF0_TAG(ps->tag)); + V_TCB_RX_DDP_BUF0_TAG(ps->prsv.prsv_tag)); /* Update the current offset in the DDP buffer and its total length */ if (db_idx == 0) @@ -879,13 +846,52 @@ calculate_hcf(int n1, int n2) return (b); } -static int -alloc_page_pods(struct tom_data *td, struct pageset *ps) +static inline int +pages_to_nppods(int npages, int ddp_page_shift) { - int i, hcf, seglen, idx, ppod, nppods; - u_int ppod_addr; - KASSERT(ps->nppods == 0, ("%s: page pods already allocated", __func__)); + MPASS(ddp_page_shift >= PAGE_SHIFT); + + return (howmany(npages >> (ddp_page_shift - PAGE_SHIFT), PPOD_PAGES)); +} + +static int +alloc_page_pods(struct ppod_region *pr, u_int nppods, u_int pgsz_idx, + struct ppod_reservation *prsv) +{ + vmem_addr_t addr; /* relative to start of region */ + + if (vmem_alloc(pr->pr_arena, PPOD_SZ(nppods), M_NOWAIT | M_FIRSTFIT, + &addr) != 0) + return (ENOMEM); + + CTR5(KTR_CXGBE, "%-17s arena %p, addr 0x%08x, nppods %d, pgsz %d", + __func__, pr->pr_arena, (uint32_t)addr & pr->pr_tag_mask, + nppods, 1 << pr->pr_page_shift[pgsz_idx]); + + /* + * The hardware tagmask includes an extra invalid bit but the arena was + * seeded with valid values only. An allocation out of this arena will + * fit inside the tagmask but won't have the invalid bit set. + */ + MPASS((addr & pr->pr_tag_mask) == addr); + MPASS((addr & pr->pr_invalid_bit) == 0); + + prsv->prsv_pr = pr; + prsv->prsv_tag = V_PPOD_PGSZ(pgsz_idx) | addr; + prsv->prsv_nppods = nppods; + + return (0); +} + +int +t4_alloc_page_pods_for_ps(struct ppod_region *pr, struct pageset *ps) +{ + int i, hcf, seglen, idx, nppods; + struct ppod_reservation *prsv = &ps->prsv; + + KASSERT(prsv->prsv_nppods == 0, + ("%s: page pods already allocated", __func__)); /* * The DDP page size is unrelated to the VM page size. We combine @@ -905,79 +911,85 @@ alloc_page_pods(struct tom_data *td, struct pageset *ps) } hcf = calculate_hcf(hcf, seglen); - if (hcf < td->ddp_pgsz[1]) { + if (hcf < (1 << pr->pr_page_shift[1])) { idx = 0; goto have_pgsz; /* give up, short circuit */ } } - if (hcf % td->ddp_pgsz[0] != 0) { - /* hmmm. This could only happen when PAGE_SIZE < 4K */ - KASSERT(PAGE_SIZE < 4096, - ("%s: PAGE_SIZE %d, hcf %d", __func__, PAGE_SIZE, hcf)); - CTR3(KTR_CXGBE, "%s: PAGE_SIZE %d, hcf %d", - __func__, PAGE_SIZE, hcf); - return (0); - } - - for (idx = nitems(td->ddp_pgsz) - 1; idx > 0; idx--) { - if (hcf % td->ddp_pgsz[idx] == 0) +#define PR_PAGE_MASK(x) ((1 << pr->pr_page_shift[(x)]) - 1) + MPASS((hcf & PR_PAGE_MASK(0)) == 0); /* PAGE_SIZE is >= 4K everywhere */ + for (idx = nitems(pr->pr_page_shift) - 1; idx > 0; idx--) { + if ((hcf & PR_PAGE_MASK(idx)) == 0) break; } +#undef PR_PAGE_MASK + have_pgsz: MPASS(idx <= M_PPOD_PGSZ); - nppods = pages_to_nppods(ps->npages, td->ddp_pgsz[idx]); - if (alloc_ppods(td, nppods, &ppod_addr) != 0) { - CTR4(KTR_CXGBE, "%s: no pods, nppods %d, npages %d, pgsz %d", - __func__, nppods, ps->npages, td->ddp_pgsz[idx]); + nppods = pages_to_nppods(ps->npages, pr->pr_page_shift[idx]); + if (alloc_page_pods(pr, nppods, idx, prsv) != 0) return (0); - } - - ppod = (ppod_addr - td->ppod_start) / PPOD_SIZE; - ps->tag = V_PPOD_PGSZ(idx) | V_PPOD_TAG(ppod); - ps->ppod_addr = ppod_addr; - ps->nppods = nppods; - - CTR5(KTR_CXGBE, "New page pods. " - "ps %p, ddp_pgsz %d, ppod 0x%x, npages %d, nppods %d", - ps, td->ddp_pgsz[idx], ppod, ps->npages, ps->nppods); + MPASS(prsv->prsv_nppods > 0); return (1); } +void +t4_free_page_pods(struct ppod_reservation *prsv) +{ + struct ppod_region *pr = prsv->prsv_pr; + vmem_addr_t addr; + + MPASS(prsv != NULL); + MPASS(prsv->prsv_nppods != 0); + + addr = prsv->prsv_tag & pr->pr_tag_mask; + MPASS((addr & pr->pr_invalid_bit) == 0); + + CTR4(KTR_CXGBE, "%-17s arena %p, addr 0x%08x, nppods %d", __func__, + pr->pr_arena, addr, prsv->prsv_nppods); + + vmem_free(pr->pr_arena, addr, PPOD_SZ(prsv->prsv_nppods)); + prsv->prsv_nppods = 0; +} + #define NUM_ULP_TX_SC_IMM_PPODS (256 / PPOD_SIZE) -static int -write_page_pods(struct adapter *sc, struct toepcb *toep, struct pageset *ps) +int +t4_write_page_pods_for_ps(struct adapter *sc, struct sge_wrq *wrq, int tid, + struct pageset *ps) { struct wrqe *wr; struct ulp_mem_io *ulpmc; struct ulptx_idata *ulpsc; struct pagepod *ppod; - struct tom_data *td = sc->tom_softc; int i, j, k, n, chunk, len, ddp_pgsz, idx; u_int ppod_addr; uint32_t cmd; + struct ppod_reservation *prsv = &ps->prsv; + struct ppod_region *pr = prsv->prsv_pr; KASSERT(!(ps->flags & PS_PPODS_WRITTEN), ("%s: page pods already written", __func__)); + MPASS(prsv->prsv_nppods > 0); cmd = htobe32(V_ULPTX_CMD(ULP_TX_MEM_WRITE)); if (is_t4(sc)) cmd |= htobe32(F_ULP_MEMIO_ORDER); else cmd |= htobe32(F_T5_ULP_MEMIO_IMM); - ddp_pgsz = td->ddp_pgsz[G_PPOD_PGSZ(ps->tag)]; - ppod_addr = ps->ppod_addr; - for (i = 0; i < ps->nppods; ppod_addr += chunk) { + ddp_pgsz = 1 << pr->pr_page_shift[G_PPOD_PGSZ(prsv->prsv_tag)]; + ppod_addr = pr->pr_start + (prsv->prsv_tag & pr->pr_tag_mask); + for (i = 0; i < prsv->prsv_nppods; ppod_addr += chunk) { /* How many page pods are we writing in this cycle */ - n = min(ps->nppods - i, NUM_ULP_TX_SC_IMM_PPODS); + n = min(prsv->prsv_nppods - i, NUM_ULP_TX_SC_IMM_PPODS); chunk = PPOD_SZ(n); len = roundup2(sizeof(*ulpmc) + sizeof(*ulpsc) + chunk, 16); - wr = alloc_wrqe(len, toep->ctrlq); + wr = alloc_wrqe(len, wrq); if (wr == NULL) return (ENOMEM); /* ok to just bail out */ ulpmc = wrtod(wr); @@ -995,7 +1007,7 @@ write_page_pods(struct adapter *sc, struct toepcb *toep, struct pageset *ps) ppod = (struct pagepod *)(ulpsc + 1); for (j = 0; j < n; i++, j++, ppod++) { ppod->vld_tid_pgsz_tag_color = htobe64(F_PPOD_VALID | - V_PPOD_TID(toep->tid) | ps->tag); + V_PPOD_TID(tid) | prsv->prsv_tag); ppod->len_offset = htobe64(V_PPOD_LEN(ps->len) | V_PPOD_OFST(ps->offset)); ppod->rsvd = 0; @@ -1053,51 +1065,64 @@ prep_pageset(struct adapter *sc, struct toepcb *toep, struct pageset *ps) if (!(ps->flags & PS_WIRED)) wire_pageset(ps); - if (ps->nppods == 0 && !alloc_page_pods(td, ps)) { + if (ps->prsv.prsv_nppods == 0 && + !t4_alloc_page_pods_for_ps(&td->pr, ps)) { return (0); } if (!(ps->flags & PS_PPODS_WRITTEN) && - write_page_pods(sc, toep, ps) != 0) { + t4_write_page_pods_for_ps(sc, toep->ctrlq, toep->tid, ps) != 0) { return (0); } return (1); } -void -t4_init_ddp(struct adapter *sc, struct tom_data *td) +int +t4_init_ppod_region(struct ppod_region *pr, struct t4_range *r, u_int psz, + const char *name) { int i; - uint32_t r; - r = t4_read_reg(sc, A_ULP_RX_TDDP_PSZ); - td->ddp_pgsz[0] = 4096 << G_HPZ0(r); - td->ddp_pgsz[1] = 4096 << G_HPZ1(r); - td->ddp_pgsz[2] = 4096 << G_HPZ2(r); - td->ddp_pgsz[3] = 4096 << G_HPZ3(r); + MPASS(pr != NULL); + MPASS(r->size > 0); - /* - * The SGL -> page pod algorithm requires the sizes to be in increasing - * order. - */ - for (i = 1; i < nitems(td->ddp_pgsz); i++) { - if (td->ddp_pgsz[i] <= td->ddp_pgsz[i - 1]) - return; + pr->pr_start = r->start; + pr->pr_len = r->size; + pr->pr_page_shift[0] = 12 + G_HPZ0(psz); + pr->pr_page_shift[1] = 12 + G_HPZ1(psz); + pr->pr_page_shift[2] = 12 + G_HPZ2(psz); + pr->pr_page_shift[3] = 12 + G_HPZ3(psz); + + /* The SGL -> page pod algorithm requires the sizes to be in order. */ + for (i = 1; i < nitems(pr->pr_page_shift); i++) { + if (pr->pr_page_shift[i] <= pr->pr_page_shift[i - 1]) + return (ENXIO); } - td->ppod_start = sc->vres.ddp.start; - td->ppod_arena = vmem_create("DDP page pods", sc->vres.ddp.start, - sc->vres.ddp.size, PPOD_SIZE, 512, M_FIRSTFIT | M_NOWAIT); + pr->pr_tag_mask = ((1 << fls(r->size)) - 1) & V_PPOD_TAG(M_PPOD_TAG); + pr->pr_alias_mask = V_PPOD_TAG(M_PPOD_TAG) & ~pr->pr_tag_mask; + if (pr->pr_tag_mask == 0 || pr->pr_alias_mask == 0) + return (ENXIO); + pr->pr_alias_shift = fls(pr->pr_tag_mask); + pr->pr_invalid_bit = 1 << (pr->pr_alias_shift - 1); + + pr->pr_arena = vmem_create(name, 0, pr->pr_len, PPOD_SIZE, 0, + M_FIRSTFIT | M_NOWAIT); + if (pr->pr_arena == NULL) + return (ENOMEM); + + return (0); } void -t4_uninit_ddp(struct adapter *sc __unused, struct tom_data *td) +t4_free_ppod_region(struct ppod_region *pr) { - if (td->ppod_arena != NULL) { - vmem_destroy(td->ppod_arena); - td->ppod_arena = NULL; - } + MPASS(pr != NULL); + + if (pr->pr_arena) + vmem_destroy(pr->pr_arena); + bzero(pr, sizeof(*pr)); } static int diff --git a/sys/dev/cxgbe/tom/t4_tom.c b/sys/dev/cxgbe/tom/t4_tom.c index 56006d0ac891..04f9bcda423c 100644 --- a/sys/dev/cxgbe/tom/t4_tom.c +++ b/sys/dev/cxgbe/tom/t4_tom.c @@ -930,7 +930,7 @@ free_tom_data(struct adapter *sc, struct tom_data *td) KASSERT(td->lctx_count == 0, ("%s: lctx hash table is not empty.", __func__)); - t4_uninit_ddp(sc, td); + t4_free_ppod_region(&td->pr); destroy_clip_table(sc, td); if (td->listen_mask != 0) @@ -1024,8 +1024,12 @@ t4_tom_activate(struct adapter *sc) if (rc != 0) goto done; - /* DDP page pods and CPL handlers */ - t4_init_ddp(sc, td); + rc = t4_init_ppod_region(&td->pr, &sc->vres.ddp, + t4_read_reg(sc, A_ULP_RX_TDDP_PSZ), "TDDP page pods"); + if (rc != 0) + goto done; + t4_set_reg_field(sc, A_ULP_RX_TDDP_TAGMASK, + V_TDDPTAGMASK(M_TDDPTAGMASK), td->pr.pr_tag_mask); /* CLIP table for IPv6 offload */ init_clip_table(sc, td); diff --git a/sys/dev/cxgbe/tom/t4_tom.h b/sys/dev/cxgbe/tom/t4_tom.h index 313fb7b510d6..eae4b92355ac 100644 --- a/sys/dev/cxgbe/tom/t4_tom.h +++ b/sys/dev/cxgbe/tom/t4_tom.h @@ -51,6 +51,9 @@ #define USE_DDP_RX_FLOW_CONTROL +#define PPOD_SZ(n) ((n) * sizeof(struct pagepod)) +#define PPOD_SIZE (PPOD_SZ(1)) + /* TOE PCB flags */ enum { TPF_ATTACHED = (1 << 0), /* a tcpcb refers to this toepcb */ @@ -83,16 +86,31 @@ struct ofld_tx_sdesc { uint8_t tx_credits; /* firmware tx credits (unit is 16B) */ }; +struct ppod_region { + u_int pr_start; + u_int pr_len; + u_int pr_page_shift[4]; + uint32_t pr_tag_mask; /* hardware tagmask for this region. */ + uint32_t pr_invalid_bit; /* OR with this to invalidate tag. */ + uint32_t pr_alias_mask; /* AND with tag to get alias bits. */ + u_int pr_alias_shift; /* shift this much for first alias bit. */ + vmem_t *pr_arena; +}; + +struct ppod_reservation { + struct ppod_region *prsv_pr; + uint32_t prsv_tag; /* Full tag: pgsz, alias, tag, color */ + u_int prsv_nppods; +}; + struct pageset { TAILQ_ENTRY(pageset) link; vm_page_t *pages; int npages; int flags; - u_int ppod_addr; - int nppods; - uint32_t tag; /* includes color, page pod addr, and DDP page size */ int offset; /* offset in first page */ int len; + struct ppod_reservation prsv; struct vmspace *vm; u_int vm_timestamp; }; @@ -239,9 +257,7 @@ struct tom_data { u_long listen_mask; int lctx_count; /* # of lctx in the hash table */ - u_int ppod_start; - u_int ddp_pgsz[4]; - vmem_t *ppod_arena; + struct ppod_region pr; struct mtx clip_table_lock; struct clip_head clip_table; @@ -346,8 +362,13 @@ void t4_push_pdus(struct adapter *sc, struct toepcb *toep, int drop); int do_set_tcb_rpl(struct sge_iq *, const struct rss_header *, struct mbuf *); /* t4_ddp.c */ -void t4_init_ddp(struct adapter *, struct tom_data *); -void t4_uninit_ddp(struct adapter *, struct tom_data *); +int t4_init_ppod_region(struct ppod_region *, struct t4_range *, u_int, + const char *); +void t4_free_ppod_region(struct ppod_region *); +int t4_alloc_page_pods_for_ps(struct ppod_region *, struct pageset *); +int t4_write_page_pods_for_ps(struct adapter *, struct sge_wrq *, int, + struct pageset *); +void t4_free_page_pods(struct ppod_reservation *); int t4_soreceive_ddp(struct socket *, struct sockaddr **, struct uio *, struct mbuf **, struct mbuf **, int *); int t4_aio_queue_ddp(struct socket *, struct kaiocb *); From a9feb2cdbb612b58e2d5b31c2732d484e3481228 Mon Sep 17 00:00:00 2001 From: Navdeep Parhar Date: Thu, 1 Sep 2016 00:51:59 +0000 Subject: [PATCH 83/86] cxgbe/t4_tom: Two new routines to allocate and write page pods for a buffer in the kernel's address space. --- sys/dev/cxgbe/tom/t4_ddp.c | 146 +++++++++++++++++++++++++++++++++++++ sys/dev/cxgbe/tom/t4_tom.h | 4 + 2 files changed, 150 insertions(+) diff --git a/sys/dev/cxgbe/tom/t4_ddp.c b/sys/dev/cxgbe/tom/t4_ddp.c index 8201fd14ea3d..1a4cb7104360 100644 --- a/sys/dev/cxgbe/tom/t4_ddp.c +++ b/sys/dev/cxgbe/tom/t4_ddp.c @@ -936,6 +936,64 @@ t4_alloc_page_pods_for_ps(struct ppod_region *pr, struct pageset *ps) return (1); } +int +t4_alloc_page_pods_for_buf(struct ppod_region *pr, vm_offset_t buf, int len, + struct ppod_reservation *prsv) +{ + int hcf, seglen, idx, npages, nppods; + uintptr_t start_pva, end_pva, pva, p1; + + MPASS(buf > 0); + MPASS(len > 0); + + /* + * The DDP page size is unrelated to the VM page size. We combine + * contiguous physical pages into larger segments to get the best DDP + * page size possible. This is the largest of the four sizes in + * A_ULP_RX_ISCSI_PSZ that evenly divides the HCF of the segment sizes + * in the page list. + */ + hcf = 0; + start_pva = trunc_page(buf); + end_pva = trunc_page(buf + len - 1); + pva = start_pva; + while (pva <= end_pva) { + seglen = PAGE_SIZE; + p1 = pmap_kextract(pva); + pva += PAGE_SIZE; + while (pva <= end_pva && p1 + seglen == pmap_kextract(pva)) { + seglen += PAGE_SIZE; + pva += PAGE_SIZE; + } + + hcf = calculate_hcf(hcf, seglen); + if (hcf < (1 << pr->pr_page_shift[1])) { + idx = 0; + goto have_pgsz; /* give up, short circuit */ + } + } + +#define PR_PAGE_MASK(x) ((1 << pr->pr_page_shift[(x)]) - 1) + MPASS((hcf & PR_PAGE_MASK(0)) == 0); /* PAGE_SIZE is >= 4K everywhere */ + for (idx = nitems(pr->pr_page_shift) - 1; idx > 0; idx--) { + if ((hcf & PR_PAGE_MASK(idx)) == 0) + break; + } +#undef PR_PAGE_MASK + +have_pgsz: + MPASS(idx <= M_PPOD_PGSZ); + + npages = 1; + npages += (end_pva - start_pva) >> pr->pr_page_shift[idx]; + nppods = howmany(npages, PPOD_PAGES); + if (alloc_page_pods(pr, nppods, idx, prsv) != 0) + return (ENOMEM); + MPASS(prsv->prsv_nppods > 0); + + return (0); +} + void t4_free_page_pods(struct ppod_reservation *prsv) { @@ -1036,6 +1094,94 @@ t4_write_page_pods_for_ps(struct adapter *sc, struct sge_wrq *wrq, int tid, return (0); } +int +t4_write_page_pods_for_buf(struct adapter *sc, struct sge_wrq *wrq, int tid, + struct ppod_reservation *prsv, vm_offset_t buf, int buflen) +{ + struct wrqe *wr; + struct ulp_mem_io *ulpmc; + struct ulptx_idata *ulpsc; + struct pagepod *ppod; + int i, j, k, n, chunk, len, ddp_pgsz; + u_int ppod_addr, offset; + uint32_t cmd; + struct ppod_region *pr = prsv->prsv_pr; + uintptr_t end_pva, pva, pa; + + cmd = htobe32(V_ULPTX_CMD(ULP_TX_MEM_WRITE)); + if (is_t4(sc)) + cmd |= htobe32(F_ULP_MEMIO_ORDER); + else + cmd |= htobe32(F_T5_ULP_MEMIO_IMM); + ddp_pgsz = 1 << pr->pr_page_shift[G_PPOD_PGSZ(prsv->prsv_tag)]; + offset = buf & PAGE_MASK; + ppod_addr = pr->pr_start + (prsv->prsv_tag & pr->pr_tag_mask); + pva = trunc_page(buf); + end_pva = trunc_page(buf + buflen - 1); + for (i = 0; i < prsv->prsv_nppods; ppod_addr += chunk) { + + /* How many page pods are we writing in this cycle */ + n = min(prsv->prsv_nppods - i, NUM_ULP_TX_SC_IMM_PPODS); + MPASS(n > 0); + chunk = PPOD_SZ(n); + len = roundup2(sizeof(*ulpmc) + sizeof(*ulpsc) + chunk, 16); + + wr = alloc_wrqe(len, wrq); + if (wr == NULL) + return (ENOMEM); /* ok to just bail out */ + ulpmc = wrtod(wr); + + INIT_ULPTX_WR(ulpmc, len, 0, 0); + ulpmc->cmd = cmd; + ulpmc->dlen = htobe32(V_ULP_MEMIO_DATA_LEN(chunk / 32)); + ulpmc->len16 = htobe32(howmany(len - sizeof(ulpmc->wr), 16)); + ulpmc->lock_addr = htobe32(V_ULP_MEMIO_ADDR(ppod_addr >> 5)); + + ulpsc = (struct ulptx_idata *)(ulpmc + 1); + ulpsc->cmd_more = htobe32(V_ULPTX_CMD(ULP_TX_SC_IMM)); + ulpsc->len = htobe32(chunk); + + ppod = (struct pagepod *)(ulpsc + 1); + for (j = 0; j < n; i++, j++, ppod++) { + ppod->vld_tid_pgsz_tag_color = htobe64(F_PPOD_VALID | + V_PPOD_TID(tid) | + (prsv->prsv_tag & ~V_PPOD_PGSZ(M_PPOD_PGSZ))); + ppod->len_offset = htobe64(V_PPOD_LEN(buflen) | + V_PPOD_OFST(offset)); + ppod->rsvd = 0; + + for (k = 0; k < nitems(ppod->addr); k++) { + if (pva > end_pva) + ppod->addr[k] = 0; + else { + pa = pmap_kextract(pva); + ppod->addr[k] = htobe64(pa); + pva += ddp_pgsz; + } +#if 0 + CTR5(KTR_CXGBE, + "%s: tid %d ppod[%d]->addr[%d] = %p", + __func__, tid, i, k, + htobe64(ppod->addr[k])); +#endif + } + + /* + * Walk back 1 segment so that the first address in the + * next pod is the same as the last one in the current + * pod. + */ + pva -= ddp_pgsz; + } + + t4_wrq_tx(sc, wr); + } + + MPASS(pva <= end_pva); + + return (0); +} + static void wire_pageset(struct pageset *ps) { diff --git a/sys/dev/cxgbe/tom/t4_tom.h b/sys/dev/cxgbe/tom/t4_tom.h index eae4b92355ac..48223b0d95d4 100644 --- a/sys/dev/cxgbe/tom/t4_tom.h +++ b/sys/dev/cxgbe/tom/t4_tom.h @@ -366,8 +366,12 @@ int t4_init_ppod_region(struct ppod_region *, struct t4_range *, u_int, const char *); void t4_free_ppod_region(struct ppod_region *); int t4_alloc_page_pods_for_ps(struct ppod_region *, struct pageset *); +int t4_alloc_page_pods_for_buf(struct ppod_region *, vm_offset_t, int, + struct ppod_reservation *); int t4_write_page_pods_for_ps(struct adapter *, struct sge_wrq *, int, struct pageset *); +int t4_write_page_pods_for_buf(struct adapter *, struct sge_wrq *, int tid, + struct ppod_reservation *, vm_offset_t, int); void t4_free_page_pods(struct ppod_reservation *); int t4_soreceive_ddp(struct socket *, struct sockaddr **, struct uio *, struct mbuf **, struct mbuf **, int *); From ff9b61ca075659efd790dd8109b4680f2ac8ea61 Mon Sep 17 00:00:00 2001 From: Eric Joyner Date: Thu, 1 Sep 2016 01:08:18 +0000 Subject: [PATCH 84/86] Fix linker warnings (errors on gcc) that resulted from r304510. The variables that are extern in the netmap header file should be defined in ixl_txrx.c (the file that is included in both ixl(4)/ixlv(4), not in the main driver source files. Reported by: ed@, dim@, ngie@ --- sys/dev/ixl/if_ixlv.c | 5 ----- sys/dev/ixl/ixl_txrx.c | 1 + sys/dev/netmap/if_ixl_netmap.h | 1 - 3 files changed, 1 insertion(+), 6 deletions(-) diff --git a/sys/dev/ixl/if_ixlv.c b/sys/dev/ixl/if_ixlv.c index c230338bbbec..c447c34689ee 100644 --- a/sys/dev/ixl/if_ixlv.c +++ b/sys/dev/ixl/if_ixlv.c @@ -217,11 +217,6 @@ TUNABLE_INT("hw.ixlv.tx_itr", &ixlv_tx_itr); SYSCTL_INT(_hw_ixlv, OID_AUTO, tx_itr, CTLFLAG_RDTUN, &ixlv_tx_itr, 0, "TX Interrupt Rate"); -/* Fix when building as a standalone module when netmap is enabled */ -#if defined(DEV_NETMAP) && !defined(NETMAP_IXL_MAIN) -int ixl_rx_miss, ixl_rx_miss_bufs, ixl_crcstrip; -#endif - /********************************************************************* * Device identification routine * diff --git a/sys/dev/ixl/ixl_txrx.c b/sys/dev/ixl/ixl_txrx.c index 5cf54fa9410a..9a7fae3b055f 100644 --- a/sys/dev/ixl/ixl_txrx.c +++ b/sys/dev/ixl/ixl_txrx.c @@ -69,6 +69,7 @@ static inline u32 ixl_get_tx_head(struct ixl_queue *que); #ifdef DEV_NETMAP #include +int ixl_rx_miss, ixl_rx_miss_bufs, ixl_crcstrip = 1; #endif /* DEV_NETMAP */ /* diff --git a/sys/dev/netmap/if_ixl_netmap.h b/sys/dev/netmap/if_ixl_netmap.h index f7e7baaf6bc2..2c7f9be541b3 100644 --- a/sys/dev/netmap/if_ixl_netmap.h +++ b/sys/dev/netmap/if_ixl_netmap.h @@ -71,7 +71,6 @@ SYSCTL_DECL(_dev_netmap); /* * The xl driver by default strips CRCs and we do not override it. */ -int ixl_rx_miss, ixl_rx_miss_bufs, ixl_crcstrip = 1; #if 0 SYSCTL_INT(_dev_netmap, OID_AUTO, ixl_crcstrip, CTLFLAG_RW, &ixl_crcstrip, 1, "strip CRC on rx frames"); From da2ded65755a2e02411931c6dfeb59ad82c60d2d Mon Sep 17 00:00:00 2001 From: Patrick Kelsey Date: Thu, 1 Sep 2016 02:05:46 +0000 Subject: [PATCH 85/86] _taskqueue_start_threads() now fails if it doesn't actually start any threads. Reviewed by: jhb MFC after: 1 week Differential Revision: https://reviews.freebsd.org/D7701 --- sys/kern/subr_taskqueue.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/sys/kern/subr_taskqueue.c b/sys/kern/subr_taskqueue.c index 5a20148f573c..21476e6674c3 100644 --- a/sys/kern/subr_taskqueue.c +++ b/sys/kern/subr_taskqueue.c @@ -625,6 +625,11 @@ _taskqueue_start_threads(struct taskqueue **tqp, int count, int pri, } else tq->tq_tcount++; } + if (tq->tq_tcount == 0) { + free(tq->tq_threads, M_TASKQUEUE); + tq->tq_threads = NULL; + return (ENOMEM); + } for (i = 0; i < count; i++) { if (tq->tq_threads[i] == NULL) continue; From eab5e7a376e04f73763bac742ad8082733da00a5 Mon Sep 17 00:00:00 2001 From: Enji Cooper Date: Thu, 1 Sep 2016 02:42:11 +0000 Subject: [PATCH 86/86] Don't bake all of CC/CPP/CXX into CFLAGS Capture executable names for CC, CPP, CXX (assumed to be the first non-CCACHE_BIN word). This change strips out all of the cross-compiler arguments, (-target, -B, etc), added to ${CC}, etc via ${CROSSENV} in Makefile.inc1, so it doesn't infect the build and subsequently the test. Add comments noting why this logic is being added, and why the logic in r305041 was necessary/what it was trying to achieve. This is required after recent changes made to the toolchain to always specify --sysroot, -target, -B, etc with clang in buildworld (presumably r304681). Reviewed by: rodrigc (earlier version) Reported by: Jenkins (FreeBSD_HEAD job from 559+) MFC after: 12 days X-MFC with: r304681, r305041 Sponsored by: EMC / Isilon Storage Division Differential Revision: https://reviews.freebsd.org/D7732 --- lib/atf/libatf-c/Makefile | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/lib/atf/libatf-c/Makefile b/lib/atf/libatf-c/Makefile index fbdc40497e4b..4b9ccd2e7fca 100644 --- a/lib/atf/libatf-c/Makefile +++ b/lib/atf/libatf-c/Makefile @@ -28,6 +28,18 @@ .include .include +# Store the toolchain executable in ATF_BUILD_{CC,CPP,CXX} to ensure other +# values -- like -target, -B ..., etc -- don't get leaked into the tests. +# +# Be sure to omit ${CCACHE_BIN} (if specified) from the variable as it gets +# automatically appended to the variables in bsd.compiler.mk when +# ${MK_CCACHE_BUILD} != no. +ATF_BUILD_CC:= ${CC:N${CCACHE_BIN}:[1]} +ATF_BUILD_CPP:= ${CPP:N${CCACHE_BIN}:[1]} +ATF_BUILD_CXX:= ${CXX:N${CCACHE_BIN}:[1]} + +# Only capture defines, includes, linker flags, optimization levels, warnings +# and preprocessor flags when building ATF_BUILD_{C,CPP,CXX}FLAGS. ATF_BUILD_CFLAGS:= ${CFLAGS:M-[DILOWf]*} ATF_BUILD_CPPFLAGS:= ${CPPFLAGS:M-[DILOWf]*} ATF_BUILD_CXXFLAGS:= ${CXXFLAGS:M-[DILOWf]*} @@ -41,11 +53,11 @@ ATF= ${SRCTOP}/contrib/atf .PATH: ${ATF}/atf-c .PATH: ${ATF}/atf-c/detail -CFLAGS+= -DATF_BUILD_CC='"${CC}"' +CFLAGS+= -DATF_BUILD_CC='"${ATF_BUILD_CC}"' CFLAGS+= -DATF_BUILD_CFLAGS='"${ATF_BUILD_CFLAGS}"' -CFLAGS+= -DATF_BUILD_CPP='"${CPP}"' +CFLAGS+= -DATF_BUILD_CPP='"${ATF_BUILD_CPP}"' CFLAGS+= -DATF_BUILD_CPPFLAGS='"${ATF_BUILD_CPPFLAGS}"' -CFLAGS+= -DATF_BUILD_CXX='"${CXX}"' +CFLAGS+= -DATF_BUILD_CXX='"${ATF_BUILD_CXX}"' CFLAGS+= -DATF_BUILD_CXXFLAGS='"${ATF_BUILD_CXXFLAGS}"' CFLAGS+= -I${ATF} CFLAGS+= -I${.CURDIR}