diff options
author | Jerry Jelinek <jerry.jelinek@joyent.com> | 2019-11-27 12:40:58 +0000 |
---|---|---|
committer | Jerry Jelinek <jerry.jelinek@joyent.com> | 2019-11-27 12:40:58 +0000 |
commit | 0b9ea52a4deeddf07798ece50f1c75d7de101baa (patch) | |
tree | 23e4dc323ed06dbd274c969bdd51e371fad0dd9f | |
parent | a0fae2e039f343951fa97d02c576ee3d45c877d1 (diff) | |
parent | c5832a5333c189dfa346a3c1edac9fa39e1de4cb (diff) | |
download | illumos-joyent-0b9ea52a4deeddf07798ece50f1c75d7de101baa.tar.gz |
[illumos-gate merge]
commit c5832a5333c189dfa346a3c1edac9fa39e1de4cb
12002 async unlinked drain
commit e2336878c3b2087bcf5c52436847f37afaec8666
11960 Add topo module and hdl api for freeing string array
commit bb51a979b2badfaa6cf79bcb781b23aa6c1502f2
12021 zfs_diff tests missing Makefile deps
commit 05c00ec58206e104da9853d2117cf39602f4d5ee
12010 extra whitespace in mmap(2)
commit f52943a93040563107b95bccb9db87d9971ef47d
12016 Use of GNU ld should explicitly specify the required output format
commit a64e1e23aa6dde2e865402bb20dde999f835fdc5
11996 format: modify should not ask for GPT partition 7
commit d30992fa3989ef47543839be59b8c86165285ec4
11995 format: efi usable size is missing 1 sector
Conflicts:
usr/src/lib/fm/topo/libtopo/common/topo_string.c
usr/src/lib/fm/topo/libtopo/common/topo_mod.h
usr/src/lib/fm/topo/libtopo/common/mapfile-vers
30 files changed, 326 insertions, 62 deletions
diff --git a/usr/src/boot/sys/boot/Makefile.inc b/usr/src/boot/sys/boot/Makefile.inc index 624d4e912c..4d030cdb59 100644 --- a/usr/src/boot/sys/boot/Makefile.inc +++ b/usr/src/boot/sys/boot/Makefile.inc @@ -12,6 +12,7 @@ # # Copyright 2017 Toomas Soome <tsoome@me.com> # Copyright 2019 Joyent, Inc. +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # # loader.help build needs better awk @@ -21,6 +22,9 @@ OBJCOPY= $(GNU_ROOT)/bin/gobjcopy OBJDUMP= $(GNU_ROOT)/bin/gobjdump GSTRIP= $(GNU_ROOT)/bin/gstrip +GLDTARGET= -melf_i386_sol2 +LDFLAGS += $(GLDTARGET) + # Default Console font setup. # We want it to be the same as kernel. # We build compressed, stripped down version of the default font, so we have diff --git a/usr/src/boot/sys/boot/i386/btx/btx/Makefile b/usr/src/boot/sys/boot/i386/btx/btx/Makefile index a83818bab6..da8b3e7d4f 100644 --- a/usr/src/boot/sys/boot/i386/btx/btx/Makefile +++ b/usr/src/boot/sys/boot/i386/btx/btx/Makefile @@ -11,6 +11,7 @@ # # Copyright 2015 Toomas Soome <tsoome@me.com> +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include $(SRC)/Makefile.master @@ -41,7 +42,7 @@ CPPFLAGS += -I./../../common ORG= 0x9000 -LDFLAGS=-e start -Ttext ${ORG} -N -S --oformat binary +LDFLAGS=-e start -Ttext ${ORG} -N -S --oformat binary $(GLDTARGET) all install: $(PROG) diff --git a/usr/src/boot/sys/boot/i386/btx/btxldr/Makefile b/usr/src/boot/sys/boot/i386/btx/btxldr/Makefile index b68ebcafe4..c209ba4ab4 100644 --- a/usr/src/boot/sys/boot/i386/btx/btxldr/Makefile +++ b/usr/src/boot/sys/boot/i386/btx/btxldr/Makefile @@ -11,6 +11,7 @@ # # Copyright 2015 Toomas Soome <tsoome@me.com> +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include $(SRC)/Makefile.master @@ -25,7 +26,7 @@ CPPFLAGS += -DLOADER_ADDRESS=${LOADER_ADDRESS} CPPFLAGS += -DBTXLDR_VERBOSE CPPFLAGS += -I./../../common -LDFLAGS=-e start -Ttext ${LOADER_ADDRESS} -N -S --oformat binary +LDFLAGS=-e start -Ttext ${LOADER_ADDRESS} -N -S --oformat binary $(GLDTARGET) all install: $(PROG) diff --git a/usr/src/boot/sys/boot/i386/btx/lib/Makefile b/usr/src/boot/sys/boot/i386/btx/lib/Makefile index 0c797d37e5..864a519441 100644 --- a/usr/src/boot/sys/boot/i386/btx/lib/Makefile +++ b/usr/src/boot/sys/boot/i386/btx/lib/Makefile @@ -11,6 +11,7 @@ # # Copyright 2015 Toomas Soome <tsoome@me.com> +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include $(SRC)/Makefile.master @@ -23,7 +24,7 @@ PROG= crt0.o SRCS= btxcsu.S btxsys.s btxv86.s OBJS= btxcsu.o btxsys.o btxv86.o -LDFLAGS =-r +LDFLAGS = -r $(GLDTARGET) all install: $(PROG) diff --git a/usr/src/boot/sys/boot/i386/cdboot/Makefile b/usr/src/boot/sys/boot/i386/cdboot/Makefile index 490029e558..31e684c922 100644 --- a/usr/src/boot/sys/boot/i386/cdboot/Makefile +++ b/usr/src/boot/sys/boot/i386/cdboot/Makefile @@ -11,6 +11,7 @@ # # Copyright 2015 Toomas Soome <tsoome@me.com> +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include $(SRC)/Makefile.master @@ -24,10 +25,9 @@ FILEMODE=0444 SRCS= ${PROG}.S OBJS= $(SRCS:%.S=%.o) - ORG= 0x7c00 -LDFLAGS=-e start -Ttext $(ORG) -N -S --oformat binary +LDFLAGS=-e start -Ttext $(ORG) -N -S --oformat binary $(GLDTARGET) all: ${PROG} diff --git a/usr/src/boot/sys/boot/i386/pmbr/Makefile b/usr/src/boot/sys/boot/i386/pmbr/Makefile index 0d24fd2e90..b7905c92f2 100644 --- a/usr/src/boot/sys/boot/i386/pmbr/Makefile +++ b/usr/src/boot/sys/boot/i386/pmbr/Makefile @@ -11,6 +11,7 @@ # # Copyright 2015 Toomas Soome <tsoome@me.com> +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # # @@ -28,7 +29,7 @@ SRCS= $(OBJS:%.o=%.s) ORG= 0x600 -LDFLAGS=-e start -Ttext ${ORG} -N -S --oformat binary +LDFLAGS=-e start -Ttext ${ORG} -N -S --oformat binary $(GLDTARGET) all: $(PROG) diff --git a/usr/src/cmd/format/io.c b/usr/src/cmd/format/io.c index d0953a59d6..dd0cbc2397 100644 --- a/usr/src/cmd/format/io.c +++ b/usr/src/cmd/format/io.c @@ -1561,7 +1561,7 @@ or g(gigabytes)\n"); reserved = efi_reserved_sectors(cur_parts->etoc); return (bounds->upper - reserved - - efi_deflt->start_sector); + efi_deflt->start_sector + 1); } /* diff --git a/usr/src/cmd/format/modify_partition.c b/usr/src/cmd/format/modify_partition.c index d01463e757..8f4905b594 100644 --- a/usr/src/cmd/format/modify_partition.c +++ b/usr/src/cmd/format/modify_partition.c @@ -564,7 +564,8 @@ get_user_map_efi(map, float_part) reserved = efi_reserved_sectors(map); for (i = 0; i < map->efi_nparts - 1; i++) { - if (i == float_part) + /* GPT partition 7 is whole disk device, minor node "wd" */ + if (i == float_part || i == 7) continue; ioparam.io_bounds.lower = start_lba; @@ -589,10 +590,10 @@ get_user_map_efi(map, float_part) start_lba += i64; } map->efi_parts[float_part].p_start = start_lba; - map->efi_parts[float_part].p_size = map->efi_last_u_lba - + map->efi_parts[float_part].p_size = map->efi_last_u_lba + 1 - start_lba - reserved; map->efi_parts[float_part].p_tag = V_USR; - if (map->efi_parts[float_part].p_size == UINT_MAX64) { + if (map->efi_parts[float_part].p_size == 0) { map->efi_parts[float_part].p_size = 0; map->efi_parts[float_part].p_start = 0; map->efi_parts[float_part].p_tag = V_UNASSIGNED; @@ -602,7 +603,7 @@ get_user_map_efi(map, float_part) for (i = 0; i < map->efi_nparts; i++) { if (map->efi_parts[i].p_tag == V_RESERVED) { map->efi_parts[i].p_start = map->efi_last_u_lba - - reserved; + reserved + 1; map->efi_parts[i].p_size = reserved; break; } diff --git a/usr/src/grub/grub-0.97/Makefile.solaris.defs b/usr/src/grub/grub-0.97/Makefile.solaris.defs index faf41925c6..86e79c484b 100644 --- a/usr/src/grub/grub-0.97/Makefile.solaris.defs +++ b/usr/src/grub/grub-0.97/Makefile.solaris.defs @@ -2,6 +2,7 @@ # Copyright 2005 Sun Microsystems, Inc. All rights reserved. # Use is subject to license terms. # Copyright 2016 Nexenta Systems, Inc. +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include $(SRC)/Makefile.master @@ -70,6 +71,7 @@ CPPFLAGS = $(DEFS) $(INCLUDES) $(WARNFLAGS) \ $(t.ENVCPPFLAGS4:I,%=-nostdinc -isystem %) CCLD = $(GNU_ROOT)/bin/gld +GLDTARGET = -melf_i386_sol2 LDFLAGS = $(BASE_LDFLAGS) LINKFLAGS = -g LINK = $(CCLD) $(LINKFLAGS) $(LDFLAGS) diff --git a/usr/src/grub/grub-0.97/stage1/Makefile.solaris b/usr/src/grub/grub-0.97/stage1/Makefile.solaris index d5d34b9d1f..2873a21a17 100644 --- a/usr/src/grub/grub-0.97/stage1/Makefile.solaris +++ b/usr/src/grub/grub-0.97/stage1/Makefile.solaris @@ -2,7 +2,7 @@ # Copyright 2005 Sun Microsystems, Inc. All rights reserved. # Use is subject to license terms. # -# ident "%Z%%M% %I% %E% SMI" +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include ../../Makefile.grub include ../Makefile.solaris.defs @@ -13,10 +13,9 @@ include ../Makefile.solaris.defs .exec: $(OBJCOPY) -O binary $< $@ - INCLUDES = -I. -I.. CCASFLAGS += -O2 -fno-builtin -nostdinc -LDFLAGS += -nostdlib -N -Ttext 7C00 +LDFLAGS += -nostdlib -N -Ttext 7C00 $(GLDTARGET) LIBS = diff --git a/usr/src/grub/grub-0.97/stage2/Makefile.solaris b/usr/src/grub/grub-0.97/stage2/Makefile.solaris index 925092fd4d..1c70f2a71b 100644 --- a/usr/src/grub/grub-0.97/stage2/Makefile.solaris +++ b/usr/src/grub/grub-0.97/stage2/Makefile.solaris @@ -4,6 +4,7 @@ # Copyright (c) 2013 by Saso Kiselkov. All rights reserved. # Copyright 2015, OmniTI Computer Consulting, Inc. All rights reserved. # Copyright 2016 Nexenta Systems, Inc. +# Copyright 2019 OmniOS Community Edition (OmniOSce) Association. # include ../../Makefile.grub include ../Makefile.solaris.defs @@ -43,12 +44,12 @@ STAGE2_CFLAGS = -Os -fno-builtin -nostdinc \ $(STAGE2_NETBOOT)STAGE2_CFLAGS += $(NETBOOT_CFLAGS) #STAGE2_CFLAGS += $(HERCULES_CFLAGS) -NBLOADER_LINK = -nostdlib -N -Ttext 0 -PRE_STAGE2_LINK = -nostdlib -N -Ttext 8200 -PXELOADER_LINK = -nostdlib -N -Ttext 7C00 -STAGE1_5_LINK = -nostdlib -N -Ttext 2000 -START_ELTORITO_LINK = -nostdlib -N -Ttext 7C00 -START_LINK = -nostdlib -N -Ttext 8000 +NBLOADER_LINK = -nostdlib -N -Ttext 0 $(GLDTARGET) +PRE_STAGE2_LINK = -nostdlib -N -Ttext 8200 $(GLDTARGET) +PXELOADER_LINK = -nostdlib -N -Ttext 7C00 $(GLDTARGET) +STAGE1_5_LINK = -nostdlib -N -Ttext 2000 $(GLDTARGET) +START_ELTORITO_LINK = -nostdlib -N -Ttext 7C00 $(GLDTARGET) +START_LINK = -nostdlib -N -Ttext 8000 $(GLDTARGET) LIBDRIVERS = ../netboot/libdrivers.a @@ -446,13 +447,13 @@ REISERFS_STAGE1_5_OBJS = reiserfs_stage1_5_exec-bios.o \ reiserfs_stage1_5_exec-fsys_reiserfs.o \ reiserfs_stage1_5_exec-moddiv.o \ reiserfs_stage1_5_exec-stage1_5.o - + $(REISERFS_STAGE1_5_EXEC) := LDFLAGS = $(BASE_LDFLAGS) $(STAGE1_5_LINK) - + $(REISERFS_STAGE1_5_ASMOBJS) := CCASFLAGS = $(BASE_CCASFLAGS) \ $(STAGE1_5_CFLAGS) \ -DFSYS_REISERFS=1 -DNO_BLOCK_FILES=1 - + $(REISERFS_STAGE1_5_OBJS) := CFLAGS = $(BASE_CFLAGS) $(STAGE1_5_CFLAGS) \ -DFSYS_REISERFS=1 -DNO_BLOCK_FILES=1 @@ -678,7 +679,7 @@ $(LIBGRUB_OBJS): $$(@:libgrub_a-%.o=%.c) # # Diskless # -$(DISKLESS_EXEC): $(DISKLESS_ASMOBJS) $(DISKLESS_OBJS) +$(DISKLESS_EXEC): $(DISKLESS_ASMOBJS) $(DISKLESS_OBJS) $(RM) $@ $(LINK) -o $@ $(DISKLESS_ASMOBJS) $(DISKLESS_OBJS) $(LIBS) diff --git a/usr/src/lib/fm/topo/libtopo/common/topo_2xml.c b/usr/src/lib/fm/topo/libtopo/common/topo_2xml.c index 768d47d182..853a373f2b 100644 --- a/usr/src/lib/fm/topo/libtopo/common/topo_2xml.c +++ b/usr/src/lib/fm/topo/libtopo/common/topo_2xml.c @@ -318,10 +318,7 @@ txml_print_prop(topo_hdl_t *thp, FILE *fp, tnode_t *node, const char *pgname, begin_end_element(fp, Propitem, Value, val[i], NULL); } - for (uint_t i = 0; i < nelem; i++) { - topo_hdl_strfree(thp, val[i]); - } - topo_hdl_free(thp, val, nelem * sizeof (char *)); + topo_hdl_strfreev(thp, val, nelem); end_element(fp, Propval); break; diff --git a/usr/src/lib/fm/topo/libtopo/common/topo_string.c b/usr/src/lib/fm/topo/libtopo/common/topo_string.c index 2a656062e6..bca2bdc66a 100644 --- a/usr/src/lib/fm/topo/libtopo/common/topo_string.c +++ b/usr/src/lib/fm/topo/libtopo/common/topo_string.c @@ -59,7 +59,7 @@ topo_hdl_strfree(topo_hdl_t *thp, char *s) void topo_hdl_strfreev(topo_hdl_t *thp, char **strarr, uint_t nelem) { - for (int i = 0; i < nelem; i++) + for (uint_t i = 0; i < nelem; i++) topo_hdl_strfree(thp, strarr[i]); topo_hdl_free(thp, strarr, (nelem * sizeof (char *))); diff --git a/usr/src/lib/fm/topo/modules/i86pc/chip/chip_serial.c b/usr/src/lib/fm/topo/modules/i86pc/chip/chip_serial.c index d2082b1b54..87b152c237 100644 --- a/usr/src/lib/fm/topo/modules/i86pc/chip/chip_serial.c +++ b/usr/src/lib/fm/topo/modules/i86pc/chip/chip_serial.c @@ -23,6 +23,9 @@ * Copyright 2009 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ +/* + * Copyright 2019 Joyent, Inc. + */ #include <stdio.h> #include <stdlib.h> @@ -144,7 +147,7 @@ ipmi_serial_lookup(topo_mod_t *mod, char *ipmi_tag, char *buf) * The components are: * * yyyy: JEDEC ID in hex (2 byte manufacture ID, 2 byte continuation - * code). + * code). * * ll: The memory module's manufacturing location. * @@ -233,9 +236,7 @@ get_dimm_serial(topo_mod_t *mod, tnode_t *node, topo_version_t vers, /* topo errno already set */ rv = -1; } - for (i = 0; i < nelems; i++) - topo_mod_strfree(mod, entity_refs[i]); - topo_mod_free(mod, entity_refs, (nelems * sizeof (char *))); + topo_mod_strfreev(mod, entity_refs, nelems); return (rv); } diff --git a/usr/src/man/man2/mmap.2 b/usr/src/man/man2/mmap.2 index bb17b99de7..bd95617ae3 100644 --- a/usr/src/man/man2/mmap.2 +++ b/usr/src/man/man2/mmap.2 @@ -45,12 +45,12 @@ .\" Copyright (c) 2009, Sun Microsystems, Inc. All Rights Reserved. .\" Copyright 2013 OmniTI Computer Consulting, Inc. All Rights Reserved. .\" Copyright 2016 James S Blachly, MD. All Rights Reserved. +.\" Copyright 2019 Joyent, Inc. .\" -.TH MMAP 2 "August 29, 2016" +.TH MMAP 2 "Nov 19, 2019" .SH NAME mmap \- map pages of memory .SH SYNOPSIS -.LP .nf #include <sys/mman.h> @@ -59,7 +59,6 @@ mmap \- map pages of memory .fi .SH DESCRIPTION -.LP The \fBmmap()\fR function establishes a mapping between a process's address space and a file or shared memory object. The format of the call is as follows: .sp @@ -71,7 +70,7 @@ space and a file or shared memory object. The format of the call is as follows: The \fBmmap()\fR function establishes a mapping between the address space of the process at an address \fIpa\fR for \fIlen\fR bytes to the memory object represented by the file descriptor \fIfildes\fR at offset \fIoff\fR for -\fIlen\fR bytes. The value of \fIpa\fR is a function of the \fIaddr\fR +\fIlen\fR bytes. The value of \fIpa\fR is a function of the \fIaddr\fR argument and values of \fIflags\fR, further described below. A successful \fBmmap()\fR call returns \fIpa\fR as its result. The address range starting at \fIpa\fR and continuing for \fIlen\fR bytes will be legitimate for the possible @@ -105,7 +104,7 @@ The \fBmmap()\fR function is supported for regular files and shared memory objects. Support for any other type of file is unspecified. .sp .LP -The \fIprot\fR argument determines whether read, write, execute, or some +The \fIprot\fR argument determines whether read, write, execute, or some combination of accesses are permitted to the data being mapped. The \fIprot\fR argument should be either \fBPROT_NONE\fR or the bitwise inclusive \fBOR\fR of one or more of the other flags in the following table, defined in the header @@ -165,7 +164,7 @@ descriptor \fIfildes\fR with write permission unless \fBMAP_PRIVATE\fR is specified in the \fIflags\fR argument as described below. .sp .LP -The \fIflags\fR argument provides other information about the handling of the +The \fIflags\fR argument provides other information about the handling of the mapped data. The value of \fIflags\fR is the bitwise inclusive \fBOR\fR of these options, defined in <\fBsys/mman.h\fR>: .sp @@ -304,7 +303,7 @@ data or stack "segments". When \fBMAP_ALIGN\fR is set, the system is informed that the alignment of \fIpa\fR must be the same as \fIaddr\fR. The alignment value in \fIaddr\fR must be 0 or some power of two multiple of page size as returned by -\fBsysconf\fR(3C). If addr is 0, the system will choose a suitable alignment. +\fBsysconf\fR(3C). If addr is 0, the system will choose a suitable alignment. .sp .LP The \fBMAP_NORESERVE\fR option specifies that no swap space be reserved for a @@ -312,11 +311,11 @@ mapping. Without this flag, the creation of a writable \fBMAP_PRIVATE\fR mapping reserves swap space equal to the size of the mapping; when the mapping is written into, the reserved space is employed to hold private copies of the data. A write into a \fBMAP_NORESERVE\fR mapping produces results which depend -on the current availability of swap space in the system. If space is -available, the write succeeds and a private copy of the written page is +on the current availability of swap space in the system. If space is +available, the write succeeds and a private copy of the written page is created; if space is not available, the write fails and a \fBSIGBUS\fR or \fBSIGSEGV\fR signal is delivered to the writing process. \fBMAP_NORESERVE\fR -mappings are inherited across \fBfork()\fR; at the time of the \fBfork()\fR, +mappings are inherited across \fBfork()\fR; at the time of the \fBfork()\fR, swap space is reserved in the child for all private pages that currently exist in the parent; thereafter the child's mapping behaves as described above. .sp @@ -358,7 +357,7 @@ The \fIoff\fR argument is constrained to be aligned and sized according to the value returned by \fBsysconf()\fR when passed \fB_SC_PAGESIZE\fR or \fB_SC_PAGE_SIZE\fR. When \fBMAP_FIXED\fR is specified, the \fIaddr\fR argument must also meet these constraints. The system performs mapping operations over -whole pages. Thus, while the \fIlen\fR argument need not meet a size or +whole pages. Thus, while the \fIlen\fR argument need not meet a size or alignment constraint, the system will include, in any mapping operation, any partial page specified by the range [\fIpa, pa + len\fR). .sp @@ -712,7 +711,6 @@ application: .RE .SH RETURN VALUES -.LP Upon successful completion, the \fBmmap()\fR function returns the address at which the mapping was placed (\fIpa\fR); otherwise, it returns a value of \fBMAP_FAILED\fR and sets \fBerrno\fR to indicate the error. The symbol @@ -724,7 +722,6 @@ If \fBmmap()\fR fails for reasons other than \fBEBADF\fR, \fBEINVAL\fR or \fBENOTSUP\fR, some of the mappings in the address range starting at \fIaddr\fR and continuing for \fIlen\fR bytes may have been unmapped. .SH ERRORS -.LP The \fBmmap()\fR function will fail if: .sp .ne 2 @@ -820,7 +817,7 @@ The mapping could not be locked in memory, if required by \fBmlockall\fR(3C), because it would require more space than the system is able to supply. .sp The composite size of \fIlen\fR plus the lengths obtained from all previous -calls to \fBmmap()\fR exceeds \fBRLIMIT_VMEM\fR (see \fBgetrlimit\fR(2)). +calls to \fBmmap()\fR exceeds \fBRLIMIT_VMEM\fR (see \fBgetrlimit\fR(2)). .RE .sp @@ -872,7 +869,6 @@ locking. See \fBfcntl\fR(2). .RE .SH USAGE -.LP Use of \fBmmap()\fR may reduce the amount of memory available to other memory allocation functions. .sp @@ -917,7 +913,7 @@ read(fildes, buf, len) .sp .LP -The following is a rewrite using \fBmmap()\fR: +The following is a rewrite using \fBmmap()\fR: .sp .in +2 .nf @@ -929,7 +925,6 @@ address = mmap((caddr_t) 0, len, (PROT_READ | PROT_WRITE), .in -2 .SH ATTRIBUTES -.LP See \fBattributes\fR(5) for descriptions of the following attributes: .sp @@ -946,7 +941,6 @@ MT-Level Async-Signal-Safe .TE .SH SEE ALSO -.LP \fBclose\fR(2), \fBexec\fR(2), \fBfcntl\fR(2), \fBfork\fR(2), \fBgetrlimit\fR(2), \fBmemcntl\fR(2), \fBmmapobj\fR(2), \fBmprotect\fR(2), \fBmunmap\fR(2), \fBshmat\fR(2), \fBlockf\fR(3C), \fBmlockall\fR(3C), diff --git a/usr/src/pkg/manifests/system-test-zfstest.mf b/usr/src/pkg/manifests/system-test-zfstest.mf index f5d7d5d07d..c3d98e063a 100644 --- a/usr/src/pkg/manifests/system-test-zfstest.mf +++ b/usr/src/pkg/manifests/system-test-zfstest.mf @@ -2619,6 +2619,8 @@ file path=opt/zfs-tests/tests/functional/mmp/setup mode=0555 file path=opt/zfs-tests/tests/functional/mount/cleanup mode=0555 file path=opt/zfs-tests/tests/functional/mount/setup mode=0555 file path=opt/zfs-tests/tests/functional/mount/umount_001 mode=0555 +file path=opt/zfs-tests/tests/functional/mount/umount_002 mode=0555 +file path=opt/zfs-tests/tests/functional/mount/umount_unlinked_drain mode=0555 file path=opt/zfs-tests/tests/functional/mount/umountall_001 mode=0555 file path=opt/zfs-tests/tests/functional/mv_files/cleanup mode=0555 file path=opt/zfs-tests/tests/functional/mv_files/mv_files.cfg mode=0444 diff --git a/usr/src/test/zfs-tests/runfiles/delphix.run b/usr/src/test/zfs-tests/runfiles/delphix.run index 3acbe9e343..a4b392cb9a 100644 --- a/usr/src/test/zfs-tests/runfiles/delphix.run +++ b/usr/src/test/zfs-tests/runfiles/delphix.run @@ -521,7 +521,7 @@ tests = ['mmp_on_thread', 'mmp_on_uberblocks', 'mmp_on_off', 'mmp_interval', 'mmp_on_zdb'] [/opt/zfs-tests/tests/functional/mount] -tests = ['umount_001', 'umountall_001'] +tests = ['umount_001', 'umount_002', 'umountall_001'] [/opt/zfs-tests/tests/functional/mv_files] tests = ['mv_files_001_pos', 'mv_files_002_pos'] diff --git a/usr/src/test/zfs-tests/runfiles/omnios.run b/usr/src/test/zfs-tests/runfiles/omnios.run index d03cbd9a6d..bc5698c864 100644 --- a/usr/src/test/zfs-tests/runfiles/omnios.run +++ b/usr/src/test/zfs-tests/runfiles/omnios.run @@ -521,7 +521,7 @@ tests = ['mmp_on_thread', 'mmp_on_uberblocks', 'mmp_on_off', 'mmp_interval', 'mmp_on_zdb'] [/opt/zfs-tests/tests/functional/mount] -tests = ['umount_001', 'umountall_001'] +tests = ['umount_001', 'umount_002', 'umountall_001'] [/opt/zfs-tests/tests/functional/mv_files] tests = ['mv_files_001_pos', 'mv_files_002_pos'] diff --git a/usr/src/test/zfs-tests/runfiles/openindiana.run b/usr/src/test/zfs-tests/runfiles/openindiana.run index 3c3675b5aa..6fcb6f724a 100644 --- a/usr/src/test/zfs-tests/runfiles/openindiana.run +++ b/usr/src/test/zfs-tests/runfiles/openindiana.run @@ -521,7 +521,7 @@ tests = ['mmp_on_thread', 'mmp_on_uberblocks', 'mmp_on_off', 'mmp_interval', 'mmp_on_zdb'] [/opt/zfs-tests/tests/functional/mount] -tests = ['umount_001', 'umountall_001'] +tests = ['umount_001', 'umount_002', 'umountall_001'] [/opt/zfs-tests/tests/functional/mv_files] tests = ['mv_files_001_pos', 'mv_files_002_pos'] diff --git a/usr/src/test/zfs-tests/runfiles/smartos.run b/usr/src/test/zfs-tests/runfiles/smartos.run index 8b326b874f..a9ce4c13d1 100644 --- a/usr/src/test/zfs-tests/runfiles/smartos.run +++ b/usr/src/test/zfs-tests/runfiles/smartos.run @@ -453,7 +453,7 @@ tests = ['mmp_on_thread', 'mmp_on_off', 'mmp_interval', 'mmp_on_zdb'] [/opt/zfs-tests/tests/functional/mount] -tests = ['umount_001', 'umountall_001'] +tests = ['umount_001', 'umount_002', 'umountall_001'] [/opt/zfs-tests/tests/functional/mv_files] tests = ['mv_files_001_pos', 'mv_files_002_pos'] diff --git a/usr/src/test/zfs-tests/tests/functional/cli_root/zfs_diff/Makefile b/usr/src/test/zfs-tests/tests/functional/cli_root/zfs_diff/Makefile index 5088e03386..d72a08c6f9 100644 --- a/usr/src/test/zfs-tests/tests/functional/cli_root/zfs_diff/Makefile +++ b/usr/src/test/zfs-tests/tests/functional/cli_root/zfs_diff/Makefile @@ -41,4 +41,6 @@ clobber: clean clean: -$(RM) $(OBJS) +$(TARGETDIR)/$(PROG): $(TARGETDIR) + include $(SRC)/test/zfs-tests/Makefile.com diff --git a/usr/src/test/zfs-tests/tests/functional/mount/umount_002.ksh b/usr/src/test/zfs-tests/tests/functional/mount/umount_002.ksh new file mode 100644 index 0000000000..c57d787e4c --- /dev/null +++ b/usr/src/test/zfs-tests/tests/functional/mount/umount_002.ksh @@ -0,0 +1,52 @@ +#! /usr/bin/ksh -p +# +# +# This file and its contents are supplied under the terms of the +# Common Development and Distribution License ("CDDL"), version 1.0. +# You may only use this file in accordance with the terms of version +# 1.0 of the CDDL. +# +# A full copy of the text of the CDDL should have accompanied this +# source. A copy of the CDDL is also available via the Internet at +# http://www.illumos.org/license/CDDL. +# + +# +# Copyright 2016 Nexenta Systems, Inc. All rights reserved. +# + +. $STF_SUITE/include/libtest.shlib + +# +# DESCRIPTION: +# zfs umount should not fail because flushing of DNLC +# uses async implementation of zfs_inactive +# +# STRATEGY: +# 1. Call zfs unmount/mount to be sure DNLC is empty +# 2. Create a lot of files +# 3. Call zfs unmount command +# 4. Make sure the file systems were unmounted +# 5. Mount them back +# + +for fs in 1 2 3; do + log_must mounted $TESTDIR.$fs + log_must zfs umount $TESTPOOL/$TESTFS.$fs + log_must unmounted $TESTDIR.$fs + log_must zfs mount $TESTPOOL/$TESTFS.$fs + log_must mounted $TESTDIR.$fs + + for fn in $(seq 1 8096); do + log_must dd if=/dev/urandom of=$TESTDIR.$fs/file$fn bs=1024 \ + count=1 + done + + log_must zfs umount $TESTPOOL/$TESTFS.$fs + log_must unmounted $TESTDIR.$fs + log_must zfs mount $TESTPOOL/$TESTFS.$fs + log_must mounted $TESTDIR.$fs + log_must rm -f $TESTDIR.$fs/file* +done + +log_pass "All file systems are unmounted" diff --git a/usr/src/test/zfs-tests/tests/functional/mount/umount_unlinked_drain.ksh b/usr/src/test/zfs-tests/tests/functional/mount/umount_unlinked_drain.ksh new file mode 100755 index 0000000000..0d2628079c --- /dev/null +++ b/usr/src/test/zfs-tests/tests/functional/mount/umount_unlinked_drain.ksh @@ -0,0 +1,119 @@ +#!/bin/ksh -p + +# +# This file and its contents are supplied under the terms of the +# Common Development and Distribution License ("CDDL"), version 1.0. +# You may only use this file in accordance with the terms of version +# 1.0 of the CDDL. +# +# A full copy of the text of the CDDL should have accompanied this +# source. A copy of the CDDL is also available via the Internet at +# http://www.illumos.org/license/CDDL. +# + +# +# Copyright 2018 Datto Inc. +# + +. $STF_SUITE/include/libtest.shlib + +# +# DESCRIPTION: +# Test async unlinked drain to ensure mounting is not held up when there are +# entries in the unlinked set. We also try to test that the list is able to be +# filled up and drained at the same time. +# +# STRATEGY: +# 1. Use zfs_unlink_suspend_progress tunable to disable freeing to build up +# the unlinked set +# 2. Make sure mount happens even when there are entries in the unlinked set +# 3. Drain and build up the unlinked list at the same time to test for races +# + +function cleanup +{ + log_must set_tunable32 zfs_unlink_suspend_progress $default_unlink_sp + for fs in $(seq 1 3); do + mounted $TESTDIR.$fs || zfs mount $TESTPOOL/$TESTFS.$fs + rm -f $TESTDIR.$fs/file-* + zfs set xattr=on $TESTPOOL/$TESTFS.$fs + done +} + +function unlinked_size_is +{ + MAX_ITERS=5 # iteration to do before we consider reported number stable + iters=0 + last_usize=0 + while [[ $iters -le $MAX_ITERS ]]; do + kstat_file=$(grep -nrwl /proc/spl/kstat/zfs/$2/objset-0x* -e $3) + nunlinks=`cat $kstat_file | grep nunlinks | awk '{print $3}'` + nunlinked=`cat $kstat_file | grep nunlinked | awk '{print $3}'` + usize=$(($nunlinks - $nunlinked)) + if [[ $iters == $MAX_ITERS && $usize == $1 ]]; then + return 0 + fi + if [[ $usize == $last_usize ]]; then + (( iters++ )) + else + iters=0 + fi + last_usize=$usize + done + + log_note "Unexpected unlinked set size: $last_usize, expected $1" + return 1 +} + + +UNLINK_SP_PARAM=/sys/module/zfs/parameters/zfs_unlink_suspend_progress +default_unlink_sp=$(get_tunable zfs_unlink_suspend_progress) + +log_onexit cleanup + +log_assert "Unlinked list drain does not hold up mounting of fs" + +for fs in 1 2 3; do + set -A xattrs on sa off + for xa in ${xattrs[@]}; do + # setup fs and ensure all deleted files got into unliked set + log_must mounted $TESTDIR.$fs + + log_must zfs set xattr=$xa $TESTPOOL/$TESTFS.$fs + + if [[ $xa == off ]]; then + for fn in $(seq 1 175); do + log_must mkfile 128k $TESTDIR.$fs/file-$fn + done + else + log_must xattrtest -f 175 -x 3 -r -k -p $TESTDIR.$fs + fi + + log_must set_tunable32 zfs_unlink_suspend_progress 1 + log_must unlinked_size_is 0 $TESTPOOL $TESTPOOL/$TESTFS.$fs + + # build up unlinked set + for fn in $(seq 1 100); do + log_must eval "rm $TESTDIR.$fs/file-$fn &" + done + log_must unlinked_size_is 100 $TESTPOOL $TESTPOOL/$TESTFS.$fs + + # test that we can mount fs without emptying the unlinked list + log_must zfs umount $TESTPOOL/$TESTFS.$fs + log_must unmounted $TESTDIR.$fs + log_must zfs mount $TESTPOOL/$TESTFS.$fs + log_must mounted $TESTDIR.$fs + log_must unlinked_size_is 100 $TESTPOOL $TESTPOOL/$TESTFS.$fs + + # confirm we can drain and add to unlinked set at the same time + log_must set_tunable32 zfs_unlink_suspend_progress 0 + log_must zfs umount $TESTPOOL/$TESTFS.$fs + log_must zfs mount $TESTPOOL/$TESTFS.$fs + for fn in $(seq 101 175); do + log_must eval "rm $TESTDIR.$fs/file-$fn &" + done + log_must unlinked_size_is 0 $TESTPOOL $TESTPOOL/$TESTFS.$fs + done +done + +log_pass "Confirmed unlinked list drain does not hold up mounting of fs" diff --git a/usr/src/uts/common/fs/zfs/dsl_pool.c b/usr/src/uts/common/fs/zfs/dsl_pool.c index 8564900fc9..d3901c6f79 100644 --- a/usr/src/uts/common/fs/zfs/dsl_pool.c +++ b/usr/src/uts/common/fs/zfs/dsl_pool.c @@ -222,6 +222,9 @@ dsl_pool_open_impl(spa_t *spa, uint64_t txg) dp->dp_vnrele_taskq = taskq_create("zfs_vn_rele_taskq", 1, minclsyspri, 1, 4, 0); + dp->dp_unlinked_drain_taskq = taskq_create("z_unlinked_drain", + max_ncpus, minclsyspri, max_ncpus, INT_MAX, + TASKQ_PREPOPULATE | TASKQ_DYNAMIC); return (dp); } @@ -403,6 +406,7 @@ dsl_pool_close(dsl_pool_t *dp) rrw_destroy(&dp->dp_config_rwlock); mutex_destroy(&dp->dp_lock); + taskq_destroy(dp->dp_unlinked_drain_taskq); taskq_destroy(dp->dp_vnrele_taskq); if (dp->dp_blkstats != NULL) kmem_free(dp->dp_blkstats, sizeof (zfs_all_blkstats_t)); @@ -1078,6 +1082,12 @@ dsl_pool_vnrele_taskq(dsl_pool_t *dp) return (dp->dp_vnrele_taskq); } +taskq_t * +dsl_pool_unlinked_drain_taskq(dsl_pool_t *dp) +{ + return (dp->dp_unlinked_drain_taskq); +} + /* * Walk through the pool-wide zap object of temporary snapshot user holds * and release them. diff --git a/usr/src/uts/common/fs/zfs/sys/dsl_pool.h b/usr/src/uts/common/fs/zfs/sys/dsl_pool.h index de13fa8bfa..cda8324da6 100644 --- a/usr/src/uts/common/fs/zfs/sys/dsl_pool.h +++ b/usr/src/uts/common/fs/zfs/sys/dsl_pool.h @@ -93,6 +93,7 @@ typedef struct dsl_pool { struct dsl_dataset *dp_origin_snap; uint64_t dp_root_dir_obj; taskq_t *dp_vnrele_taskq; + struct taskq *dp_unlinked_drain_taskq; /* No lock needed - sync context only */ blkptr_t dp_meta_rootbp; @@ -173,6 +174,7 @@ boolean_t dsl_pool_config_held_writer(dsl_pool_t *dp); boolean_t dsl_pool_need_dirty_delay(dsl_pool_t *dp); taskq_t *dsl_pool_vnrele_taskq(dsl_pool_t *dp); +taskq_t *dsl_pool_unlinked_drain_taskq(dsl_pool_t *dp); int dsl_pool_user_hold(dsl_pool_t *dp, uint64_t dsobj, const char *tag, uint64_t now, dmu_tx_t *tx); diff --git a/usr/src/uts/common/fs/zfs/sys/zfs_dir.h b/usr/src/uts/common/fs/zfs/sys/zfs_dir.h index 349f8ef373..d8edb79286 100644 --- a/usr/src/uts/common/fs/zfs/sys/zfs_dir.h +++ b/usr/src/uts/common/fs/zfs/sys/zfs_dir.h @@ -63,6 +63,7 @@ extern void zfs_dl_name_switch(zfs_dirlock_t *dl, char *new, char **old); extern boolean_t zfs_dirempty(znode_t *); extern void zfs_unlinked_add(znode_t *, dmu_tx_t *); extern void zfs_unlinked_drain(zfsvfs_t *zfsvfs); +extern void zfs_unlinked_drain_stop_wait(zfsvfs_t *zfsvfs); extern int zfs_sticky_remove_access(znode_t *, znode_t *, cred_t *cr); extern int zfs_get_xattrdir(znode_t *, vnode_t **, cred_t *, int); extern int zfs_make_xattrdir(znode_t *, vattr_t *, vnode_t **, cred_t *); diff --git a/usr/src/uts/common/fs/zfs/sys/zfs_vfsops.h b/usr/src/uts/common/fs/zfs/sys/zfs_vfsops.h index 199c8446ca..0d1611b66c 100644 --- a/usr/src/uts/common/fs/zfs/sys/zfs_vfsops.h +++ b/usr/src/uts/common/fs/zfs/sys/zfs_vfsops.h @@ -75,6 +75,8 @@ struct zfsvfs { boolean_t z_use_fuids; /* version allows fuids */ boolean_t z_replay; /* set during ZIL replay */ boolean_t z_use_sa; /* version allow system attributes */ + boolean_t z_draining; /* is true when drain is active */ + boolean_t z_drain_cancel; /* signal the unlinked drain to stop */ uint64_t z_version; /* ZPL version */ uint64_t z_shares_dir; /* hidden shares dir */ kmutex_t z_lock; @@ -88,6 +90,7 @@ struct zfsvfs { sa_attr_type_t *z_attr_table; /* SA attr mapping->id */ #define ZFS_OBJ_MTX_SZ 64 kmutex_t z_hold_mtx[ZFS_OBJ_MTX_SZ]; /* znode hold locks */ + taskqid_t z_drain_task; /* task id for the unlink drain task */ }; /* diff --git a/usr/src/uts/common/fs/zfs/zfs_dir.c b/usr/src/uts/common/fs/zfs/zfs_dir.c index ac262161ae..c5add7b25f 100644 --- a/usr/src/uts/common/fs/zfs/zfs_dir.c +++ b/usr/src/uts/common/fs/zfs/zfs_dir.c @@ -481,20 +481,23 @@ zfs_unlinked_add(znode_t *zp, dmu_tx_t *tx) * Clean up any znodes that had no links when we either crashed or * (force) umounted the file system. */ -void -zfs_unlinked_drain(zfsvfs_t *zfsvfs) +static void +zfs_unlinked_drain_task(void *arg) { + zfsvfs_t *zfsvfs = arg; zap_cursor_t zc; zap_attribute_t zap; dmu_object_info_t doi; znode_t *zp; int error; + ASSERT3B(zfsvfs->z_draining, ==, B_TRUE); + /* * Interate over the contents of the unlinked set. */ for (zap_cursor_init(&zc, zfsvfs->z_os, zfsvfs->z_unlinkedobj); - zap_cursor_retrieve(&zc, &zap) == 0; + zap_cursor_retrieve(&zc, &zap) == 0 && !zfsvfs->z_drain_cancel; zap_cursor_advance(&zc)) { /* @@ -524,9 +527,52 @@ zfs_unlinked_drain(zfsvfs_t *zfsvfs) continue; zp->z_unlinked = B_TRUE; + VN_RELE(ZTOV(zp)); + ASSERT3B(zfsvfs->z_unmounted, ==, B_FALSE); } zap_cursor_fini(&zc); + + zfsvfs->z_draining = B_FALSE; + zfsvfs->z_drain_task = TASKQID_INVALID; +} + +/* + * Sets z_draining then tries to dispatch async unlinked drain. + * If that fails executes synchronous unlinked drain. + */ +void +zfs_unlinked_drain(zfsvfs_t *zfsvfs) +{ + ASSERT3B(zfsvfs->z_unmounted, ==, B_FALSE); + ASSERT3B(zfsvfs->z_draining, ==, B_FALSE); + + zfsvfs->z_draining = B_TRUE; + zfsvfs->z_drain_cancel = B_FALSE; + + zfsvfs->z_drain_task = taskq_dispatch( + dsl_pool_unlinked_drain_taskq(dmu_objset_pool(zfsvfs->z_os)), + zfs_unlinked_drain_task, zfsvfs, TQ_SLEEP); + if (zfsvfs->z_drain_task == TASKQID_INVALID) { + zfs_dbgmsg("async zfs_unlinked_drain dispatch failed"); + zfs_unlinked_drain_task(zfsvfs); + } +} + +/* + * Wait for the unlinked drain taskq task to stop. This will interrupt the + * unlinked set processing if it is in progress. + */ +void +zfs_unlinked_drain_stop_wait(zfsvfs_t *zfsvfs) +{ + ASSERT3B(zfsvfs->z_unmounted, ==, B_FALSE); + + while (zfsvfs->z_draining) { + zfsvfs->z_drain_cancel = B_TRUE; + taskq_wait(dsl_pool_unlinked_drain_taskq( + dmu_objset_pool(zfsvfs->z_os))); + } } /* @@ -1110,7 +1156,7 @@ top: int zfs_sticky_remove_access(znode_t *zdp, znode_t *zp, cred_t *cr) { - uid_t uid; + uid_t uid; uid_t downer; uid_t fowner; zfsvfs_t *zfsvfs = zdp->z_zfsvfs; diff --git a/usr/src/uts/common/fs/zfs/zfs_vfsops.c b/usr/src/uts/common/fs/zfs/zfs_vfsops.c index 6ee003101a..6b61cd7a84 100644 --- a/usr/src/uts/common/fs/zfs/zfs_vfsops.c +++ b/usr/src/uts/common/fs/zfs/zfs_vfsops.c @@ -1201,6 +1201,10 @@ zfsvfs_create_impl(zfsvfs_t **zfvp, zfsvfs_t *zfsvfs, objset_t *os) return (error); } + zfsvfs->z_drain_task = TASKQID_INVALID; + zfsvfs->z_draining = B_FALSE; + zfsvfs->z_drain_cancel = B_TRUE; + *zfvp = zfsvfs; return (0); } @@ -1229,10 +1233,11 @@ zfsvfs_setup(zfsvfs_t *zfsvfs, boolean_t mounting) * allow replays to succeed. */ readonly = zfsvfs->z_vfs->vfs_flag & VFS_RDONLY; - if (readonly != 0) + if (readonly != 0) { zfsvfs->z_vfs->vfs_flag &= ~VFS_RDONLY; - else + } else { zfs_unlinked_drain(zfsvfs); + } /* * Parse and replay the intent log. @@ -2039,6 +2044,8 @@ zfsvfs_teardown(zfsvfs_t *zfsvfs, boolean_t unmounting) { znode_t *zp; + zfs_unlinked_drain_stop_wait(zfsvfs); + rrm_enter(&zfsvfs->z_teardown_lock, RW_WRITER, FTAG); if (!unmounting) { @@ -2371,6 +2378,16 @@ zfs_resume_fs(zfsvfs_t *zfsvfs, dsl_dataset_t *ds) } mutex_exit(&zfsvfs->z_znodes_lock); + if (((zfsvfs->z_vfs->vfs_flag & VFS_RDONLY) == 0) && + !zfsvfs->z_unmounted) { + /* + * zfs_suspend_fs() could have interrupted freeing + * of dnodes. We need to restart this freeing so + * that we don't "leak" the space. + */ + zfs_unlinked_drain(zfsvfs); + } + bail: /* release the VOPs */ rw_exit(&zfsvfs->z_teardown_inactive_lock); diff --git a/usr/src/uts/common/fs/zfs/zfs_znode.c b/usr/src/uts/common/fs/zfs/zfs_znode.c index 9abfc025d5..257d5b2a35 100644 --- a/usr/src/uts/common/fs/zfs/zfs_znode.c +++ b/usr/src/uts/common/fs/zfs/zfs_znode.c @@ -100,6 +100,12 @@ krwlock_t zfsvfs_lock; static kmem_cache_t *znode_cache = NULL; +/* + * This is used by the test suite so that it can delay znodes from being + * freed in order to inspect the unlinked set. + */ +int zfs_unlink_suspend_progress = 0; + /*ARGSUSED*/ static void znode_evict_error(dmu_buf_t *dbuf, void *user_ptr) @@ -1416,7 +1422,8 @@ zfs_zinactive(znode_t *zp) */ if (zp->z_unlinked) { ASSERT(!zfsvfs->z_issnap); - if ((zfsvfs->z_vfs->vfs_flag & VFS_RDONLY) == 0) { + if ((zfsvfs->z_vfs->vfs_flag & VFS_RDONLY) == 0 && + !zfs_unlink_suspend_progress) { mutex_exit(&zp->z_lock); ZFS_OBJ_HOLD_EXIT(zfsvfs, z_id); zfs_rmnode(zp); |