2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* CDDL HEADER START
|
|
|
|
*
|
|
|
|
* The contents of this file are subject to the terms of the
|
|
|
|
* Common Development and Distribution License (the "License").
|
|
|
|
* You may not use this file except in compliance with the License.
|
|
|
|
*
|
|
|
|
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
2022-07-11 21:16:13 +00:00
|
|
|
* or https://opensource.org/licenses/CDDL-1.0.
|
2008-11-20 20:01:55 +00:00
|
|
|
* See the License for the specific language governing permissions
|
|
|
|
* and limitations under the License.
|
|
|
|
*
|
|
|
|
* When distributing Covered Code, include this CDDL HEADER in each
|
|
|
|
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
|
|
|
* If applicable, add the following below this CDDL HEADER, with the
|
|
|
|
* fields enclosed by brackets "[]" replaced with your own identifying
|
|
|
|
* information: Portions Copyright [yyyy] [name of copyright owner]
|
|
|
|
*
|
|
|
|
* CDDL HEADER END
|
|
|
|
*/
|
|
|
|
/*
|
2010-08-26 21:24:34 +00:00
|
|
|
* Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
|
Implement Redacted Send/Receive
Redacted send/receive allows users to send subsets of their data to
a target system. One possible use case for this feature is to not
transmit sensitive information to a data warehousing, test/dev, or
analytics environment. Another is to save space by not replicating
unimportant data within a given dataset, for example in backup tools
like zrepl.
Redacted send/receive is a three-stage process. First, a clone (or
clones) is made of the snapshot to be sent to the target. In this
clone (or clones), all unnecessary or unwanted data is removed or
modified. This clone is then snapshotted to create the "redaction
snapshot" (or snapshots). Second, the new zfs redact command is used
to create a redaction bookmark. The redaction bookmark stores the
list of blocks in a snapshot that were modified by the redaction
snapshot(s). Finally, the redaction bookmark is passed as a parameter
to zfs send. When sending to the snapshot that was redacted, the
redaction bookmark is used to filter out blocks that contain sensitive
or unwanted information, and those blocks are not included in the send
stream. When sending from the redaction bookmark, the blocks it
contains are considered as candidate blocks in addition to those
blocks in the destination snapshot that were modified since the
creation_txg of the redaction bookmark. This step is necessary to
allow the target to rehydrate data in the case where some blocks are
accidentally or unnecessarily modified in the redaction snapshot.
The changes to bookmarks to enable fast space estimation involve
adding deadlists to bookmarks. There is also logic to manage the
life cycles of these deadlists.
The new size estimation process operates in cases where previously
an accurate estimate could not be provided. In those cases, a send
is performed where no data blocks are read, reducing the runtime
significantly and providing a byte-accurate size estimate.
Reviewed-by: Dan Kimmel <dan.kimmel@delphix.com>
Reviewed-by: Matt Ahrens <mahrens@delphix.com>
Reviewed-by: Prashanth Sreenivasa <pks@delphix.com>
Reviewed-by: John Kennedy <john.kennedy@delphix.com>
Reviewed-by: George Wilson <george.wilson@delphix.com>
Reviewed-by: Chris Williamson <chris.williamson@delphix.com>
Reviewed-by: Pavel Zhakarov <pavel.zakharov@delphix.com>
Reviewed-by: Sebastien Roy <sebastien.roy@delphix.com>
Reviewed-by: Prakash Surya <prakash.surya@delphix.com>
Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Paul Dagnelie <pcd@delphix.com>
Closes #7958
2019-06-19 16:48:13 +00:00
|
|
|
* Copyright (c) 2012, 2018 by Delphix. All rights reserved.
|
2014-03-22 09:07:14 +00:00
|
|
|
* Copyright (c) 2016 Actifio, Inc. All rights reserved.
|
2008-11-20 20:01:55 +00:00
|
|
|
*/
|
|
|
|
|
|
|
|
#include <assert.h>
|
|
|
|
#include <fcntl.h>
|
2020-06-09 22:59:04 +00:00
|
|
|
#include <libgen.h>
|
2008-11-20 20:01:55 +00:00
|
|
|
#include <poll.h>
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <string.h>
|
2022-11-28 21:24:17 +00:00
|
|
|
#include <limits.h>
|
2021-05-22 15:19:14 +00:00
|
|
|
#include <libzutil.h>
|
2020-06-09 22:59:04 +00:00
|
|
|
#include <sys/crypto/icp.h>
|
2008-11-20 20:01:55 +00:00
|
|
|
#include <sys/processor.h>
|
2013-09-04 12:00:57 +00:00
|
|
|
#include <sys/rrwlock.h>
|
2020-06-09 22:59:04 +00:00
|
|
|
#include <sys/spa.h>
|
|
|
|
#include <sys/stat.h>
|
2009-02-18 20:51:31 +00:00
|
|
|
#include <sys/systeminfo.h>
|
2020-06-09 22:59:04 +00:00
|
|
|
#include <sys/time.h>
|
|
|
|
#include <sys/utsname.h>
|
|
|
|
#include <sys/zfs_context.h>
|
|
|
|
#include <sys/zfs_onexit.h>
|
2020-09-01 23:14:16 +00:00
|
|
|
#include <sys/zfs_vfsops.h>
|
Add zstd support to zfs
This PR adds two new compression types, based on ZStandard:
- zstd: A basic ZStandard compression algorithm Available compression.
Levels for zstd are zstd-1 through zstd-19, where the compression
increases with every level, but speed decreases.
- zstd-fast: A faster version of the ZStandard compression algorithm
zstd-fast is basically a "negative" level of zstd. The compression
decreases with every level, but speed increases.
Available compression levels for zstd-fast:
- zstd-fast-1 through zstd-fast-10
- zstd-fast-20 through zstd-fast-100 (in increments of 10)
- zstd-fast-500 and zstd-fast-1000
For more information check the man page.
Implementation details:
Rather than treat each level of zstd as a different algorithm (as was
done historically with gzip), the block pointer `enum zio_compress`
value is simply zstd for all levels, including zstd-fast, since they all
use the same decompression function.
The compress= property (a 64bit unsigned integer) uses the lower 7 bits
to store the compression algorithm (matching the number of bits used in
a block pointer, as the 8th bit was borrowed for embedded block
pointers). The upper bits are used to store the compression level.
It is necessary to be able to determine what compression level was used
when later reading a block back, so the concept used in LZ4, where the
first 32bits of the on-disk value are the size of the compressed data
(since the allocation is rounded up to the nearest ashift), was
extended, and we store the version of ZSTD and the level as well as the
compressed size. This value is returned when decompressing a block, so
that if the block needs to be recompressed (L2ARC, nop-write, etc), that
the same parameters will be used to result in the matching checksum.
All of the internal ZFS code ( `arc_buf_hdr_t`, `objset_t`,
`zio_prop_t`, etc.) uses the separated _compress and _complevel
variables. Only the properties ZAP contains the combined/bit-shifted
value. The combined value is split when the compression_changed_cb()
callback is called, and sets both objset members (os_compress and
os_complevel).
The userspace tools all use the combined/bit-shifted value.
Additional notes:
zdb can now also decode the ZSTD compression header (flag -Z) and
inspect the size, version and compression level saved in that header.
For each record, if it is ZSTD compressed, the parameters of the decoded
compression header get printed.
ZSTD is included with all current tests and new tests are added
as-needed.
Per-dataset feature flags now get activated when the property is set.
If a compression algorithm requires a feature flag, zfs activates the
feature when the property is set, rather than waiting for the first
block to be born. This is currently only used by zstd but can be
extended as needed.
Portions-Sponsored-By: The FreeBSD Foundation
Co-authored-by: Allan Jude <allanjude@freebsd.org>
Co-authored-by: Brian Behlendorf <behlendorf1@llnl.gov>
Co-authored-by: Sebastian Gottschall <s.gottschall@dd-wrt.com>
Co-authored-by: Kjeld Schouten-Lebbing <kjeld@schouten-lebbing.nl>
Co-authored-by: Michael Niewöhner <foss@mniewoehner.de>
Signed-off-by: Allan Jude <allan@klarasystems.com>
Signed-off-by: Allan Jude <allanjude@freebsd.org>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Sebastian Gottschall <s.gottschall@dd-wrt.com>
Signed-off-by: Kjeld Schouten-Lebbing <kjeld@schouten-lebbing.nl>
Signed-off-by: Michael Niewöhner <foss@mniewoehner.de>
Closes #6247
Closes #9024
Closes #10277
Closes #10278
2020-08-18 17:10:17 +00:00
|
|
|
#include <sys/zstd/zstd.h>
|
2020-06-09 22:59:04 +00:00
|
|
|
#include <sys/zvol.h>
|
2015-12-09 23:34:16 +00:00
|
|
|
#include <zfs_fletcher.h>
|
2020-06-09 22:59:04 +00:00
|
|
|
#include <zlib.h>
|
2008-11-20 20:01:55 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Emulation of kernel services in userland.
|
|
|
|
*/
|
|
|
|
|
|
|
|
uint64_t physmem;
|
2022-05-07 17:18:41 +00:00
|
|
|
uint32_t hostid;
|
2014-10-01 19:02:12 +00:00
|
|
|
struct utsname hw_utsname;
|
2008-11-20 20:01:55 +00:00
|
|
|
|
2016-01-01 13:42:58 +00:00
|
|
|
/* If set, all blocks read will be copied to the specified directory. */
|
|
|
|
char *vn_dumpdir = NULL;
|
|
|
|
|
2010-05-28 20:45:14 +00:00
|
|
|
/* this only exists to have its address taken */
|
|
|
|
struct proc p0;
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* threads
|
|
|
|
* =========================================================================
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
*
|
|
|
|
* TS_STACK_MIN is dictated by the minimum allowed pthread stack size. While
|
|
|
|
* TS_STACK_MAX is somewhat arbitrary, it was selected to be large enough for
|
|
|
|
* the expected stack depth while small enough to avoid exhausting address
|
|
|
|
* space with high thread counts.
|
2008-11-20 20:01:55 +00:00
|
|
|
*/
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
#define TS_STACK_MIN MAX(PTHREAD_STACK_MIN, 32768)
|
|
|
|
#define TS_STACK_MAX (256 * 1024)
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2022-03-05 00:25:22 +00:00
|
|
|
struct zk_thread_wrapper {
|
|
|
|
void (*func)(void *);
|
|
|
|
void *arg;
|
|
|
|
};
|
|
|
|
|
|
|
|
static void *
|
|
|
|
zk_thread_wrapper(void *arg)
|
|
|
|
{
|
|
|
|
struct zk_thread_wrapper ztw;
|
|
|
|
memcpy(&ztw, arg, sizeof (ztw));
|
|
|
|
free(arg);
|
|
|
|
ztw.func(ztw.arg);
|
|
|
|
return (NULL);
|
|
|
|
}
|
|
|
|
|
2010-08-26 17:43:27 +00:00
|
|
|
kthread_t *
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
zk_thread_create(void (*func)(void *), void *arg, size_t stksize, int state)
|
2010-08-26 17:43:27 +00:00
|
|
|
{
|
|
|
|
pthread_attr_t attr;
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
pthread_t tid;
|
2014-09-25 22:15:45 +00:00
|
|
|
char *stkstr;
|
2022-03-05 00:25:22 +00:00
|
|
|
struct zk_thread_wrapper *ztw;
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
int detachstate = PTHREAD_CREATE_DETACHED;
|
2010-08-26 17:43:27 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_attr_init(&attr));
|
2010-08-26 17:43:27 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
if (state & TS_JOINABLE)
|
|
|
|
detachstate = PTHREAD_CREATE_JOINABLE;
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2014-09-25 22:15:45 +00:00
|
|
|
VERIFY0(pthread_attr_setdetachstate(&attr, detachstate));
|
|
|
|
|
2010-08-26 17:43:27 +00:00
|
|
|
/*
|
2014-09-25 22:15:45 +00:00
|
|
|
* We allow the default stack size in user space to be specified by
|
|
|
|
* setting the ZFS_STACK_SIZE environment variable. This allows us
|
|
|
|
* the convenience of observing and debugging stack overruns in
|
|
|
|
* user space. Explicitly specified stack sizes will be honored.
|
|
|
|
* The usage of ZFS_STACK_SIZE is discussed further in the
|
|
|
|
* ENVIRONMENT VARIABLES sections of the ztest(1) man page.
|
2010-08-26 17:43:27 +00:00
|
|
|
*/
|
2014-09-25 22:15:45 +00:00
|
|
|
if (stksize == 0) {
|
|
|
|
stkstr = getenv("ZFS_STACK_SIZE");
|
|
|
|
|
|
|
|
if (stkstr == NULL)
|
|
|
|
stksize = TS_STACK_MAX;
|
|
|
|
else
|
|
|
|
stksize = MAX(atoi(stkstr), TS_STACK_MIN);
|
|
|
|
}
|
|
|
|
|
|
|
|
VERIFY3S(stksize, >, 0);
|
|
|
|
stksize = P2ROUNDUP(MAX(stksize, TS_STACK_MIN), PAGESIZE);
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
|
2016-05-15 22:18:25 +00:00
|
|
|
/*
|
|
|
|
* If this ever fails, it may be because the stack size is not a
|
|
|
|
* multiple of system page size.
|
|
|
|
*/
|
2014-09-25 22:15:45 +00:00
|
|
|
VERIFY0(pthread_attr_setstacksize(&attr, stksize));
|
|
|
|
VERIFY0(pthread_attr_setguardsize(&attr, PAGESIZE));
|
|
|
|
|
2022-03-05 00:25:22 +00:00
|
|
|
VERIFY(ztw = malloc(sizeof (*ztw)));
|
|
|
|
ztw->func = func;
|
|
|
|
ztw->arg = arg;
|
|
|
|
VERIFY0(pthread_create(&tid, &attr, zk_thread_wrapper, ztw));
|
2014-09-25 22:15:45 +00:00
|
|
|
VERIFY0(pthread_attr_destroy(&attr));
|
2010-08-26 17:43:27 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
return ((void *)(uintptr_t)tid);
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* kstats
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
kstat_t *
|
2013-08-27 00:09:29 +00:00
|
|
|
kstat_create(const char *module, int instance, const char *name,
|
|
|
|
const char *class, uchar_t type, ulong_t ndata, uchar_t ks_flag)
|
2008-11-20 20:01:55 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) module, (void) instance, (void) name, (void) class, (void) type,
|
|
|
|
(void) ndata, (void) ks_flag;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (NULL);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
kstat_install(kstat_t *ksp)
|
2021-12-12 15:01:06 +00:00
|
|
|
{
|
|
|
|
(void) ksp;
|
|
|
|
}
|
2008-11-20 20:01:55 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
kstat_delete(kstat_t *ksp)
|
2021-12-12 15:01:06 +00:00
|
|
|
{
|
|
|
|
(void) ksp;
|
|
|
|
}
|
2008-11-20 20:01:55 +00:00
|
|
|
|
Add visibility in to arc_read
This change is an attempt to add visibility into the arc_read calls
occurring on a system, in real time. To do this, a list was added to the
in memory SPA data structure for a pool, with each element on the list
corresponding to a call to arc_read. These entries are then exported
through the kstat interface, which can then be interpreted in userspace.
For each arc_read call, the following information is exported:
* A unique identifier (uint64_t)
* The time the entry was added to the list (hrtime_t)
(*not* wall clock time; relative to the other entries on the list)
* The objset ID (uint64_t)
* The object number (uint64_t)
* The indirection level (uint64_t)
* The block ID (uint64_t)
* The name of the function originating the arc_read call (char[24])
* The arc_flags from the arc_read call (uint32_t)
* The PID of the reading thread (pid_t)
* The command or name of thread originating read (char[16])
From this exported information one can see, in real time, exactly what
is being read, what function is generating the read, and whether or not
the read was found to be already cached.
There is still some work to be done, but this should serve as a good
starting point.
Specifically, dbuf_read's are not accounted for in the currently
exported information. Thus, a follow up patch should probably be added
to export these calls that never call into arc_read (they only hit the
dbuf hash table). In addition, it might be nice to create a utility
similar to "arcstat.py" to digest the exported information and display
it in a more readable format. Or perhaps, log the information and allow
for it to be "replayed" at a later time.
Signed-off-by: Prakash Surya <surya1@llnl.gov>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
2013-09-06 23:09:05 +00:00
|
|
|
void
|
|
|
|
kstat_set_raw_ops(kstat_t *ksp,
|
|
|
|
int (*headers)(char *buf, size_t size),
|
|
|
|
int (*data)(char *buf, size_t size, void *data),
|
|
|
|
void *(*addr)(kstat_t *ksp, loff_t index))
|
2021-12-12 15:01:06 +00:00
|
|
|
{
|
|
|
|
(void) ksp, (void) headers, (void) data, (void) addr;
|
|
|
|
}
|
Add visibility in to arc_read
This change is an attempt to add visibility into the arc_read calls
occurring on a system, in real time. To do this, a list was added to the
in memory SPA data structure for a pool, with each element on the list
corresponding to a call to arc_read. These entries are then exported
through the kstat interface, which can then be interpreted in userspace.
For each arc_read call, the following information is exported:
* A unique identifier (uint64_t)
* The time the entry was added to the list (hrtime_t)
(*not* wall clock time; relative to the other entries on the list)
* The objset ID (uint64_t)
* The object number (uint64_t)
* The indirection level (uint64_t)
* The block ID (uint64_t)
* The name of the function originating the arc_read call (char[24])
* The arc_flags from the arc_read call (uint32_t)
* The PID of the reading thread (pid_t)
* The command or name of thread originating read (char[16])
From this exported information one can see, in real time, exactly what
is being read, what function is generating the read, and whether or not
the read was found to be already cached.
There is still some work to be done, but this should serve as a good
starting point.
Specifically, dbuf_read's are not accounted for in the currently
exported information. Thus, a follow up patch should probably be added
to export these calls that never call into arc_read (they only hit the
dbuf hash table). In addition, it might be nice to create a utility
similar to "arcstat.py" to digest the exported information and display
it in a more readable format. Or perhaps, log the information and allow
for it to be "replayed" at a later time.
Signed-off-by: Prakash Surya <surya1@llnl.gov>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
2013-09-06 23:09:05 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* mutexes
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
void
|
2010-08-26 17:43:27 +00:00
|
|
|
mutex_init(kmutex_t *mp, char *name, int type, void *cookie)
|
2008-11-20 20:01:55 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name, (void) type, (void) cookie;
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_mutex_init(&mp->m_lock, NULL));
|
|
|
|
memset(&mp->m_owner, 0, sizeof (pthread_t));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2010-08-26 17:43:27 +00:00
|
|
|
mutex_destroy(kmutex_t *mp)
|
2008-11-20 20:01:55 +00:00
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_mutex_destroy(&mp->m_lock));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
mutex_enter(kmutex_t *mp)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_mutex_lock(&mp->m_lock));
|
|
|
|
mp->m_owner = pthread_self();
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
mutex_tryenter(kmutex_t *mp)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
int error = pthread_mutex_trylock(&mp->m_lock);
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
if (error == 0) {
|
|
|
|
mp->m_owner = pthread_self();
|
2008-11-20 20:01:55 +00:00
|
|
|
return (1);
|
|
|
|
} else {
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY3S(error, ==, EBUSY);
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
mutex_exit(kmutex_t *mp)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
memset(&mp->m_owner, 0, sizeof (pthread_t));
|
|
|
|
VERIFY0(pthread_mutex_unlock(&mp->m_lock));
|
2010-08-26 17:43:27 +00:00
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* rwlocks
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
void
|
|
|
|
rw_init(krwlock_t *rwlp, char *name, int type, void *arg)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name, (void) type, (void) arg;
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_rwlock_init(&rwlp->rw_lock, NULL));
|
2010-08-26 17:43:27 +00:00
|
|
|
rwlp->rw_readers = 0;
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
rwlp->rw_owner = 0;
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
rw_destroy(krwlock_t *rwlp)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_rwlock_destroy(&rwlp->rw_lock));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
rw_enter(krwlock_t *rwlp, krw_t rw)
|
|
|
|
{
|
2010-08-26 17:43:27 +00:00
|
|
|
if (rw == RW_READER) {
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_rwlock_rdlock(&rwlp->rw_lock));
|
2010-08-26 17:43:27 +00:00
|
|
|
atomic_inc_uint(&rwlp->rw_readers);
|
|
|
|
} else {
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_rwlock_wrlock(&rwlp->rw_lock));
|
|
|
|
rwlp->rw_owner = pthread_self();
|
2010-08-26 17:43:27 +00:00
|
|
|
}
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
rw_exit(krwlock_t *rwlp)
|
|
|
|
{
|
2010-08-26 17:43:27 +00:00
|
|
|
if (RW_READ_HELD(rwlp))
|
|
|
|
atomic_dec_uint(&rwlp->rw_readers);
|
|
|
|
else
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
rwlp->rw_owner = 0;
|
2008-11-20 20:01:55 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_rwlock_unlock(&rwlp->rw_lock));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
rw_tryenter(krwlock_t *rwlp, krw_t rw)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
int error;
|
2008-11-20 20:01:55 +00:00
|
|
|
|
|
|
|
if (rw == RW_READER)
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
error = pthread_rwlock_tryrdlock(&rwlp->rw_lock);
|
2008-11-20 20:01:55 +00:00
|
|
|
else
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
error = pthread_rwlock_trywrlock(&rwlp->rw_lock);
|
2010-08-26 17:43:27 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
if (error == 0) {
|
2010-08-26 17:43:27 +00:00
|
|
|
if (rw == RW_READER)
|
|
|
|
atomic_inc_uint(&rwlp->rw_readers);
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
else
|
|
|
|
rwlp->rw_owner = pthread_self();
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
return (1);
|
|
|
|
}
|
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY3S(error, ==, EBUSY);
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
OpenZFS 9075 - Improve ZFS pool import/load process and corrupted pool recovery
Some work has been done lately to improve the debugability of the ZFS pool
load (and import) process. This includes:
7638 Refactor spa_load_impl into several functions
8961 SPA load/import should tell us why it failed
7277 zdb should be able to print zfs_dbgmsg's
To iterate on top of that, there's a few changes that were made to make the
import process more resilient and crash free. One of the first tasks during the
pool load process is to parse a config provided from userland that describes
what devices the pool is composed of. A vdev tree is generated from that config,
and then all the vdevs are opened.
The Meta Object Set (MOS) of the pool is accessed, and several metadata objects
that are necessary to load the pool are read. The exact configuration of the
pool is also stored inside the MOS. Since the configuration provided from
userland is external and might not accurately describe the vdev tree
of the pool at the txg that is being loaded, it cannot be relied upon to safely
operate the pool. For that reason, the configuration in the MOS is read early
on. In the past, the two configurations were compared together and if there was
a mismatch then the load process was aborted and an error was returned.
The latter was a good way to ensure a pool does not get corrupted, however it
made the pool load process needlessly fragile in cases where the vdev
configuration changed or the userland configuration was outdated. Since the MOS
is stored in 3 copies, the configuration provided by userland doesn't have to be
perfect in order to read its contents. Hence, a new approach has been adopted:
The pool is first opened with the untrusted userland configuration just so that
the real configuration can be read from the MOS. The trusted MOS configuration
is then used to generate a new vdev tree and the pool is re-opened.
When the pool is opened with an untrusted configuration, writes are disabled
to avoid accidentally damaging it. During reads, some sanity checks are
performed on block pointers to see if each DVA points to a known vdev;
when the configuration is untrusted, instead of panicking the system if those
checks fail we simply avoid issuing reads to the invalid DVAs.
This new two-step pool load process now allows rewinding pools accross
vdev tree changes such as device replacement, addition, etc. Loading a pool
from an external config file in a clustering environment also becomes much
safer now since the pool will import even if the config is outdated and didn't,
for instance, register a recent device addition.
With this code in place, it became relatively easy to implement a
long-sought-after feature: the ability to import a pool with missing top level
(i.e. non-redundant) devices. Note that since this almost guarantees some loss
of data, this feature is for now restricted to a read-only import.
Porting notes (ZTS):
* Fix 'make dist' target in zpool_import
* The maximum path length allowed by tar is 99 characters. Several
of the new test cases exceeded this limit resulting in them not
being included in the tarball. Shorten the names slightly.
* Set/get tunables using accessor functions.
* Get last synced txg via the "zfs_txg_history" mechanism.
* Clear zinject handlers in cleanup for import_cache_device_replaced
and import_rewind_device_replaced in order that the zpool can be
exported if there is an error.
* Increase FILESIZE to 8G in zfs-test.sh to allow for a larger
ext4 file system to be created on ZFS_DISK2. Also, there's
no need to partition ZFS_DISK2 at all. The partitioning had
already been disabled for multipath devices. Among other things,
the partitioning steals some space from the ext4 file system,
makes it difficult to accurately calculate the paramters to
parted and can make some of the tests fail.
* Increase FS_SIZE and FILE_SIZE in the zpool_import test
configuration now that FILESIZE is larger.
* Write more data in order that device evacuation take lonnger in
a couple tests.
* Use mkdir -p to avoid errors when the directory already exists.
* Remove use of sudo in import_rewind_config_changed.
Authored by: Pavel Zakharov <pavel.zakharov@delphix.com>
Reviewed by: George Wilson <george.wilson@delphix.com>
Reviewed by: Matthew Ahrens <mahrens@delphix.com>
Reviewed by: Andrew Stormont <andyjstormont@gmail.com>
Approved by: Hans Rosenfeld <rosenfeld@grumpf.hope-2000.org>
Ported-by: Tim Chase <tim@chase2k.com>
Signed-off-by: Tim Chase <tim@chase2k.com>
OpenZFS-issue: https://illumos.org/issues/9075
OpenZFS-commit: https://github.com/openzfs/openzfs/commit/619c0123
Closes #7459
2016-07-22 14:39:36 +00:00
|
|
|
uint32_t
|
|
|
|
zone_get_hostid(void *zonep)
|
|
|
|
{
|
|
|
|
/*
|
|
|
|
* We're emulating the system's hostid in userland.
|
|
|
|
*/
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) zonep;
|
2022-05-07 17:18:41 +00:00
|
|
|
return (hostid);
|
OpenZFS 9075 - Improve ZFS pool import/load process and corrupted pool recovery
Some work has been done lately to improve the debugability of the ZFS pool
load (and import) process. This includes:
7638 Refactor spa_load_impl into several functions
8961 SPA load/import should tell us why it failed
7277 zdb should be able to print zfs_dbgmsg's
To iterate on top of that, there's a few changes that were made to make the
import process more resilient and crash free. One of the first tasks during the
pool load process is to parse a config provided from userland that describes
what devices the pool is composed of. A vdev tree is generated from that config,
and then all the vdevs are opened.
The Meta Object Set (MOS) of the pool is accessed, and several metadata objects
that are necessary to load the pool are read. The exact configuration of the
pool is also stored inside the MOS. Since the configuration provided from
userland is external and might not accurately describe the vdev tree
of the pool at the txg that is being loaded, it cannot be relied upon to safely
operate the pool. For that reason, the configuration in the MOS is read early
on. In the past, the two configurations were compared together and if there was
a mismatch then the load process was aborted and an error was returned.
The latter was a good way to ensure a pool does not get corrupted, however it
made the pool load process needlessly fragile in cases where the vdev
configuration changed or the userland configuration was outdated. Since the MOS
is stored in 3 copies, the configuration provided by userland doesn't have to be
perfect in order to read its contents. Hence, a new approach has been adopted:
The pool is first opened with the untrusted userland configuration just so that
the real configuration can be read from the MOS. The trusted MOS configuration
is then used to generate a new vdev tree and the pool is re-opened.
When the pool is opened with an untrusted configuration, writes are disabled
to avoid accidentally damaging it. During reads, some sanity checks are
performed on block pointers to see if each DVA points to a known vdev;
when the configuration is untrusted, instead of panicking the system if those
checks fail we simply avoid issuing reads to the invalid DVAs.
This new two-step pool load process now allows rewinding pools accross
vdev tree changes such as device replacement, addition, etc. Loading a pool
from an external config file in a clustering environment also becomes much
safer now since the pool will import even if the config is outdated and didn't,
for instance, register a recent device addition.
With this code in place, it became relatively easy to implement a
long-sought-after feature: the ability to import a pool with missing top level
(i.e. non-redundant) devices. Note that since this almost guarantees some loss
of data, this feature is for now restricted to a read-only import.
Porting notes (ZTS):
* Fix 'make dist' target in zpool_import
* The maximum path length allowed by tar is 99 characters. Several
of the new test cases exceeded this limit resulting in them not
being included in the tarball. Shorten the names slightly.
* Set/get tunables using accessor functions.
* Get last synced txg via the "zfs_txg_history" mechanism.
* Clear zinject handlers in cleanup for import_cache_device_replaced
and import_rewind_device_replaced in order that the zpool can be
exported if there is an error.
* Increase FILESIZE to 8G in zfs-test.sh to allow for a larger
ext4 file system to be created on ZFS_DISK2. Also, there's
no need to partition ZFS_DISK2 at all. The partitioning had
already been disabled for multipath devices. Among other things,
the partitioning steals some space from the ext4 file system,
makes it difficult to accurately calculate the paramters to
parted and can make some of the tests fail.
* Increase FS_SIZE and FILE_SIZE in the zpool_import test
configuration now that FILESIZE is larger.
* Write more data in order that device evacuation take lonnger in
a couple tests.
* Use mkdir -p to avoid errors when the directory already exists.
* Remove use of sudo in import_rewind_config_changed.
Authored by: Pavel Zakharov <pavel.zakharov@delphix.com>
Reviewed by: George Wilson <george.wilson@delphix.com>
Reviewed by: Matthew Ahrens <mahrens@delphix.com>
Reviewed by: Andrew Stormont <andyjstormont@gmail.com>
Approved by: Hans Rosenfeld <rosenfeld@grumpf.hope-2000.org>
Ported-by: Tim Chase <tim@chase2k.com>
Signed-off-by: Tim Chase <tim@chase2k.com>
OpenZFS-issue: https://illumos.org/issues/9075
OpenZFS-commit: https://github.com/openzfs/openzfs/commit/619c0123
Closes #7459
2016-07-22 14:39:36 +00:00
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
int
|
|
|
|
rw_tryupgrade(krwlock_t *rwlp)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) rwlp;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* condition variables
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
2010-08-26 17:43:27 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
void
|
|
|
|
cv_init(kcondvar_t *cv, char *name, int type, void *arg)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name, (void) type, (void) arg;
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_cond_init(cv, NULL));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
cv_destroy(kcondvar_t *cv)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_cond_destroy(cv));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
cv_wait(kcondvar_t *cv, kmutex_t *mp)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
memset(&mp->m_owner, 0, sizeof (pthread_t));
|
|
|
|
VERIFY0(pthread_cond_wait(cv, &mp->m_lock));
|
|
|
|
mp->m_owner = pthread_self();
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
2019-06-22 23:51:46 +00:00
|
|
|
int
|
|
|
|
cv_wait_sig(kcondvar_t *cv, kmutex_t *mp)
|
|
|
|
{
|
|
|
|
cv_wait(cv, mp);
|
|
|
|
return (1);
|
|
|
|
}
|
|
|
|
|
2020-06-18 17:17:50 +00:00
|
|
|
int
|
2008-11-20 20:01:55 +00:00
|
|
|
cv_timedwait(kcondvar_t *cv, kmutex_t *mp, clock_t abstime)
|
|
|
|
{
|
|
|
|
int error;
|
2010-08-26 17:43:27 +00:00
|
|
|
struct timeval tv;
|
2018-06-20 04:51:18 +00:00
|
|
|
struct timespec ts;
|
2008-11-20 20:01:55 +00:00
|
|
|
clock_t delta;
|
|
|
|
|
2010-05-28 20:45:14 +00:00
|
|
|
delta = abstime - ddi_get_lbolt();
|
2008-11-20 20:01:55 +00:00
|
|
|
if (delta <= 0)
|
|
|
|
return (-1);
|
|
|
|
|
2010-08-26 17:43:27 +00:00
|
|
|
VERIFY(gettimeofday(&tv, NULL) == 0);
|
|
|
|
|
|
|
|
ts.tv_sec = tv.tv_sec + delta / hz;
|
2016-08-25 20:24:01 +00:00
|
|
|
ts.tv_nsec = tv.tv_usec * NSEC_PER_USEC + (delta % hz) * (NANOSEC / hz);
|
2010-08-26 17:43:27 +00:00
|
|
|
if (ts.tv_nsec >= NANOSEC) {
|
|
|
|
ts.tv_sec++;
|
|
|
|
ts.tv_nsec -= NANOSEC;
|
|
|
|
}
|
2008-11-20 20:01:55 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
memset(&mp->m_owner, 0, sizeof (pthread_t));
|
|
|
|
error = pthread_cond_timedwait(cv, &mp->m_lock, &ts);
|
|
|
|
mp->m_owner = pthread_self();
|
2008-11-20 20:01:55 +00:00
|
|
|
|
2010-08-26 17:43:27 +00:00
|
|
|
if (error == ETIMEDOUT)
|
2008-11-20 20:01:55 +00:00
|
|
|
return (-1);
|
|
|
|
|
2016-05-15 22:18:25 +00:00
|
|
|
VERIFY0(error);
|
2008-11-20 20:01:55 +00:00
|
|
|
|
|
|
|
return (1);
|
|
|
|
}
|
|
|
|
|
2020-06-18 17:17:50 +00:00
|
|
|
int
|
2013-08-28 23:05:48 +00:00
|
|
|
cv_timedwait_hires(kcondvar_t *cv, kmutex_t *mp, hrtime_t tim, hrtime_t res,
|
|
|
|
int flag)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) res;
|
2013-08-28 23:05:48 +00:00
|
|
|
int error;
|
2016-08-25 20:24:01 +00:00
|
|
|
struct timeval tv;
|
2018-06-20 04:51:18 +00:00
|
|
|
struct timespec ts;
|
2013-08-28 23:05:48 +00:00
|
|
|
hrtime_t delta;
|
|
|
|
|
2016-05-15 22:18:25 +00:00
|
|
|
ASSERT(flag == 0 || flag == CALLOUT_FLAG_ABSOLUTE);
|
|
|
|
|
|
|
|
delta = tim;
|
|
|
|
if (flag & CALLOUT_FLAG_ABSOLUTE)
|
|
|
|
delta -= gethrtime();
|
2013-08-28 23:05:48 +00:00
|
|
|
|
|
|
|
if (delta <= 0)
|
|
|
|
return (-1);
|
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(gettimeofday(&tv, NULL));
|
2016-08-25 20:24:01 +00:00
|
|
|
|
|
|
|
ts.tv_sec = tv.tv_sec + delta / NANOSEC;
|
|
|
|
ts.tv_nsec = tv.tv_usec * NSEC_PER_USEC + (delta % NANOSEC);
|
|
|
|
if (ts.tv_nsec >= NANOSEC) {
|
|
|
|
ts.tv_sec++;
|
|
|
|
ts.tv_nsec -= NANOSEC;
|
|
|
|
}
|
2013-08-28 23:05:48 +00:00
|
|
|
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
memset(&mp->m_owner, 0, sizeof (pthread_t));
|
|
|
|
error = pthread_cond_timedwait(cv, &mp->m_lock, &ts);
|
|
|
|
mp->m_owner = pthread_self();
|
2013-08-28 23:05:48 +00:00
|
|
|
|
2016-05-15 22:18:25 +00:00
|
|
|
if (error == ETIMEDOUT)
|
2013-08-28 23:05:48 +00:00
|
|
|
return (-1);
|
|
|
|
|
2016-05-15 22:18:25 +00:00
|
|
|
VERIFY0(error);
|
2013-08-28 23:05:48 +00:00
|
|
|
|
|
|
|
return (1);
|
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
void
|
|
|
|
cv_signal(kcondvar_t *cv)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_cond_signal(cv));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
cv_broadcast(kcondvar_t *cv)
|
|
|
|
{
|
Simplify threads, mutexs, cvs and rwlocks
* Simplify threads, mutexs, cvs and rwlocks
* Update the zk_thread_create() function to use the same trick
as Illumos. Specifically, cast the new pthread_t to a void
pointer and return that as the kthread_t *. This avoids the
issues associated with managing a wrapper structure and is
safe as long as the callers never attempt to dereference it.
* Update all function prototypes passed to pthread_create() to
match the expected prototype. We were getting away this with
before since the function were explicitly cast.
* Replaced direct zk_thread_create() calls with thread_create()
for code consistency. All consumers of libzpool now use the
proper wrappers.
* The mutex_held() calls were converted to MUTEX_HELD().
* Removed all mutex_owner() calls and retired the interface.
Instead use MUTEX_HELD() which provides the same information
and allows the implementation details to be hidden. In this
case the use of the pthread_equals() function.
* The kthread_t, kmutex_t, krwlock_t, and krwlock_t types had
any non essential fields removed. In the case of kthread_t
and kcondvar_t they could be directly typedef'd to pthread_t
and pthread_cond_t respectively.
* Removed all extra ASSERTS from the thread, mutex, rwlock, and
cv wrapper functions. In practice, pthreads already provides
the vast majority of checks as long as we check the return
code. Removing this code from our wrappers help readability.
* Added TS_JOINABLE state flag to pass to request a joinable rather
than detached thread. This isn't a standard thread_create() state
but it's the least invasive way to pass this information and is
only used by ztest.
TEST_ZTEST_TIMEOUT=3600
Chunwei Chen <tuxoko@gmail.com>
Reviewed-by: Tom Caputi <tcaputi@datto.com>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Closes #4547
Closes #5503
Closes #5523
Closes #6377
Closes #6495
2017-08-11 15:51:44 +00:00
|
|
|
VERIFY0(pthread_cond_broadcast(cv));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
2018-09-26 18:08:12 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* procfs list
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
|
|
|
|
void
|
|
|
|
seq_printf(struct seq_file *m, const char *fmt, ...)
|
2021-12-12 15:01:06 +00:00
|
|
|
{
|
|
|
|
(void) m, (void) fmt;
|
|
|
|
}
|
2018-09-26 18:08:12 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
procfs_list_install(const char *module,
|
2020-09-23 23:43:51 +00:00
|
|
|
const char *submodule,
|
2018-09-26 18:08:12 +00:00
|
|
|
const char *name,
|
2019-04-05 01:57:06 +00:00
|
|
|
mode_t mode,
|
2018-09-26 18:08:12 +00:00
|
|
|
procfs_list_t *procfs_list,
|
|
|
|
int (*show)(struct seq_file *f, void *p),
|
|
|
|
int (*show_header)(struct seq_file *f),
|
|
|
|
int (*clear)(procfs_list_t *procfs_list),
|
|
|
|
size_t procfs_list_node_off)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) module, (void) submodule, (void) name, (void) mode, (void) show,
|
|
|
|
(void) show_header, (void) clear;
|
2018-09-26 18:08:12 +00:00
|
|
|
mutex_init(&procfs_list->pl_lock, NULL, MUTEX_DEFAULT, NULL);
|
|
|
|
list_create(&procfs_list->pl_list,
|
|
|
|
procfs_list_node_off + sizeof (procfs_list_node_t),
|
|
|
|
procfs_list_node_off + offsetof(procfs_list_node_t, pln_link));
|
|
|
|
procfs_list->pl_next_id = 1;
|
|
|
|
procfs_list->pl_node_offset = procfs_list_node_off;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
procfs_list_uninstall(procfs_list_t *procfs_list)
|
2021-12-12 15:01:06 +00:00
|
|
|
{
|
|
|
|
(void) procfs_list;
|
|
|
|
}
|
2018-09-26 18:08:12 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
procfs_list_destroy(procfs_list_t *procfs_list)
|
|
|
|
{
|
|
|
|
ASSERT(list_is_empty(&procfs_list->pl_list));
|
|
|
|
list_destroy(&procfs_list->pl_list);
|
|
|
|
mutex_destroy(&procfs_list->pl_lock);
|
|
|
|
}
|
|
|
|
|
|
|
|
#define NODE_ID(procfs_list, obj) \
|
|
|
|
(((procfs_list_node_t *)(((char *)obj) + \
|
|
|
|
(procfs_list)->pl_node_offset))->pln_id)
|
|
|
|
|
|
|
|
void
|
|
|
|
procfs_list_add(procfs_list_t *procfs_list, void *p)
|
|
|
|
{
|
|
|
|
ASSERT(MUTEX_HELD(&procfs_list->pl_lock));
|
|
|
|
NODE_ID(procfs_list, p) = procfs_list->pl_next_id++;
|
|
|
|
list_insert_tail(&procfs_list->pl_list, p);
|
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* vnode operations
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
2010-05-28 20:45:14 +00:00
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* Figure out which debugging statements to print
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
|
|
|
|
static char *dprintf_string;
|
|
|
|
static int dprintf_print_all;
|
|
|
|
|
|
|
|
int
|
|
|
|
dprintf_find_string(const char *string)
|
|
|
|
{
|
|
|
|
char *tmp_str = dprintf_string;
|
|
|
|
int len = strlen(string);
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Find out if this is a string we want to print.
|
|
|
|
* String format: file1.c,function_name1,file2.c,file3.c
|
|
|
|
*/
|
|
|
|
|
|
|
|
while (tmp_str != NULL) {
|
|
|
|
if (strncmp(tmp_str, string, len) == 0 &&
|
|
|
|
(tmp_str[len] == ',' || tmp_str[len] == '\0'))
|
|
|
|
return (1);
|
|
|
|
tmp_str = strchr(tmp_str, ',');
|
|
|
|
if (tmp_str != NULL)
|
|
|
|
tmp_str++; /* Get rid of , */
|
|
|
|
}
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
dprintf_setup(int *argc, char **argv)
|
|
|
|
{
|
|
|
|
int i, j;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Debugging can be specified two ways: by setting the
|
|
|
|
* environment variable ZFS_DEBUG, or by including a
|
|
|
|
* "debug=..." argument on the command line. The command
|
|
|
|
* line setting overrides the environment variable.
|
|
|
|
*/
|
|
|
|
|
|
|
|
for (i = 1; i < *argc; i++) {
|
|
|
|
int len = strlen("debug=");
|
|
|
|
/* First look for a command line argument */
|
|
|
|
if (strncmp("debug=", argv[i], len) == 0) {
|
|
|
|
dprintf_string = argv[i] + len;
|
|
|
|
/* Remove from args */
|
|
|
|
for (j = i; j < *argc; j++)
|
|
|
|
argv[j] = argv[j+1];
|
|
|
|
argv[j] = NULL;
|
|
|
|
(*argc)--;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (dprintf_string == NULL) {
|
|
|
|
/* Look for ZFS_DEBUG environment variable */
|
|
|
|
dprintf_string = getenv("ZFS_DEBUG");
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Are we just turning on all debugging?
|
|
|
|
*/
|
|
|
|
if (dprintf_find_string("on"))
|
|
|
|
dprintf_print_all = 1;
|
2014-09-05 22:03:09 +00:00
|
|
|
|
|
|
|
if (dprintf_string != NULL)
|
|
|
|
zfs_flags |= ZFS_DEBUG_DPRINTF;
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* debug printfs
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
void
|
2018-10-15 19:14:22 +00:00
|
|
|
__dprintf(boolean_t dprint, const char *file, const char *func,
|
|
|
|
int line, const char *fmt, ...)
|
2008-11-20 20:01:55 +00:00
|
|
|
{
|
2021-05-22 15:19:14 +00:00
|
|
|
/* Get rid of annoying "../common/" prefix to filename. */
|
|
|
|
const char *newfile = zfs_basename(file);
|
2008-11-20 20:01:55 +00:00
|
|
|
|
2021-05-22 15:19:14 +00:00
|
|
|
va_list adx;
|
2018-10-15 19:14:22 +00:00
|
|
|
if (dprint) {
|
|
|
|
/* dprintf messages are printed immediately */
|
|
|
|
|
|
|
|
if (!dprintf_print_all &&
|
|
|
|
!dprintf_find_string(newfile) &&
|
|
|
|
!dprintf_find_string(func))
|
|
|
|
return;
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/* Print out just the function name if requested */
|
|
|
|
flockfile(stdout);
|
|
|
|
if (dprintf_find_string("pid"))
|
|
|
|
(void) printf("%d ", getpid());
|
|
|
|
if (dprintf_find_string("tid"))
|
2019-04-10 03:49:03 +00:00
|
|
|
(void) printf("%ju ",
|
|
|
|
(uintmax_t)(uintptr_t)pthread_self());
|
2008-11-20 20:01:55 +00:00
|
|
|
if (dprintf_find_string("cpu"))
|
|
|
|
(void) printf("%u ", getcpuid());
|
|
|
|
if (dprintf_find_string("time"))
|
|
|
|
(void) printf("%llu ", gethrtime());
|
|
|
|
if (dprintf_find_string("long"))
|
|
|
|
(void) printf("%s, line %d: ", newfile, line);
|
2018-10-15 19:14:22 +00:00
|
|
|
(void) printf("dprintf: %s: ", func);
|
2008-11-20 20:01:55 +00:00
|
|
|
va_start(adx, fmt);
|
|
|
|
(void) vprintf(fmt, adx);
|
|
|
|
va_end(adx);
|
|
|
|
funlockfile(stdout);
|
2018-10-15 19:14:22 +00:00
|
|
|
} else {
|
|
|
|
/* zfs_dbgmsg is logged for dumping later */
|
|
|
|
size_t size;
|
|
|
|
char *buf;
|
|
|
|
int i;
|
|
|
|
|
|
|
|
size = 1024;
|
|
|
|
buf = umem_alloc(size, UMEM_NOFAIL);
|
|
|
|
i = snprintf(buf, size, "%s:%d:%s(): ", newfile, line, func);
|
|
|
|
|
|
|
|
if (i < size) {
|
|
|
|
va_start(adx, fmt);
|
|
|
|
(void) vsnprintf(buf + i, size - i, fmt, adx);
|
|
|
|
va_end(adx);
|
|
|
|
}
|
|
|
|
|
|
|
|
__zfs_dbgmsg(buf);
|
|
|
|
|
|
|
|
umem_free(buf, size);
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* cmn_err() and panic()
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
static char ce_prefix[CE_IGNORE][10] = { "", "NOTICE: ", "WARNING: ", "" };
|
|
|
|
static char ce_suffix[CE_IGNORE][2] = { "", "\n", "\n", "" };
|
|
|
|
|
2022-03-23 15:51:00 +00:00
|
|
|
__attribute__((noreturn)) void
|
2008-11-20 20:01:55 +00:00
|
|
|
vpanic(const char *fmt, va_list adx)
|
|
|
|
{
|
|
|
|
(void) fprintf(stderr, "error: ");
|
|
|
|
(void) vfprintf(stderr, fmt, adx);
|
|
|
|
(void) fprintf(stderr, "\n");
|
|
|
|
|
|
|
|
abort(); /* think of it as a "user-level crash dump" */
|
|
|
|
}
|
|
|
|
|
2022-03-23 15:51:00 +00:00
|
|
|
__attribute__((noreturn)) void
|
2008-11-20 20:01:55 +00:00
|
|
|
panic(const char *fmt, ...)
|
|
|
|
{
|
|
|
|
va_list adx;
|
|
|
|
|
|
|
|
va_start(adx, fmt);
|
|
|
|
vpanic(fmt, adx);
|
|
|
|
va_end(adx);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
vcmn_err(int ce, const char *fmt, va_list adx)
|
|
|
|
{
|
|
|
|
if (ce == CE_PANIC)
|
|
|
|
vpanic(fmt, adx);
|
|
|
|
if (ce != CE_NOTE) { /* suppress noise in userland stress testing */
|
|
|
|
(void) fprintf(stderr, "%s", ce_prefix[ce]);
|
|
|
|
(void) vfprintf(stderr, fmt, adx);
|
|
|
|
(void) fprintf(stderr, "%s", ce_suffix[ce]);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
cmn_err(int ce, const char *fmt, ...)
|
|
|
|
{
|
|
|
|
va_list adx;
|
|
|
|
|
|
|
|
va_start(adx, fmt);
|
|
|
|
vcmn_err(ce, fmt, adx);
|
|
|
|
va_end(adx);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* misc routines
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
|
|
|
|
void
|
|
|
|
delay(clock_t ticks)
|
|
|
|
{
|
2016-10-11 18:32:34 +00:00
|
|
|
(void) poll(0, 0, ticks * (1000 / hz));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Find highest one bit set.
|
2017-08-09 22:31:08 +00:00
|
|
|
* Returns bit number + 1 of highest bit that is set, otherwise returns 0.
|
|
|
|
* The __builtin_clzll() function is supported by both GCC and Clang.
|
2008-11-20 20:01:55 +00:00
|
|
|
*/
|
|
|
|
int
|
2014-04-16 03:40:22 +00:00
|
|
|
highbit64(uint64_t i)
|
2008-11-20 20:01:55 +00:00
|
|
|
{
|
|
|
|
if (i == 0)
|
2017-08-09 22:31:08 +00:00
|
|
|
return (0);
|
|
|
|
|
|
|
|
return (NBBY * sizeof (uint64_t) - __builtin_clzll(i));
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
2016-02-29 18:05:23 +00:00
|
|
|
/*
|
|
|
|
* Find lowest one bit set.
|
|
|
|
* Returns bit number + 1 of lowest bit that is set, otherwise returns 0.
|
2017-08-09 22:31:08 +00:00
|
|
|
* The __builtin_ffsll() function is supported by both GCC and Clang.
|
2016-02-29 18:05:23 +00:00
|
|
|
*/
|
|
|
|
int
|
|
|
|
lowbit64(uint64_t i)
|
|
|
|
{
|
|
|
|
if (i == 0)
|
|
|
|
return (0);
|
|
|
|
|
2017-08-09 22:31:08 +00:00
|
|
|
return (__builtin_ffsll(i));
|
2016-05-12 14:51:24 +00:00
|
|
|
}
|
2016-02-29 18:05:23 +00:00
|
|
|
|
2021-04-08 20:17:38 +00:00
|
|
|
const char *random_path = "/dev/random";
|
|
|
|
const char *urandom_path = "/dev/urandom";
|
2008-11-20 20:01:55 +00:00
|
|
|
static int random_fd = -1, urandom_fd = -1;
|
|
|
|
|
2016-05-12 14:51:24 +00:00
|
|
|
void
|
|
|
|
random_init(void)
|
|
|
|
{
|
2021-04-08 20:17:38 +00:00
|
|
|
VERIFY((random_fd = open(random_path, O_RDONLY | O_CLOEXEC)) != -1);
|
|
|
|
VERIFY((urandom_fd = open(urandom_path, O_RDONLY | O_CLOEXEC)) != -1);
|
2016-05-12 14:51:24 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
random_fini(void)
|
|
|
|
{
|
|
|
|
close(random_fd);
|
|
|
|
close(urandom_fd);
|
|
|
|
|
|
|
|
random_fd = -1;
|
|
|
|
urandom_fd = -1;
|
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
static int
|
|
|
|
random_get_bytes_common(uint8_t *ptr, size_t len, int fd)
|
|
|
|
{
|
|
|
|
size_t resid = len;
|
|
|
|
ssize_t bytes;
|
|
|
|
|
|
|
|
ASSERT(fd != -1);
|
|
|
|
|
|
|
|
while (resid != 0) {
|
|
|
|
bytes = read(fd, ptr, resid);
|
|
|
|
ASSERT3S(bytes, >=, 0);
|
|
|
|
ptr += bytes;
|
|
|
|
resid -= bytes;
|
|
|
|
}
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
random_get_bytes(uint8_t *ptr, size_t len)
|
|
|
|
{
|
|
|
|
return (random_get_bytes_common(ptr, len, random_fd));
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
random_get_pseudo_bytes(uint8_t *ptr, size_t len)
|
|
|
|
{
|
|
|
|
return (random_get_bytes_common(ptr, len, urandom_fd));
|
|
|
|
}
|
|
|
|
|
2010-05-28 20:45:14 +00:00
|
|
|
int
|
|
|
|
ddi_strtoull(const char *str, char **nptr, int base, u_longlong_t *result)
|
|
|
|
{
|
2023-01-09 20:49:35 +00:00
|
|
|
errno = 0;
|
|
|
|
*result = strtoull(str, nptr, base);
|
2010-05-28 20:45:14 +00:00
|
|
|
if (*result == 0)
|
|
|
|
return (errno);
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2014-10-01 19:02:12 +00:00
|
|
|
utsname_t *
|
|
|
|
utsname(void)
|
|
|
|
{
|
|
|
|
return (&hw_utsname);
|
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
/*
|
|
|
|
* =========================================================================
|
|
|
|
* kernel emulation setup & teardown
|
|
|
|
* =========================================================================
|
|
|
|
*/
|
|
|
|
static int
|
|
|
|
umem_out_of_memory(void)
|
|
|
|
{
|
|
|
|
char errmsg[] = "out of memory -- generating core dump\n";
|
|
|
|
|
2010-08-26 16:52:40 +00:00
|
|
|
(void) fprintf(stderr, "%s", errmsg);
|
2008-11-20 20:01:55 +00:00
|
|
|
abort();
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
kernel_init(int mode)
|
|
|
|
{
|
2013-09-04 12:00:57 +00:00
|
|
|
extern uint_t rrw_tsd_key;
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
umem_nofail_callback(umem_out_of_memory);
|
|
|
|
|
|
|
|
physmem = sysconf(_SC_PHYS_PAGES);
|
|
|
|
|
2021-06-23 04:53:45 +00:00
|
|
|
dprintf("physmem = %llu pages (%.2f GB)\n", (u_longlong_t)physmem,
|
2008-11-20 20:01:55 +00:00
|
|
|
(double)physmem * sysconf(_SC_PAGE_SIZE) / (1ULL << 30));
|
|
|
|
|
2022-05-07 17:18:41 +00:00
|
|
|
hostid = (mode & SPA_MODE_WRITE) ? get_system_hostid() : 0;
|
2008-11-20 20:01:55 +00:00
|
|
|
|
2016-05-12 14:51:24 +00:00
|
|
|
random_init();
|
|
|
|
|
2014-10-01 19:02:12 +00:00
|
|
|
VERIFY0(uname(&hw_utsname));
|
2008-11-20 20:01:55 +00:00
|
|
|
|
2008-12-03 20:09:06 +00:00
|
|
|
system_taskq_init();
|
2016-05-12 14:51:24 +00:00
|
|
|
icp_init();
|
2008-12-03 20:09:06 +00:00
|
|
|
|
Add zstd support to zfs
This PR adds two new compression types, based on ZStandard:
- zstd: A basic ZStandard compression algorithm Available compression.
Levels for zstd are zstd-1 through zstd-19, where the compression
increases with every level, but speed decreases.
- zstd-fast: A faster version of the ZStandard compression algorithm
zstd-fast is basically a "negative" level of zstd. The compression
decreases with every level, but speed increases.
Available compression levels for zstd-fast:
- zstd-fast-1 through zstd-fast-10
- zstd-fast-20 through zstd-fast-100 (in increments of 10)
- zstd-fast-500 and zstd-fast-1000
For more information check the man page.
Implementation details:
Rather than treat each level of zstd as a different algorithm (as was
done historically with gzip), the block pointer `enum zio_compress`
value is simply zstd for all levels, including zstd-fast, since they all
use the same decompression function.
The compress= property (a 64bit unsigned integer) uses the lower 7 bits
to store the compression algorithm (matching the number of bits used in
a block pointer, as the 8th bit was borrowed for embedded block
pointers). The upper bits are used to store the compression level.
It is necessary to be able to determine what compression level was used
when later reading a block back, so the concept used in LZ4, where the
first 32bits of the on-disk value are the size of the compressed data
(since the allocation is rounded up to the nearest ashift), was
extended, and we store the version of ZSTD and the level as well as the
compressed size. This value is returned when decompressing a block, so
that if the block needs to be recompressed (L2ARC, nop-write, etc), that
the same parameters will be used to result in the matching checksum.
All of the internal ZFS code ( `arc_buf_hdr_t`, `objset_t`,
`zio_prop_t`, etc.) uses the separated _compress and _complevel
variables. Only the properties ZAP contains the combined/bit-shifted
value. The combined value is split when the compression_changed_cb()
callback is called, and sets both objset members (os_compress and
os_complevel).
The userspace tools all use the combined/bit-shifted value.
Additional notes:
zdb can now also decode the ZSTD compression header (flag -Z) and
inspect the size, version and compression level saved in that header.
For each record, if it is ZSTD compressed, the parameters of the decoded
compression header get printed.
ZSTD is included with all current tests and new tests are added
as-needed.
Per-dataset feature flags now get activated when the property is set.
If a compression algorithm requires a feature flag, zfs activates the
feature when the property is set, rather than waiting for the first
block to be born. This is currently only used by zstd but can be
extended as needed.
Portions-Sponsored-By: The FreeBSD Foundation
Co-authored-by: Allan Jude <allanjude@freebsd.org>
Co-authored-by: Brian Behlendorf <behlendorf1@llnl.gov>
Co-authored-by: Sebastian Gottschall <s.gottschall@dd-wrt.com>
Co-authored-by: Kjeld Schouten-Lebbing <kjeld@schouten-lebbing.nl>
Co-authored-by: Michael Niewöhner <foss@mniewoehner.de>
Signed-off-by: Allan Jude <allan@klarasystems.com>
Signed-off-by: Allan Jude <allanjude@freebsd.org>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Sebastian Gottschall <s.gottschall@dd-wrt.com>
Signed-off-by: Kjeld Schouten-Lebbing <kjeld@schouten-lebbing.nl>
Signed-off-by: Michael Niewöhner <foss@mniewoehner.de>
Closes #6247
Closes #9024
Closes #10277
Closes #10278
2020-08-18 17:10:17 +00:00
|
|
|
zstd_init();
|
|
|
|
|
2019-11-21 17:32:57 +00:00
|
|
|
spa_init((spa_mode_t)mode);
|
2013-09-04 12:00:57 +00:00
|
|
|
|
2015-12-09 23:34:16 +00:00
|
|
|
fletcher_4_init();
|
|
|
|
|
2013-09-04 12:00:57 +00:00
|
|
|
tsd_create(&rrw_tsd_key, rrw_tsd_destroy);
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
kernel_fini(void)
|
|
|
|
{
|
2015-12-09 23:34:16 +00:00
|
|
|
fletcher_4_fini();
|
2008-11-20 20:01:55 +00:00
|
|
|
spa_fini();
|
|
|
|
|
Add zstd support to zfs
This PR adds two new compression types, based on ZStandard:
- zstd: A basic ZStandard compression algorithm Available compression.
Levels for zstd are zstd-1 through zstd-19, where the compression
increases with every level, but speed decreases.
- zstd-fast: A faster version of the ZStandard compression algorithm
zstd-fast is basically a "negative" level of zstd. The compression
decreases with every level, but speed increases.
Available compression levels for zstd-fast:
- zstd-fast-1 through zstd-fast-10
- zstd-fast-20 through zstd-fast-100 (in increments of 10)
- zstd-fast-500 and zstd-fast-1000
For more information check the man page.
Implementation details:
Rather than treat each level of zstd as a different algorithm (as was
done historically with gzip), the block pointer `enum zio_compress`
value is simply zstd for all levels, including zstd-fast, since they all
use the same decompression function.
The compress= property (a 64bit unsigned integer) uses the lower 7 bits
to store the compression algorithm (matching the number of bits used in
a block pointer, as the 8th bit was borrowed for embedded block
pointers). The upper bits are used to store the compression level.
It is necessary to be able to determine what compression level was used
when later reading a block back, so the concept used in LZ4, where the
first 32bits of the on-disk value are the size of the compressed data
(since the allocation is rounded up to the nearest ashift), was
extended, and we store the version of ZSTD and the level as well as the
compressed size. This value is returned when decompressing a block, so
that if the block needs to be recompressed (L2ARC, nop-write, etc), that
the same parameters will be used to result in the matching checksum.
All of the internal ZFS code ( `arc_buf_hdr_t`, `objset_t`,
`zio_prop_t`, etc.) uses the separated _compress and _complevel
variables. Only the properties ZAP contains the combined/bit-shifted
value. The combined value is split when the compression_changed_cb()
callback is called, and sets both objset members (os_compress and
os_complevel).
The userspace tools all use the combined/bit-shifted value.
Additional notes:
zdb can now also decode the ZSTD compression header (flag -Z) and
inspect the size, version and compression level saved in that header.
For each record, if it is ZSTD compressed, the parameters of the decoded
compression header get printed.
ZSTD is included with all current tests and new tests are added
as-needed.
Per-dataset feature flags now get activated when the property is set.
If a compression algorithm requires a feature flag, zfs activates the
feature when the property is set, rather than waiting for the first
block to be born. This is currently only used by zstd but can be
extended as needed.
Portions-Sponsored-By: The FreeBSD Foundation
Co-authored-by: Allan Jude <allanjude@freebsd.org>
Co-authored-by: Brian Behlendorf <behlendorf1@llnl.gov>
Co-authored-by: Sebastian Gottschall <s.gottschall@dd-wrt.com>
Co-authored-by: Kjeld Schouten-Lebbing <kjeld@schouten-lebbing.nl>
Co-authored-by: Michael Niewöhner <foss@mniewoehner.de>
Signed-off-by: Allan Jude <allan@klarasystems.com>
Signed-off-by: Allan Jude <allanjude@freebsd.org>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Sebastian Gottschall <s.gottschall@dd-wrt.com>
Signed-off-by: Kjeld Schouten-Lebbing <kjeld@schouten-lebbing.nl>
Signed-off-by: Michael Niewöhner <foss@mniewoehner.de>
Closes #6247
Closes #9024
Closes #10277
Closes #10278
2020-08-18 17:10:17 +00:00
|
|
|
zstd_fini();
|
|
|
|
|
2016-05-12 14:51:24 +00:00
|
|
|
icp_fini();
|
2010-05-28 20:45:14 +00:00
|
|
|
system_taskq_fini();
|
|
|
|
|
2016-05-12 14:51:24 +00:00
|
|
|
random_fini();
|
2008-11-20 20:01:55 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
uid_t
|
|
|
|
crgetuid(cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2013-08-28 11:45:09 +00:00
|
|
|
uid_t
|
|
|
|
crgetruid(cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr;
|
2013-08-28 11:45:09 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
gid_t
|
|
|
|
crgetgid(cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
crgetngroups(cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
gid_t *
|
|
|
|
crgetgroups(cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (NULL);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
zfs_secpolicy_snapshot_perms(const char *name, cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name, (void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
zfs_secpolicy_rename_perms(const char *from, const char *to, cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) from, (void) to, (void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
zfs_secpolicy_destroy_perms(const char *name, cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name, (void) cr;
|
2008-11-20 20:01:55 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2016-06-07 16:16:52 +00:00
|
|
|
int
|
|
|
|
secpolicy_zfs(const cred_t *cr)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr;
|
2016-06-07 16:16:52 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2020-07-12 00:18:02 +00:00
|
|
|
int
|
|
|
|
secpolicy_zfs_proc(const cred_t *cr, proc_t *proc)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cr, (void) proc;
|
2020-07-12 00:18:02 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2008-11-20 20:01:55 +00:00
|
|
|
ksiddomain_t *
|
|
|
|
ksid_lookupdomain(const char *dom)
|
|
|
|
{
|
|
|
|
ksiddomain_t *kd;
|
|
|
|
|
|
|
|
kd = umem_zalloc(sizeof (ksiddomain_t), UMEM_NOFAIL);
|
|
|
|
kd->kd_name = spa_strdup(dom);
|
|
|
|
return (kd);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
ksiddomain_rele(ksiddomain_t *ksid)
|
|
|
|
{
|
|
|
|
spa_strfree(ksid->kd_name);
|
|
|
|
umem_free(ksid, sizeof (ksiddomain_t));
|
|
|
|
}
|
2010-05-28 20:45:14 +00:00
|
|
|
|
|
|
|
char *
|
2010-08-26 18:46:09 +00:00
|
|
|
kmem_vasprintf(const char *fmt, va_list adx)
|
2010-05-28 20:45:14 +00:00
|
|
|
{
|
2010-08-26 18:46:09 +00:00
|
|
|
char *buf = NULL;
|
|
|
|
va_list adx_copy;
|
2010-05-28 20:45:14 +00:00
|
|
|
|
2010-08-26 18:46:09 +00:00
|
|
|
va_copy(adx_copy, adx);
|
|
|
|
VERIFY(vasprintf(&buf, fmt, adx_copy) != -1);
|
|
|
|
va_end(adx_copy);
|
2010-05-28 20:45:14 +00:00
|
|
|
|
2010-08-26 18:46:09 +00:00
|
|
|
return (buf);
|
|
|
|
}
|
|
|
|
|
|
|
|
char *
|
|
|
|
kmem_asprintf(const char *fmt, ...)
|
|
|
|
{
|
|
|
|
char *buf = NULL;
|
|
|
|
va_list adx;
|
2010-05-28 20:45:14 +00:00
|
|
|
|
|
|
|
va_start(adx, fmt);
|
2010-08-26 18:46:09 +00:00
|
|
|
VERIFY(vasprintf(&buf, fmt, adx) != -1);
|
2010-05-28 20:45:14 +00:00
|
|
|
va_end(adx);
|
|
|
|
|
|
|
|
return (buf);
|
|
|
|
}
|
2010-08-26 21:24:34 +00:00
|
|
|
|
Introduce kmem_scnprintf()
`snprintf()` is meant to protect against buffer overflows, but operating
on the buffer using its return value, possibly by calling it again, can
cause a buffer overflow, because it will return how many characters it
would have written if it had enough space even when it did not. In a
number of places, we repeatedly call snprintf() by successively
incrementing a buffer offset and decrementing a buffer length, by its
return value. This is a potentially unsafe usage of `snprintf()`
whenever the buffer length is reached. CodeQL complained about this.
To fix this, we introduce `kmem_scnprintf()`, which will return 0 when
the buffer is zero or the number of written characters, minus 1 to
exclude the NULL character, when the buffer was too small. In all other
cases, it behaves like snprintf(). The name is inspired by the Linux and
XNU kernels' `scnprintf()`. The implementation was written before I
thought to look at `scnprintf()` and had a good name for it, but it
turned out to have identical semantics to the Linux kernel version.
That lead to the name, `kmem_scnprintf()`.
CodeQL only catches this issue in loops, so repeated use of snprintf()
outside of a loop was not caught. As a result, a thorough audit of the
codebase was done to examine all instances of `snprintf()` usage for
potential problems and a few were caught. Fixes for them are included in
this patch.
Unfortunately, ZED is one of the places where `snprintf()` is
potentially used incorrectly. Since using `kmem_scnprintf()` in it would
require changing how it is linked, we modify its usage to make it safe,
no matter what buffer length is used. In addition, there was a bug in
the use of the return value where the NULL format character was not
being written by pwrite(). That has been fixed.
Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Richard Yao <richard.yao@alumni.stonybrook.edu>
Closes #14098
2022-10-27 18:16:04 +00:00
|
|
|
/*
|
|
|
|
* kmem_scnprintf() will return the number of characters that it would have
|
|
|
|
* printed whenever it is limited by value of the size variable, rather than
|
|
|
|
* the number of characters that it did print. This can cause misbehavior on
|
|
|
|
* subsequent uses of the return value, so we define a safe version that will
|
|
|
|
* return the number of characters actually printed, minus the NULL format
|
|
|
|
* character. Subsequent use of this by the safe string functions is safe
|
|
|
|
* whether it is snprintf(), strlcat() or strlcpy().
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
kmem_scnprintf(char *restrict str, size_t size, const char *restrict fmt, ...)
|
|
|
|
{
|
|
|
|
int n;
|
|
|
|
va_list ap;
|
|
|
|
|
|
|
|
/* Make the 0 case a no-op so that we do not return -1 */
|
|
|
|
if (size == 0)
|
|
|
|
return (0);
|
|
|
|
|
|
|
|
va_start(ap, fmt);
|
|
|
|
n = vsnprintf(str, size, fmt, ap);
|
|
|
|
va_end(ap);
|
|
|
|
|
|
|
|
if (n >= size)
|
|
|
|
n = size - 1;
|
|
|
|
|
|
|
|
return (n);
|
|
|
|
}
|
|
|
|
|
2021-07-11 01:00:37 +00:00
|
|
|
zfs_file_t *
|
2010-08-26 21:24:34 +00:00
|
|
|
zfs_onexit_fd_hold(int fd, minor_t *minorp)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) fd;
|
2010-08-26 21:24:34 +00:00
|
|
|
*minorp = 0;
|
2021-07-11 01:00:37 +00:00
|
|
|
return (NULL);
|
2010-08-26 21:24:34 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2021-07-11 01:00:37 +00:00
|
|
|
zfs_onexit_fd_rele(zfs_file_t *fp)
|
2010-08-26 21:24:34 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) fp;
|
2010-08-26 21:24:34 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
zfs_onexit_add_cb(minor_t minor, void (*func)(void *), void *data,
|
2022-10-27 22:20:05 +00:00
|
|
|
uintptr_t *action_handle)
|
2010-08-26 21:24:34 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) minor, (void) func, (void) data, (void) action_handle;
|
2010-08-26 21:24:34 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2014-07-13 18:35:19 +00:00
|
|
|
fstrans_cookie_t
|
|
|
|
spl_fstrans_mark(void)
|
|
|
|
{
|
2016-12-12 18:46:26 +00:00
|
|
|
return ((fstrans_cookie_t)0);
|
2014-07-13 18:35:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
spl_fstrans_unmark(fstrans_cookie_t cookie)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) cookie;
|
2014-07-13 18:35:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2017-05-09 17:38:46 +00:00
|
|
|
__spl_pf_fstrans_check(void)
|
2014-07-13 18:35:19 +00:00
|
|
|
{
|
|
|
|
return (0);
|
|
|
|
}
|
2014-03-22 09:07:14 +00:00
|
|
|
|
2017-03-15 23:41:52 +00:00
|
|
|
int
|
|
|
|
kmem_cache_reap_active(void)
|
|
|
|
{
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2014-03-22 09:07:14 +00:00
|
|
|
void
|
2020-06-09 22:59:04 +00:00
|
|
|
zvol_create_minor(const char *name)
|
2014-03-22 09:07:14 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name;
|
2014-03-22 09:07:14 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2020-06-09 22:59:04 +00:00
|
|
|
zvol_create_minors_recursive(const char *name)
|
2014-03-22 09:07:14 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) name;
|
2014-03-22 09:07:14 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
zvol_remove_minors(spa_t *spa, const char *name, boolean_t async)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) spa, (void) name, (void) async;
|
2014-03-22 09:07:14 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
zvol_rename_minors(spa_t *spa, const char *oldname, const char *newname,
|
|
|
|
boolean_t async)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) spa, (void) oldname, (void) newname, (void) async;
|
2014-03-22 09:07:14 +00:00
|
|
|
}
|
2019-11-21 17:32:57 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Open file
|
|
|
|
*
|
|
|
|
* path - fully qualified path to file
|
|
|
|
* flags - file attributes O_READ / O_WRITE / O_EXCL
|
|
|
|
* fpp - pointer to return file pointer
|
|
|
|
*
|
|
|
|
* Returns 0 on success underlying error on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_open(const char *path, int flags, int mode, zfs_file_t **fpp)
|
|
|
|
{
|
|
|
|
int fd = -1;
|
|
|
|
int dump_fd = -1;
|
|
|
|
int err;
|
|
|
|
int old_umask = 0;
|
|
|
|
zfs_file_t *fp;
|
|
|
|
struct stat64 st;
|
|
|
|
|
|
|
|
if (!(flags & O_CREAT) && stat64(path, &st) == -1)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
if (!(flags & O_CREAT) && S_ISBLK(st.st_mode))
|
|
|
|
flags |= O_DIRECT;
|
|
|
|
|
|
|
|
if (flags & O_CREAT)
|
|
|
|
old_umask = umask(0);
|
|
|
|
|
|
|
|
fd = open64(path, flags, mode);
|
|
|
|
if (fd == -1)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
if (flags & O_CREAT)
|
|
|
|
(void) umask(old_umask);
|
|
|
|
|
|
|
|
if (vn_dumpdir != NULL) {
|
|
|
|
char *dumppath = umem_zalloc(MAXPATHLEN, UMEM_NOFAIL);
|
2021-05-22 15:19:14 +00:00
|
|
|
const char *inpath = zfs_basename(path);
|
2019-11-21 17:32:57 +00:00
|
|
|
|
|
|
|
(void) snprintf(dumppath, MAXPATHLEN,
|
|
|
|
"%s/%s", vn_dumpdir, inpath);
|
|
|
|
dump_fd = open64(dumppath, O_CREAT | O_WRONLY, 0666);
|
|
|
|
umem_free(dumppath, MAXPATHLEN);
|
|
|
|
if (dump_fd == -1) {
|
|
|
|
err = errno;
|
|
|
|
close(fd);
|
|
|
|
return (err);
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
dump_fd = -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
(void) fcntl(fd, F_SETFD, FD_CLOEXEC);
|
|
|
|
|
|
|
|
fp = umem_zalloc(sizeof (zfs_file_t), UMEM_NOFAIL);
|
|
|
|
fp->f_fd = fd;
|
|
|
|
fp->f_dump_fd = dump_fd;
|
|
|
|
*fpp = fp;
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
zfs_file_close(zfs_file_t *fp)
|
|
|
|
{
|
|
|
|
close(fp->f_fd);
|
|
|
|
if (fp->f_dump_fd != -1)
|
|
|
|
close(fp->f_dump_fd);
|
|
|
|
|
|
|
|
umem_free(fp, sizeof (zfs_file_t));
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Stateful write - use os internal file pointer to determine where to
|
|
|
|
* write and update on successful completion.
|
|
|
|
*
|
|
|
|
* fp - pointer to file (pipe, socket, etc) to write to
|
|
|
|
* buf - buffer to write
|
|
|
|
* count - # of bytes to write
|
|
|
|
* resid - pointer to count of unwritten bytes (if short write)
|
|
|
|
*
|
|
|
|
* Returns 0 on success errno on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_write(zfs_file_t *fp, const void *buf, size_t count, ssize_t *resid)
|
|
|
|
{
|
|
|
|
ssize_t rc;
|
|
|
|
|
|
|
|
rc = write(fp->f_fd, buf, count);
|
|
|
|
if (rc < 0)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
if (resid) {
|
|
|
|
*resid = count - rc;
|
|
|
|
} else if (rc != count) {
|
|
|
|
return (EIO);
|
|
|
|
}
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Stateless write - os internal file pointer is not updated.
|
|
|
|
*
|
|
|
|
* fp - pointer to file (pipe, socket, etc) to write to
|
|
|
|
* buf - buffer to write
|
|
|
|
* count - # of bytes to write
|
|
|
|
* off - file offset to write to (only valid for seekable types)
|
|
|
|
* resid - pointer to count of unwritten bytes
|
|
|
|
*
|
|
|
|
* Returns 0 on success errno on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_pwrite(zfs_file_t *fp, const void *buf,
|
|
|
|
size_t count, loff_t pos, ssize_t *resid)
|
|
|
|
{
|
|
|
|
ssize_t rc, split, done;
|
|
|
|
int sectors;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* To simulate partial disk writes, we split writes into two
|
|
|
|
* system calls so that the process can be killed in between.
|
|
|
|
* This is used by ztest to simulate realistic failure modes.
|
|
|
|
*/
|
|
|
|
sectors = count >> SPA_MINBLOCKSHIFT;
|
|
|
|
split = (sectors > 0 ? rand() % sectors : 0) << SPA_MINBLOCKSHIFT;
|
|
|
|
rc = pwrite64(fp->f_fd, buf, split, pos);
|
|
|
|
if (rc != -1) {
|
|
|
|
done = rc;
|
|
|
|
rc = pwrite64(fp->f_fd, (char *)buf + split,
|
|
|
|
count - split, pos + split);
|
|
|
|
}
|
|
|
|
#ifdef __linux__
|
|
|
|
if (rc == -1 && errno == EINVAL) {
|
|
|
|
/*
|
|
|
|
* Under Linux, this most likely means an alignment issue
|
|
|
|
* (memory or disk) due to O_DIRECT, so we abort() in order
|
|
|
|
* to catch the offender.
|
|
|
|
*/
|
|
|
|
abort();
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
|
|
if (rc < 0)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
done += rc;
|
|
|
|
|
|
|
|
if (resid) {
|
|
|
|
*resid = count - done;
|
|
|
|
} else if (done != count) {
|
|
|
|
return (EIO);
|
|
|
|
}
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Stateful read - use os internal file pointer to determine where to
|
|
|
|
* read and update on successful completion.
|
|
|
|
*
|
|
|
|
* fp - pointer to file (pipe, socket, etc) to read from
|
|
|
|
* buf - buffer to write
|
|
|
|
* count - # of bytes to read
|
|
|
|
* resid - pointer to count of unread bytes (if short read)
|
|
|
|
*
|
|
|
|
* Returns 0 on success errno on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_read(zfs_file_t *fp, void *buf, size_t count, ssize_t *resid)
|
|
|
|
{
|
|
|
|
int rc;
|
|
|
|
|
|
|
|
rc = read(fp->f_fd, buf, count);
|
|
|
|
if (rc < 0)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
if (resid) {
|
|
|
|
*resid = count - rc;
|
|
|
|
} else if (rc != count) {
|
|
|
|
return (EIO);
|
|
|
|
}
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Stateless read - os internal file pointer is not updated.
|
|
|
|
*
|
|
|
|
* fp - pointer to file (pipe, socket, etc) to read from
|
|
|
|
* buf - buffer to write
|
|
|
|
* count - # of bytes to write
|
|
|
|
* off - file offset to read from (only valid for seekable types)
|
|
|
|
* resid - pointer to count of unwritten bytes (if short write)
|
|
|
|
*
|
|
|
|
* Returns 0 on success errno on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_pread(zfs_file_t *fp, void *buf, size_t count, loff_t off,
|
|
|
|
ssize_t *resid)
|
|
|
|
{
|
|
|
|
ssize_t rc;
|
|
|
|
|
|
|
|
rc = pread64(fp->f_fd, buf, count, off);
|
|
|
|
if (rc < 0) {
|
|
|
|
#ifdef __linux__
|
|
|
|
/*
|
|
|
|
* Under Linux, this most likely means an alignment issue
|
|
|
|
* (memory or disk) due to O_DIRECT, so we abort() in order to
|
|
|
|
* catch the offender.
|
|
|
|
*/
|
|
|
|
if (errno == EINVAL)
|
|
|
|
abort();
|
|
|
|
#endif
|
|
|
|
return (errno);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (fp->f_dump_fd != -1) {
|
|
|
|
int status;
|
|
|
|
|
|
|
|
status = pwrite64(fp->f_dump_fd, buf, rc, off);
|
|
|
|
ASSERT(status != -1);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (resid) {
|
|
|
|
*resid = count - rc;
|
|
|
|
} else if (rc != count) {
|
|
|
|
return (EIO);
|
|
|
|
}
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* lseek - set / get file pointer
|
|
|
|
*
|
|
|
|
* fp - pointer to file (pipe, socket, etc) to read from
|
|
|
|
* offp - value to seek to, returns current value plus passed offset
|
|
|
|
* whence - see man pages for standard lseek whence values
|
|
|
|
*
|
|
|
|
* Returns 0 on success errno on failure (ESPIPE for non seekable types)
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_seek(zfs_file_t *fp, loff_t *offp, int whence)
|
|
|
|
{
|
|
|
|
loff_t rc;
|
|
|
|
|
|
|
|
rc = lseek(fp->f_fd, *offp, whence);
|
|
|
|
if (rc < 0)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
*offp = rc;
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Get file attributes
|
|
|
|
*
|
|
|
|
* filp - file pointer
|
|
|
|
* zfattr - pointer to file attr structure
|
|
|
|
*
|
|
|
|
* Currently only used for fetching size and file mode
|
|
|
|
*
|
|
|
|
* Returns 0 on success or error code of underlying getattr call on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_getattr(zfs_file_t *fp, zfs_file_attr_t *zfattr)
|
|
|
|
{
|
|
|
|
struct stat64 st;
|
|
|
|
|
|
|
|
if (fstat64_blk(fp->f_fd, &st) == -1)
|
|
|
|
return (errno);
|
|
|
|
|
|
|
|
zfattr->zfa_size = st.st_size;
|
|
|
|
zfattr->zfa_mode = st.st_mode;
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Sync file to disk
|
|
|
|
*
|
|
|
|
* filp - file pointer
|
|
|
|
* flags - O_SYNC and or O_DSYNC
|
|
|
|
*
|
|
|
|
* Returns 0 on success or error code of underlying sync call on failure.
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_fsync(zfs_file_t *fp, int flags)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) flags;
|
2019-11-21 17:32:57 +00:00
|
|
|
|
2021-12-12 15:01:06 +00:00
|
|
|
if (fsync(fp->f_fd) < 0)
|
2019-11-21 17:32:57 +00:00
|
|
|
return (errno);
|
|
|
|
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* fallocate - allocate or free space on disk
|
|
|
|
*
|
|
|
|
* fp - file pointer
|
|
|
|
* mode (non-standard options for hole punching etc)
|
|
|
|
* offset - offset to start allocating or freeing from
|
|
|
|
* len - length to free / allocate
|
|
|
|
*
|
|
|
|
* OPTIONAL
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_fallocate(zfs_file_t *fp, int mode, loff_t offset, loff_t len)
|
|
|
|
{
|
2019-11-30 23:40:22 +00:00
|
|
|
#ifdef __linux__
|
2019-11-21 17:32:57 +00:00
|
|
|
return (fallocate(fp->f_fd, mode, offset, len));
|
2019-11-30 23:40:22 +00:00
|
|
|
#else
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) fp, (void) mode, (void) offset, (void) len;
|
2019-11-30 23:40:22 +00:00
|
|
|
return (EOPNOTSUPP);
|
|
|
|
#endif
|
2019-11-21 17:32:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Request current file pointer offset
|
|
|
|
*
|
|
|
|
* fp - pointer to file
|
|
|
|
*
|
|
|
|
* Returns current file offset.
|
|
|
|
*/
|
|
|
|
loff_t
|
|
|
|
zfs_file_off(zfs_file_t *fp)
|
|
|
|
{
|
|
|
|
return (lseek(fp->f_fd, SEEK_CUR, 0));
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* unlink file
|
|
|
|
*
|
|
|
|
* path - fully qualified file path
|
|
|
|
*
|
|
|
|
* Returns 0 on success.
|
|
|
|
*
|
|
|
|
* OPTIONAL
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
zfs_file_unlink(const char *path)
|
|
|
|
{
|
|
|
|
return (remove(path));
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Get reference to file pointer
|
|
|
|
*
|
|
|
|
* fd - input file descriptor
|
|
|
|
*
|
2021-07-11 01:00:37 +00:00
|
|
|
* Returns pointer to file struct or NULL.
|
2019-11-21 17:32:57 +00:00
|
|
|
* Unsupported in user space.
|
|
|
|
*/
|
2021-07-11 01:00:37 +00:00
|
|
|
zfs_file_t *
|
|
|
|
zfs_file_get(int fd)
|
2019-11-21 17:32:57 +00:00
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) fd;
|
2019-11-21 17:32:57 +00:00
|
|
|
abort();
|
2021-07-11 01:00:37 +00:00
|
|
|
return (NULL);
|
2019-11-21 17:32:57 +00:00
|
|
|
}
|
|
|
|
/*
|
|
|
|
* Drop reference to file pointer
|
|
|
|
*
|
2021-07-11 01:00:37 +00:00
|
|
|
* fp - pointer to file struct
|
2019-11-21 17:32:57 +00:00
|
|
|
*
|
|
|
|
* Unsupported in user space.
|
|
|
|
*/
|
|
|
|
void
|
2021-07-11 01:00:37 +00:00
|
|
|
zfs_file_put(zfs_file_t *fp)
|
2019-11-21 17:32:57 +00:00
|
|
|
{
|
|
|
|
abort();
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) fp;
|
2019-11-21 17:32:57 +00:00
|
|
|
}
|
2020-09-01 23:14:16 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
zfsvfs_update_fromname(const char *oldname, const char *newname)
|
|
|
|
{
|
2021-12-12 15:01:06 +00:00
|
|
|
(void) oldname, (void) newname;
|
2020-09-01 23:14:16 +00:00
|
|
|
}
|
2022-02-15 23:54:25 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
spa_import_os(spa_t *spa)
|
|
|
|
{
|
|
|
|
(void) spa;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
spa_export_os(spa_t *spa)
|
|
|
|
{
|
|
|
|
(void) spa;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
spa_activate_os(spa_t *spa)
|
|
|
|
{
|
|
|
|
(void) spa;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
spa_deactivate_os(spa_t *spa)
|
|
|
|
{
|
|
|
|
(void) spa;
|
|
|
|
}
|