Index: stand/libsa/zfs/Makefile.inc =================================================================== --- stand/libsa/zfs/Makefile.inc +++ stand/libsa/zfs/Makefile.inc @@ -3,11 +3,13 @@ .PATH: ${ZFSSRC} .PATH: ${SYSDIR}/crypto/skein .PATH: ${ZFSOSSRC}/spl +.PATH: ${OZFS}/module/zstd .PATH: ${OZFS}/module/zstd/lib/common .PATH: ${OZFS}/module/zstd/lib/compress .PATH: ${OZFS}/module/zstd/lib/decompress +.PATH: ${OZFS}/module/icp/algs/blake3 ZFS_SRC= zfs.c nvlist.c skein.c skein_block.c list.c -ZFS_SRC+= zstd_shim.c +ZFS_SRC+= zfs_zstd.c blake3.c blake3_generic.c blake3_impl.c ZSTD_SRC+= entropy_common.c error_private.c ZSTD_SRC+= fse_compress.c fse_decompress.c hist.c ZSTD_SRC+= huf_compress.c huf_decompress.c pool.c xxhash.c @@ -24,17 +26,21 @@ CFLAGS+= -I${SYSDIR}/cddl/boot/zfs CFLAGS+= -I${SYSDIR}/crypto/skein -ZFS_EARLY= -I${ZFSOSINC} \ +ZFS_EARLY= -I${ZFSSRC}/spl \ + -I${ZFSOSINC} \ -I${ZFSOSINC}/spl \ -I${ZFSOSINC}/zfs .for i in ${ZFS_SRC} ${ZSTD_SRC} -CFLAGS.$i+= -include ${ZFSOSINC}/spl/sys/ccompile.h -CFLAGS.$i+= -Wformat -Wall +CFLAGS.$i+= -include ${ZFSOSINC}/spl/sys/ccompile.h -Wformat -Wall -I${OZFS}/include \ + -DNEED_SOLARIS_BOOLEAN .endfor +CFLAGS_EARLY.blake3.c+= ${ZFS_EARLY} +CFLAGS_EARLY.blake3_generic.c+= ${ZFS_EARLY} +CFLAGS_EARLY.blake3_impl.c+= ${ZFS_EARLY} CFLAGS_EARLY.list.c+= ${ZFS_EARLY} -CFLAGS_EARLY.zstd_shim.c+= ${ZFS_EARLY} +CFLAGS_EARLY.zfs_zstd.c+= ${ZFS_EARLY} # Can't use the early flags because there's two conflicting definitions of boolean_t in # the zfs code that need to be unified. @@ -52,7 +58,7 @@ CFLAGS.$i+= -U__BMI__ ${NO_WBITWISE_INSTEAD_OF_LOGICAL} .endfor -CFLAGS.zstd_shim.c+= -DIN_BASE -DIN_LIBSA -I${OZFS}/include +CFLAGS.zfs_zstd.c+= -DIN_BASE -DIN_LIBSA # Do not unroll skein loops, reduce code size CFLAGS.skein_block.c+= -DSKEIN_LOOP=111 Index: stand/libsa/zfs/spl/sys/blake3.h =================================================================== --- /dev/null +++ stand/libsa/zfs/spl/sys/blake3.h @@ -0,0 +1,17 @@ +/* + * Copyright 2022, Netflix, Inc + * + * SPDX-License-Identifier: BSD-2-Clause + */ + +#pragma once + +/* + * Gross and ugly hack to cope with upstream's sys/blake3.h not being standalone + * safe. + */ +#define _KERNEL + +#include_next + +#undef _KERNEL Index: stand/libsa/zfs/spl/sys/zfs_context.h =================================================================== --- /dev/null +++ stand/libsa/zfs/spl/sys/zfs_context.h @@ -0,0 +1,32 @@ +/* + * Copyright 2022, Netflix, Inc + * + * SPDX-License-Identifier: BSD-2-Clause + */ + +#pragma once + +/* TODO: openzfs/include/sys/uio_impl.h must not be included in stand */ +#ifndef _SYS_UIO_IMPL_H +#define _SYS_UIO_IMPL_H +#endif + +/* + * sys/atomic.h must be included after sys/sysmacros.h. The latter includes + * machine/atomic.h, which interferes. Sadly, upstream includes them in the + * wrong order, so we include it here to fix that. + */ +#include + +#include_next + +#define ZFS_MODULE_PARAM_ARGS void + +/* + * Not sure why I need these, but including the canonical stand.h fails because + * the normal string.h doesn't like all the other shenanigans in this environment. + */ +void *memcpy(void *dst, const void *src, size_t len); +void *memset(void *dest, int c, size_t len); +void *memmem(const void *big, size_t big_len, const void *little, + size_t little_len); Index: stand/libsa/zfs/zfsimpl.c =================================================================== --- stand/libsa/zfs/zfsimpl.c +++ stand/libsa/zfs/zfsimpl.c @@ -140,6 +140,7 @@ "org.freebsd:zstd_compress", "com.delphix:bookmark_written", "com.delphix:head_errlog", + "org.openzfs:blake3", NULL }; Index: stand/libsa/zfs/zstd_shim.c =================================================================== --- stand/libsa/zfs/zstd_shim.c +++ /dev/null @@ -1,45 +0,0 @@ -/*- - * Copyright (c) 2020 M. Warner Losh - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - * - */ -#include -__FBSDID("$FreeBSD$"); - -/* - * Small amount of shim code needed to get zfs_zstd.c to compile. These items - * here should all be defined in the SPL or as part of libsa somewhere, but - * aren't for reasons that haven't been tracked down yet. Ideally, they would - * all go away and we'd compile zfs_zstd.c directly. Based on an original by - * Matt Macey, but only the #include remains untouched from that. - */ - -#define ZFS_MODULE_PARAM_ARGS void -typedef int boolean_t; /* This one may be tough to get rid of */ - -/* TODO: openzfs/include/sys/uio_impl.h must not be included */ -#ifndef _SYS_UIO_IMPL_H -#define _SYS_UIO_IMPL_H -#endif - -#include Index: sys/cddl/boot/zfs/blake3_zfs.c =================================================================== --- /dev/null +++ sys/cddl/boot/zfs/blake3_zfs.c @@ -0,0 +1,97 @@ +/* + * 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 + * or http://opensource.org/licenses/CDDL-1.0. + * 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 + */ + +/* + * Copyright 2022 Tino Reichardt + */ + +#include + +/* + * Computes a native 256-bit BLAKE3 MAC checksum. Please note that this + * function requires the presence of a ctx_template that should be allocated + * using zio_checksum_blake3_tmpl_init. + */ +static void +zio_checksum_blake3_native(const void *buf, uint64_t size, + const void *ctx_template, zio_cksum_t *zcp) +{ + BLAKE3_CTX ctx; + + ASSERT(ctx_template != 0); + + memcpy(&ctx, ctx_template, sizeof(ctx)); + Blake3_Update(&ctx, buf, size); + Blake3_Final(&ctx, (uint8_t *)zcp); + + memset(&ctx, 0, sizeof (ctx)); +} + +/* + * Byteswapped version of zio_checksum_blake3_native. This just invokes + * the native checksum function and byteswaps the resulting checksum (since + * BLAKE3 is internally endian-insensitive). + */ +static void +zio_checksum_blake3_byteswap(const void *buf, uint64_t size, + const void *ctx_template, zio_cksum_t *zcp) +{ + zio_cksum_t tmp; + + ASSERT(ctx_template != 0); + + zio_checksum_blake3_native(buf, size, ctx_template, &tmp); + zcp->zc_word[0] = BSWAP_64(tmp.zc_word[0]); + zcp->zc_word[1] = BSWAP_64(tmp.zc_word[1]); + zcp->zc_word[2] = BSWAP_64(tmp.zc_word[2]); + zcp->zc_word[3] = BSWAP_64(tmp.zc_word[3]); +} + +/* + * Allocates a BLAKE3 MAC template suitable for using in BLAKE3 MAC checksum + * computations and returns a pointer to it. + */ +static void * +zio_checksum_blake3_tmpl_init(const zio_cksum_salt_t *salt) +{ + BLAKE3_CTX *ctx; + + ASSERT(sizeof (salt->zcs_bytes) == 32); + + /* init reference object */ + ctx = calloc(1, sizeof(*ctx)); + Blake3_InitKeyed(ctx, salt->zcs_bytes); + + return (ctx); +} + +/* + * Frees a BLAKE3 context template previously allocated using + * zio_checksum_blake3_tmpl_init. + */ +static void +zio_checksum_blake3_tmpl_free(void *ctx_template) +{ + BLAKE3_CTX *ctx = ctx_template; + + memset(ctx, 0, sizeof(*ctx)); + free(ctx); +} Index: sys/cddl/boot/zfs/zfsimpl.h =================================================================== --- sys/cddl/boot/zfs/zfsimpl.h +++ sys/cddl/boot/zfs/zfsimpl.h @@ -602,6 +602,7 @@ ZIO_CHECKSUM_SHA512, ZIO_CHECKSUM_SKEIN, ZIO_CHECKSUM_EDONR, + ZIO_CHECKSUM_BLAKE3, ZIO_CHECKSUM_FUNCTIONS }; Index: sys/cddl/boot/zfs/zfssubr.c =================================================================== --- sys/cddl/boot/zfs/zfssubr.c +++ sys/cddl/boot/zfs/zfssubr.c @@ -102,6 +102,7 @@ #include "blkptr.c" #include "fletcher.c" +#include "blake3_zfs.c" #include "sha256.c" #include "skein_zfs.c" @@ -140,7 +141,11 @@ ZCHECKSUM_FLAG_SALTED | ZCHECKSUM_FLAG_NOPWRITE, "skein"}, /* no edonr for now */ {{NULL, NULL}, NULL, NULL, ZCHECKSUM_FLAG_METADATA | - ZCHECKSUM_FLAG_SALTED | ZCHECKSUM_FLAG_NOPWRITE, "edonr"} + ZCHECKSUM_FLAG_SALTED | ZCHECKSUM_FLAG_NOPWRITE, "edonr"}, + {{zio_checksum_blake3_native, zio_checksum_blake3_byteswap}, + zio_checksum_blake3_tmpl_init, zio_checksum_blake3_tmpl_free, + ZCHECKSUM_FLAG_METADATA | ZCHECKSUM_FLAG_DEDUP | + ZCHECKSUM_FLAG_SALTED | ZCHECKSUM_FLAG_NOPWRITE, "blake3"} }; /*