diff --git a/all_output.txt b/all_output.txt new file mode 100644 index 0000000000..a57810688b --- /dev/null +++ b/all_output.txt @@ -0,0 +1,2442 @@ +[uberenv python: /usr/bin/python3] +[uberenv project settings: + package_name: serac + package_version: develop + package_final_phase: initconfig + package_source_dir: ../.. + spack_url: https://github.com/spack/spack.git + spack_commit: cfee88a5bb56a1c8ec892879e04cb6a17c4f9404 + spack_configs_path: scripts/spack/configs + spack_packages_path: ['scripts/spack/radiuss-spack-configs/packages', 'scripts/spack/packages'] + spack_concretizer: clingo + force_commandline_prefix: False +] +[uberenv command line options: + install: False + prefix: ../serac_libs_dec_24 + spec: %gcc@12.3.0+profiling + vcpkg_triplet: None + mirror: None + create_mirror: False + upstream: None + reuse: False + vcpkg_ports_path: None + package_name: None + spack_build_mode: None + spack_debug: False + spack_allow_deprecated: False + package_final_phase: None + package_source_dir: None + project_json: /home/sam/code/serac/.uberenv_config.json + build_jobs: None + ignore_ssl_errors: False + repo_pull: False + spack_clean: False + run_tests: False + macos_sdk_env_setup: False + setup_only: False + skip_setup: False + spack_externals: None + spack_compiler_paths: None + spack_env_name: spack_env + spack_env_file: spack.yaml +] +[uberenv spack build mode: dev-build] +[spack spec: @develop%gcc@12.3.0+profiling] +[Spack Environment file: /home/sam/code/serac/spack.yaml] +[installing to: /home/sam/code/serac_libs_dec_24] +[info: cloning spack develop branch from github] +[exe: git clone --single-branch --depth=1 -b develop https://github.com/spack/spack.git spack] +Cloning into 'spack'... +[info: using spack commit cfee88a5bb56a1c8ec892879e04cb6a17c4f9404] +[exe: git stash] +No local changes to save +[exe: git fetch --depth=1 origin cfee88a5bb56a1c8ec892879e04cb6a17c4f9404] +From https://github.com/spack/spack + * branch cfee88a5bb56a1c8ec892879e04cb6a17c4f9404 -> FETCH_HEAD +[exe: git checkout cfee88a5bb56a1c8ec892879e04cb6a17c4f9404] +Note: switching to 'cfee88a5bb56a1c8ec892879e04cb6a17c4f9404'. + +You are in 'detached HEAD' state. You can look around, make experimental +changes and commit them, and you can discard any commits you make in this +state without impacting any branches by switching back to a branch. + +If you want to create a new branch to retain commits you create, you may +do so (now or later) by using -c with the switch command. Example: + + git switch -c + +Or undo this operation with: + + git switch - + +Turn off this advice by setting config variable advice.detachedHead to false + +HEAD is now at cfee88a5 Docs/Windows: Clarify supported shells and caveats (#46381) +[spack python: /usr/bin/python3] +[Checking for concretizer options...] +[--fresh exists.] +[--reuse exists.] +[disabling config scope (except defaults) in: /home/sam/code/serac_libs_dec_24/spack/lib/spack/spack/config.py] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack config --scope defaults add config:concretizer:clingo] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack clean --misc-cache --failures --python-cache] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +==> Removing install failure marks +==> Removing cached information on repositories +==> Removing python cache files +[creating spack env] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack env create -d /home/sam/code/serac_libs_dec_24/spack_env /home/sam/code/serac/spack.yaml] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +==> Created independent environment in: /home/sam/code/serac_libs_dec_24/spack_env +==> Activate with: spack env activate /home/sam/code/serac_libs_dec_24/spack_env +[adding spack repo /home/sam/code/serac/scripts/spack/radiuss-spack-configs/packages/../] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env repo add /home/sam/code/serac/scripts/spack/radiuss-spack-configs/packages/../] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +==> Error: Repository is already registered with Spack: /home/sam/code/serac/scripts/spack/radiuss-spack-configs/packages/../ +[adding spack repo /home/sam/code/serac/scripts/spack/packages/../] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env repo add /home/sam/code/serac/scripts/spack/packages/../] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +==> Error: Repository is already registered with Spack: /home/sam/code/serac/scripts/spack/packages/../ +[adding spack package] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env add 'serac@develop%gcc@12.3.0+profiling'] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +==> Adding serac@develop%gcc@12.3.0+profiling to environment /home/sam/code/serac_libs_dec_24/spack_env +[calling spack develop] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env develop --no-clone --path=/home/sam/code/serac 'serac@develop%gcc@12.3.0+profiling'] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +[concretizing spack env] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env concretize --fresh ] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +==> Warning: duplicate found for clang@=14.0.0 on ubuntu22.04/x86_64. Edit your compilers.yaml configuration to remove it. +==> Warning: duplicate found for gcc@=9.5.0 on ubuntu22.04/x86_64. Edit your compilers.yaml configuration to remove it. +==> Warning: duplicate found for gcc@=10.5.0 on ubuntu22.04/x86_64. Edit your compilers.yaml configuration to remove it. +==> Warning: duplicate found for gcc@=11.4.0 on ubuntu22.04/x86_64. Edit your compilers.yaml configuration to remove it. +==> Warning: duplicate found for gcc@=12.3.0 on ubuntu22.04/x86_64. Edit your compilers.yaml configuration to remove it. +==> Warning: using "cmake@3.28.3" which is a deprecated version +==> Warning: using "perl@5.34.0" which is a deprecated version +==> Concretized 2 specs: + - l77xejh serac@develop%gcc@12.3.0~asan~cuda~devtools~ipo+openmp+petsc+profiling+raja~rocm~shared+slepc+strumpack+sundials+tribol+umpire build_system=cmake build_type=Release dev_path=/home/sam/code/serac generator=make arch=linux-ubuntu22.04-skylake + - kgt73cv ^adiak@0.4.0%gcc@12.3.0~ipo+mpi~shared build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - crlt4id ^axom@0.9.0.1%gcc@12.3.0+cpp14~cuda~devtools~examples~fortran+hdf5~ipo+lua+mfem+mpi+openmp~python+raja~rocm~scr~shared~tools+umpire build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - 2oxa6mf ^blt@0.6.2%gcc@12.3.0 build_system=generic arch=linux-ubuntu22.04-skylake + - julim3s ^caliper@2.10.0%gcc@12.3.0+adiak~cuda~fortran+gotcha~ipo+kokkos+libdw~libpfm+libunwind+mpi~papi~rocm+sampler~shared~sosflow~tests~variorum build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - vtbtqmz ^elfutils@0.191%gcc@12.3.0~debuginfod+exeprefix+nls build_system=autotools arch=linux-ubuntu22.04-skylake +[e] aac2civ ^bzip2@1.0.8%gcc@12.3.0~debug~pic+shared build_system=generic arch=linux-ubuntu22.04-skylake +[e] vjtarjv ^gettext@0.21%gcc@12.3.0+bzip2+curses+git~libunistring+libxml2+pic+shared+tar+xz build_system=autotools arch=linux-ubuntu22.04-skylake + - yurditi ^libiconv@1.17%gcc@12.3.0 build_system=autotools libs=shared,static arch=linux-ubuntu22.04-skylake +[e] d5ozks2 ^m4@1.4.18%gcc@12.3.0+sigsegv build_system=autotools patches=3877ab5,fc9b616 arch=linux-ubuntu22.04-skylake +[e] oa6rfve ^xz@5.2.5%gcc@12.3.0~pic build_system=autotools libs=shared,static arch=linux-ubuntu22.04-skylake + - dwvdelj ^zstd@1.5.6%gcc@12.3.0~programs build_system=makefile libs=shared,static arch=linux-ubuntu22.04-skylake + - 6otmcgj ^libunwind@1.6.2%gcc@12.3.0~block_signals~conservative_checks~cxx_exceptions~debug~debug_frame+docs~pic+tests+weak_backtrace~xz~zlib build_system=autotools components=none libs=shared,static arch=linux-ubuntu22.04-skylake +[e] vrnm5c2 ^python@3.10.14%gcc@12.3.0+bz2+crypt+ctypes+dbm~debug+libxml2+lzma+nis~optimizations+pic+pyexpat~pythoncmd+readline+shared+sqlite3+ssl+tix+tkinter+uuid+zlib build_system=generic patches=0d98e93,ebdca64,f2fd060 arch=linux-ubuntu22.04-skylake + - v5g75d7 ^camp@2024.02.0%gcc@12.3.0~cuda~ipo+openmp~rocm~tests build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake +[e] yl7xufq ^cmake@3.28.3%gcc@12.3.0~doc+ncurses+ownlibs build_system=generic build_type=Release patches=dbc3892 arch=linux-ubuntu22.04-skylake + - 7ymuqal ^conduit@0.9.2%gcc@12.3.0~adios+blt_find_mpi~caliper~doc~doxygen+examples~fortran+hdf5+hdf5_compat~ipo+mpi+parmetis~python+shared~silo~test+utilities~zfp build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - qupzzv7 ^gcc-runtime@12.3.0%gcc@12.3.0 build_system=generic arch=linux-ubuntu22.04-skylake +[e] d4i5knf ^glibc@2.35%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] nizar4h ^gmake@4.3%gcc@12.3.0~guile build_system=generic patches=599f134 arch=linux-ubuntu22.04-skylake + - gpzjvgu ^hdf5@1.8.23%gcc@12.3.0~cxx~fortran+hl~ipo~mpi~shared~szip~threadsafe+tools api=default build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - yerv6on ^pkgconf@2.2.0%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake + - 46skka2 ^zlib-ng@2.2.1%gcc@12.3.0+compat+new_strategies+opt+pic+shared build_system=autotools arch=linux-ubuntu22.04-skylake + - kwxuezs ^hypre@2.26.0%gcc@12.3.0~caliper~complex~cublas~cuda~debug+fortran~gptune~gpu-aware-mpi~int64~internal-superlu~magma~mixedint+mpi~openmp~rocblas~rocm~shared~superlu-dist~sycl~umpire~unified-memory build_system=autotools precision=double arch=linux-ubuntu22.04-skylake + - haeuwrx ^openblas@0.3.27%gcc@12.3.0~bignuma~consistent_fpcsr+dynamic_dispatch+fortran~ilp64+locking+pic+shared build_system=makefile symbol_suffix=none threads=openmp arch=linux-ubuntu22.04-skylake + - 4gqzkxq ^lua@5.4.6%gcc@12.3.0~pcfile+shared build_system=makefile fetcher=curl arch=linux-ubuntu22.04-skylake +[e] dkdfsjq ^curl@7.81.0%gcc@12.3.0+gssapi+ldap~libidn2~librtmp~libssh~libssh2+nghttp2 build_system=autotools libs=shared,static tls=openssl arch=linux-ubuntu22.04-skylake +[e] s6wsuoj ^ncurses@6.3.20211021%gcc@12.3.0+symlinks+termlib abi=6 build_system=autotools patches=7a351bc arch=linux-ubuntu22.04-skylake + - qyfndow ^readline@8.2%gcc@12.3.0 build_system=autotools patches=bbf97f1 arch=linux-ubuntu22.04-skylake + - shglyno ^unzip@6.0%gcc@12.3.0 build_system=makefile patches=881d2ed,f6f6236 arch=linux-ubuntu22.04-skylake + - 2g2acji ^metis@5.1.0%gcc@12.3.0~gdb~int64~ipo~real64~shared build_system=cmake build_type=Release generator=make patches=4991da9,93a7903,b1225da arch=linux-ubuntu22.04-skylake + - hg6gqwa ^mfem@4.7.0.1%gcc@12.3.0~amgx~asan~conduit~cuda~debug~examples~exceptions~fms~ginkgo~gnutls~gslib~hiop+lapack~libceed~libunwind+metis~miniapps~mpfr+mpi~mumps+netcdf~occa+openmp+petsc~pumi~raja~rocm~shared+slepc+static+strumpack~suite-sparse+sundials+superlu-dist~threadsafe~umpire+zlib build_system=generic cxxstd=auto patches=937da2a precision=double timer=auto arch=linux-ubuntu22.04-skylake + - o4h3fi5 ^netcdf-c@4.7.4%gcc@12.3.0~blosc~byterange~dap~fsync~hdf4~jna~logging~mpi~nczarr_zip+optimize~parallel-netcdf+pic~shared~szip~zstd build_system=autotools arch=linux-ubuntu22.04-skylake + - gyvgslw ^openmpi@5.0.5%gcc@12.3.0~atomics~cuda~debug~gpfs~internal-hwloc~internal-libevent~internal-pmix~java~lustre~memchecker~openshmem~romio+rsh~static+vt+wrapper-rpath build_system=autotools fabrics=none romio-filesystem=none schedulers=none arch=linux-ubuntu22.04-skylake +[e] s4xelvy ^autoconf@2.71%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] 3shmde2 ^automake@1.16.5%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] qjwrtgr ^hwloc@2.10.0%gcc@12.3.0~cairo~cuda~gl~libudev+libxml2~nvml~oneapi-level-zero~opencl+pci~rocm build_system=autotools libs=shared,static arch=linux-ubuntu22.04-skylake + - 73jyhsb ^libevent@2.1.12%gcc@12.3.0+openssl build_system=autotools arch=linux-ubuntu22.04-skylake +[e] v2nk7ea ^openssl@3.0.2%gcc@12.3.0~docs+shared build_system=generic certs=mozilla arch=linux-ubuntu22.04-skylake +[e] teurcse ^libtool@2.4.6%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake + - maffne2 ^numactl@2.0.18%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] 7mc7oea ^openssh@8.9p1%gcc@12.3.0+gssapi build_system=autotools arch=linux-ubuntu22.04-skylake +[e] h2ikxcy ^perl@5.34.0%gcc@12.3.0~cpanm+opcode+open+shared+threads build_system=generic arch=linux-ubuntu22.04-skylake + - 3dzzw34 ^pmix@5.0.3%gcc@12.3.0~munge~python~restful build_system=autotools arch=linux-ubuntu22.04-skylake + - njvbvvp ^parmetis@4.0.3%gcc@12.3.0~gdb~int64~ipo~shared build_system=cmake build_type=Release generator=make patches=4f89253,50ed208,704b84f arch=linux-ubuntu22.04-skylake + - hb3kxxh ^petsc@3.21.5%gcc@12.3.0~X~batch~cgns~complex~cuda~debug+double~exodusii~fftw+fortran~giflib~hdf5~hpddm~hwloc+hypre~int64~jpeg~knl~kokkos~libpng~libyaml~memkind+metis~mkl-pardiso~mmg~moab~mpfr+mpi~mumps+openmp~p4est~parmmg~ptscotch~random123~rocm~saws~scalapack~shared+strumpack~suite-sparse+superlu-dist~sycl~tetgen~trilinos~valgrind~zoltan build_system=generic clanguage=C memalign=none arch=linux-ubuntu22.04-skylake +[e] 5amzlzl ^diffutils@3.8%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake + - feus7pk ^netlib-scalapack@2.2.0%gcc@12.3.0~ipo~pic+shared build_system=cmake build_type=Release generator=make patches=072b006,1c9ce5f,244a9aa arch=linux-ubuntu22.04-skylake + - 5pwfb3y ^raja@2024.02.0%gcc@12.3.0~cuda~desul~examples~exercises~ipo~omptask+openmp~rocm~run-all-tests~shared~tests+vectorization build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - hzaovye ^slepc@3.21.0%gcc@12.3.0+arpack~blopex~cuda~hpddm~rocm build_system=generic arch=linux-ubuntu22.04-skylake + - fq3up2e ^arpack-ng@3.9.0%gcc@12.3.0~icb~ipo+mpi+shared build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - 6rmybu6 ^strumpack@7.2.0%gcc@12.3.0~butterflypack+c_interface~count_flops~cuda~ipo~magma+mpi+openmp+parmetis~rocm~scotch~shared~slate~task_timers~zfp build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - t4m7tfi ^sundials@6.7.0%gcc@12.3.0+ARKODE+CVODE+CVODES+IDA+IDAS+KINSOL~asan~cuda~examples~examples-install~f2003~fcmix+generic-math~ginkgo+hypre~int64~ipo~klu~kokkos~kokkos-kernels~lapack~magma~monitoring+mpi~openmp~petsc~profiling~pthread~raja~rocm~shared+static~superlu-dist~superlu-mt~sycl~trilinos build_system=cmake build_type=Release cstd=99 cxxstd=14 generator=make logging-level=2 logging-mpi=OFF precision=double arch=linux-ubuntu22.04-skylake + - 2glyola ^superlu-dist@8.1.2%gcc@12.3.0~cuda~int64~ipo~openmp+parmetis~rocm~shared build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - 5rbkklt ^tribol@0.1.0.16%gcc@12.3.0~cuda~devtools~examples~fortran~ipo~raja+redecomp~rocm~tests~umpire build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - zapeqzp ^umpire@2024.02.0%gcc@12.3.0~asan~backtrace+c~cuda~dev_benchmarks~device_alloc~deviceconst~examples~fortran~ipc_shmem~ipo~mpi~numa+openmp~openmp_target~rocm~sanitizer_tests~shared~sqlite_experimental~tools+werror build_system=cmake build_type=Release generator=make tests=none arch=linux-ubuntu22.04-skylake + - i4xqurx ^fmt@10.2.1%gcc@12.3.0~ipo+pic~shared build_system=cmake build_type=Release cxxstd=11 generator=make arch=linux-ubuntu22.04-skylake + +[spack version: 0.23.0.dev0 (cfee88a5bb56a1c8ec892879e04cb6a17c4f9404) +] +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env spec --fresh --install-status --very-long] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. + - l77xejhejbbfmh5b4vqtxxw3paidppuo serac@develop%gcc@12.3.0~asan~cuda~devtools~ipo+openmp+petsc+profiling+raja~rocm~shared+slepc+strumpack+sundials+tribol+umpire build_system=cmake build_type=Release dev_path=/home/sam/code/serac generator=make arch=linux-ubuntu22.04-skylake + - kgt73cvn75plcq5fuk2cvxulzm4izttf ^adiak@0.4.0%gcc@12.3.0~ipo+mpi~shared build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - crlt4idlryebgcrsch46aoakm55a7jnf ^axom@0.9.0.1%gcc@12.3.0+cpp14~cuda~devtools~examples~fortran+hdf5~ipo+lua+mfem+mpi+openmp~python+raja~rocm~scr~shared~tools+umpire build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - 2oxa6mfgyufajnx7lccymostfdcgq3lp ^blt@0.6.2%gcc@12.3.0 build_system=generic arch=linux-ubuntu22.04-skylake + - julim3sed75ysjjl4xi2wqn2oui3gogn ^caliper@2.10.0%gcc@12.3.0+adiak~cuda~fortran+gotcha~ipo+kokkos+libdw~libpfm+libunwind+mpi~papi~rocm+sampler~shared~sosflow~tests~variorum build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - vtbtqmzvsgyoup5klhaeea2olssag5xo ^elfutils@0.191%gcc@12.3.0~debuginfod+exeprefix+nls build_system=autotools arch=linux-ubuntu22.04-skylake +[e] aac2civ6ci2uby6upmaa3m7sgmtvdbpg ^bzip2@1.0.8%gcc@12.3.0~debug~pic+shared build_system=generic arch=linux-ubuntu22.04-skylake +[e] vjtarjvd6hsfitnohpniv6hlw4or46rv ^gettext@0.21%gcc@12.3.0+bzip2+curses+git~libunistring+libxml2+pic+shared+tar+xz build_system=autotools arch=linux-ubuntu22.04-skylake + - yurditifflzptvup5hj7ytoaswco6aav ^libiconv@1.17%gcc@12.3.0 build_system=autotools libs=shared,static arch=linux-ubuntu22.04-skylake +[e] d5ozks2k43ljdiex2skxldizlcndlg6j ^m4@1.4.18%gcc@12.3.0+sigsegv build_system=autotools patches=3877ab5,fc9b616 arch=linux-ubuntu22.04-skylake +[e] oa6rfveivxlvxemjhxf3yoqfdvgz4ugi ^xz@5.2.5%gcc@12.3.0~pic build_system=autotools libs=shared,static arch=linux-ubuntu22.04-skylake + - dwvdelj5psbmp2y3rv4n7q7myybsagtv ^zstd@1.5.6%gcc@12.3.0~programs build_system=makefile libs=shared,static arch=linux-ubuntu22.04-skylake + - 6otmcgjqj3ksscic4ffhigbltvhdbwx3 ^libunwind@1.6.2%gcc@12.3.0~block_signals~conservative_checks~cxx_exceptions~debug~debug_frame+docs~pic+tests+weak_backtrace~xz~zlib build_system=autotools components=none libs=shared,static arch=linux-ubuntu22.04-skylake +[e] vrnm5c2htjzjygd2llzllhsf6qeocpl3 ^python@3.10.14%gcc@12.3.0+bz2+crypt+ctypes+dbm~debug+libxml2+lzma+nis~optimizations+pic+pyexpat~pythoncmd+readline+shared+sqlite3+ssl+tix+tkinter+uuid+zlib build_system=generic patches=0d98e93,ebdca64,f2fd060 arch=linux-ubuntu22.04-skylake + - v5g75d763xm5z5ohoqyp77effjwc6saz ^camp@2024.02.0%gcc@12.3.0~cuda~ipo+openmp~rocm~tests build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake +[e] yl7xufqmnkpmkpesokspgtdl2ra22qem ^cmake@3.28.3%gcc@12.3.0~doc+ncurses+ownlibs build_system=generic build_type=Release patches=dbc3892 arch=linux-ubuntu22.04-skylake + - 7ymuqal4duighrautwywbotvwk4kbcub ^conduit@0.9.2%gcc@12.3.0~adios+blt_find_mpi~caliper~doc~doxygen+examples~fortran+hdf5+hdf5_compat~ipo+mpi+parmetis~python+shared~silo~test+utilities~zfp build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - qupzzv7mylo3ksncvjw7preg334dwn6g ^gcc-runtime@12.3.0%gcc@12.3.0 build_system=generic arch=linux-ubuntu22.04-skylake +[e] d4i5knfmnmcjw3kbim4levymdzvsw6k6 ^glibc@2.35%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] nizar4hq6pq6uhwx2na42tzq3rsilzgc ^gmake@4.3%gcc@12.3.0~guile build_system=generic patches=599f134 arch=linux-ubuntu22.04-skylake + - gpzjvgu5li5br7sy2f2otmenx3cr54oy ^hdf5@1.8.23%gcc@12.3.0~cxx~fortran+hl~ipo~mpi~shared~szip~threadsafe+tools api=default build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - yerv6onx7zaznqoipailrhm5wjj2goa2 ^pkgconf@2.2.0%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake + - 46skka27gwzx4san5zkrunivcm7nz564 ^zlib-ng@2.2.1%gcc@12.3.0+compat+new_strategies+opt+pic+shared build_system=autotools arch=linux-ubuntu22.04-skylake + - kwxuezssmhwryylzr744fx3c5dnf6mn2 ^hypre@2.26.0%gcc@12.3.0~caliper~complex~cublas~cuda~debug+fortran~gptune~gpu-aware-mpi~int64~internal-superlu~magma~mixedint+mpi~openmp~rocblas~rocm~shared~superlu-dist~sycl~umpire~unified-memory build_system=autotools precision=double arch=linux-ubuntu22.04-skylake + - haeuwrx5wsiflbxtqpust2bgmpf2gnpl ^openblas@0.3.27%gcc@12.3.0~bignuma~consistent_fpcsr+dynamic_dispatch+fortran~ilp64+locking+pic+shared build_system=makefile symbol_suffix=none threads=openmp arch=linux-ubuntu22.04-skylake + - 4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz ^lua@5.4.6%gcc@12.3.0~pcfile+shared build_system=makefile fetcher=curl arch=linux-ubuntu22.04-skylake +[e] dkdfsjqgkymgsvoxzvmisjmqccerwrzh ^curl@7.81.0%gcc@12.3.0+gssapi+ldap~libidn2~librtmp~libssh~libssh2+nghttp2 build_system=autotools libs=shared,static tls=openssl arch=linux-ubuntu22.04-skylake +[e] s6wsuojbpehnjguu5b2bruh2po4ckvhq ^ncurses@6.3.20211021%gcc@12.3.0+symlinks+termlib abi=6 build_system=autotools patches=7a351bc arch=linux-ubuntu22.04-skylake + - qyfndow76bgnuknlhqya72ipad7f3vh5 ^readline@8.2%gcc@12.3.0 build_system=autotools patches=bbf97f1 arch=linux-ubuntu22.04-skylake + - shglynoblvdrnsjdpcrqn6os3p4wrofa ^unzip@6.0%gcc@12.3.0 build_system=makefile patches=881d2ed,f6f6236 arch=linux-ubuntu22.04-skylake + - 2g2acji3wh53ez3bmun3glc7h3gqxtg3 ^metis@5.1.0%gcc@12.3.0~gdb~int64~ipo~real64~shared build_system=cmake build_type=Release generator=make patches=4991da9,93a7903,b1225da arch=linux-ubuntu22.04-skylake + - hg6gqwaz5i5qibpbj7f6qzq4gbf4az6i ^mfem@4.7.0.1%gcc@12.3.0~amgx~asan~conduit~cuda~debug~examples~exceptions~fms~ginkgo~gnutls~gslib~hiop+lapack~libceed~libunwind+metis~miniapps~mpfr+mpi~mumps+netcdf~occa+openmp+petsc~pumi~raja~rocm~shared+slepc+static+strumpack~suite-sparse+sundials+superlu-dist~threadsafe~umpire+zlib build_system=generic cxxstd=auto patches=937da2a precision=double timer=auto arch=linux-ubuntu22.04-skylake + - o4h3fi5jvtfrikv5zvt47mw7tiut4vk6 ^netcdf-c@4.7.4%gcc@12.3.0~blosc~byterange~dap~fsync~hdf4~jna~logging~mpi~nczarr_zip+optimize~parallel-netcdf+pic~shared~szip~zstd build_system=autotools arch=linux-ubuntu22.04-skylake + - gyvgslwg3a74emc456byyqhdcvrf3c7e ^openmpi@5.0.5%gcc@12.3.0~atomics~cuda~debug~gpfs~internal-hwloc~internal-libevent~internal-pmix~java~lustre~memchecker~openshmem~romio+rsh~static+vt+wrapper-rpath build_system=autotools fabrics=none romio-filesystem=none schedulers=none arch=linux-ubuntu22.04-skylake +[e] s4xelvym5xghrbblsn5d64j4q5cbzdvn ^autoconf@2.71%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] 3shmde2nyksetqfqvugxj3gnopbuysd2 ^automake@1.16.5%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] qjwrtgr5fanycnfnhvad7y3ovpsrc227 ^hwloc@2.10.0%gcc@12.3.0~cairo~cuda~gl~libudev+libxml2~nvml~oneapi-level-zero~opencl+pci~rocm build_system=autotools libs=shared,static arch=linux-ubuntu22.04-skylake + - 73jyhsbj4rgjg4mf4ydazdyn6d73dgoe ^libevent@2.1.12%gcc@12.3.0+openssl build_system=autotools arch=linux-ubuntu22.04-skylake +[e] v2nk7eanai3jquaxrh323plahs74dhmh ^openssl@3.0.2%gcc@12.3.0~docs+shared build_system=generic certs=mozilla arch=linux-ubuntu22.04-skylake +[e] teurcseg4faxdpkasgwv7wgmv5xkq5rx ^libtool@2.4.6%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake + - maffne2uu3zxmwkvsojcdm53nrnpamdg ^numactl@2.0.18%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake +[e] 7mc7oeaeksdrivorvckleagevraiq3y7 ^openssh@8.9p1%gcc@12.3.0+gssapi build_system=autotools arch=linux-ubuntu22.04-skylake +[e] h2ikxcyjhik64arwme2ca2ky2ftauoei ^perl@5.34.0%gcc@12.3.0~cpanm+opcode+open+shared+threads build_system=generic arch=linux-ubuntu22.04-skylake + - 3dzzw34om3f3egm2mvq2euhc57zsu6py ^pmix@5.0.3%gcc@12.3.0~munge~python~restful build_system=autotools arch=linux-ubuntu22.04-skylake + - njvbvvpjyx2hjvel7asmtlpugntv66lt ^parmetis@4.0.3%gcc@12.3.0~gdb~int64~ipo~shared build_system=cmake build_type=Release generator=make patches=4f89253,50ed208,704b84f arch=linux-ubuntu22.04-skylake + - hb3kxxheevzh3emk6qc6s346zmxnevj5 ^petsc@3.21.5%gcc@12.3.0~X~batch~cgns~complex~cuda~debug+double~exodusii~fftw+fortran~giflib~hdf5~hpddm~hwloc+hypre~int64~jpeg~knl~kokkos~libpng~libyaml~memkind+metis~mkl-pardiso~mmg~moab~mpfr+mpi~mumps+openmp~p4est~parmmg~ptscotch~random123~rocm~saws~scalapack~shared+strumpack~suite-sparse+superlu-dist~sycl~tetgen~trilinos~valgrind~zoltan build_system=generic clanguage=C memalign=none arch=linux-ubuntu22.04-skylake +[e] 5amzlzl3eeav4k4jmnesz7keno6xhfwf ^diffutils@3.8%gcc@12.3.0 build_system=autotools arch=linux-ubuntu22.04-skylake + - feus7pkj7yhgvqrrf635dcj6id4gpe46 ^netlib-scalapack@2.2.0%gcc@12.3.0~ipo~pic+shared build_system=cmake build_type=Release generator=make patches=072b006,1c9ce5f,244a9aa arch=linux-ubuntu22.04-skylake + - 5pwfb3yr4p575lhqtzhhvywvsghkdbfc ^raja@2024.02.0%gcc@12.3.0~cuda~desul~examples~exercises~ipo~omptask+openmp~rocm~run-all-tests~shared~tests+vectorization build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - hzaovye7lucyxctskz3arfluk6q75v7g ^slepc@3.21.0%gcc@12.3.0+arpack~blopex~cuda~hpddm~rocm build_system=generic arch=linux-ubuntu22.04-skylake + - fq3up2e27wezbrye23mrhb7hc6ktbxha ^arpack-ng@3.9.0%gcc@12.3.0~icb~ipo+mpi+shared build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - 6rmybu6moclr62zaoqs26m2sj4gvl4ru ^strumpack@7.2.0%gcc@12.3.0~butterflypack+c_interface~count_flops~cuda~ipo~magma+mpi+openmp+parmetis~rocm~scotch~shared~slate~task_timers~zfp build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - t4m7tfitf4lv7ebf5uax4mg7jqovgv4c ^sundials@6.7.0%gcc@12.3.0+ARKODE+CVODE+CVODES+IDA+IDAS+KINSOL~asan~cuda~examples~examples-install~f2003~fcmix+generic-math~ginkgo+hypre~int64~ipo~klu~kokkos~kokkos-kernels~lapack~magma~monitoring+mpi~openmp~petsc~profiling~pthread~raja~rocm~shared+static~superlu-dist~superlu-mt~sycl~trilinos build_system=cmake build_type=Release cstd=99 cxxstd=14 generator=make logging-level=2 logging-mpi=OFF precision=double arch=linux-ubuntu22.04-skylake + - 2glyola75o2amhmctein5g2oipuynvk4 ^superlu-dist@8.1.2%gcc@12.3.0~cuda~int64~ipo~openmp+parmetis~rocm~shared build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - 5rbkkltig563suvbqo4qstu7djugw5dd ^tribol@0.1.0.16%gcc@12.3.0~cuda~devtools~examples~fortran~ipo~raja+redecomp~rocm~tests~umpire build_system=cmake build_type=Release generator=make arch=linux-ubuntu22.04-skylake + - zapeqzpd4ambdf6nzl5r7micjyabnmta ^umpire@2024.02.0%gcc@12.3.0~asan~backtrace+c~cuda~dev_benchmarks~device_alloc~deviceconst~examples~fortran~ipc_shmem~ipo~mpi~numa+openmp~openmp_target~rocm~sanitizer_tests~shared~sqlite_experimental~tools+werror build_system=cmake build_type=Release generator=make tests=none arch=linux-ubuntu22.04-skylake + - i4xqurx3ohsd4qgoohzq4xvarh3bs43a ^fmt@10.2.1%gcc@12.3.0~ipo+pic~shared build_system=cmake build_type=Release cxxstd=11 generator=make arch=linux-ubuntu22.04-skylake + + +[exe: /home/sam/code/serac_libs_dec_24/spack/bin/spack -D /home/sam/code/serac_libs_dec_24/spack_env install --fresh --keep-stage -u initconfig ] +==> Warning: Spack supports only clingo as a concretizer from v0.23. The config:concretizer config option is ignored. +[+] /home/sam/.local (external cmake-3.28.3-yl7xufqmnkpmkpesokspgtdl2ra22qem) +[+] /usr (external glibc-2.35-d4i5knfmnmcjw3kbim4levymdzvsw6k6) +[+] /usr (external gmake-4.3-nizar4hq6pq6uhwx2na42tzq3rsilzgc) +[+] /usr (external autoconf-2.71-s4xelvym5xghrbblsn5d64j4q5cbzdvn) +[+] /usr (external automake-1.16.5-3shmde2nyksetqfqvugxj3gnopbuysd2) +[+] /usr (external hwloc-2.10.0-qjwrtgr5fanycnfnhvad7y3ovpsrc227) +[+] /usr (external openssl-3.0.2-v2nk7eanai3jquaxrh323plahs74dhmh) +[+] /usr (external libtool-2.4.6-teurcseg4faxdpkasgwv7wgmv5xkq5rx) +[+] /usr (external m4-1.4.18-d5ozks2k43ljdiex2skxldizlcndlg6j) +[+] /usr (external openssh-8.9p1-7mc7oeaeksdrivorvckleagevraiq3y7) +[+] /usr (external perl-5.34.0-h2ikxcyjhik64arwme2ca2ky2ftauoei) +[+] /usr (external curl-7.81.0-dkdfsjqgkymgsvoxzvmisjmqccerwrzh) +[+] /usr (external ncurses-6.3.20211021-s6wsuojbpehnjguu5b2bruh2po4ckvhq) +[+] /usr (external diffutils-3.8-5amzlzl3eeav4k4jmnesz7keno6xhfwf) +[+] /usr (external python-3.10.14-vrnm5c2htjzjygd2llzllhsf6qeocpl3) +[+] /usr (external bzip2-1.0.8-aac2civ6ci2uby6upmaa3m7sgmtvdbpg) +[+] /usr (external gettext-0.21-vjtarjvd6hsfitnohpniv6hlw4or46rv) +[+] /usr (external xz-5.2.5-oa6rfveivxlvxemjhxf3yoqfdvgz4ugi) +==> Installing gcc-runtime-12.3.0-qupzzv7mylo3ksncvjw7preg334dwn6g [19/57] +==> No binary for gcc-runtime-12.3.0-qupzzv7mylo3ksncvjw7preg334dwn6g found: installing from source +==> No patches needed for gcc-runtime +==> gcc-runtime: Executing phase: 'install' +==> gcc-runtime: Successfully installed gcc-runtime-12.3.0-qupzzv7mylo3ksncvjw7preg334dwn6g + Stage: 0.00s. Install: 0.09s. Post-install: 0.02s. Total: 0.12s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/gcc-runtime-12.3.0-qupzzv7mylo3ksncvjw7preg334dwn6g +==> Installing zstd-1.5.6-dwvdelj5psbmp2y3rv4n7q7myybsagtv [20/57] +==> No binary for zstd-1.5.6-dwvdelj5psbmp2y3rv4n7q7myybsagtv found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/30/30f35f71c1203369dc979ecde0400ffea93c27391bfd2ac5a9715d2173d92ff7.tar.gz +==> No patches needed for zstd +==> zstd: Executing phase: 'edit' +==> zstd: Executing phase: 'build' +==> zstd: Executing phase: 'install' +==> zstd: Successfully installed zstd-1.5.6-dwvdelj5psbmp2y3rv4n7q7myybsagtv + Stage: 0.18s. Edit: 0.00s. Build: 0.00s. Install: 5.48s. Post-install: 0.01s. Total: 5.70s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/zstd-1.5.6-dwvdelj5psbmp2y3rv4n7q7myybsagtv +==> Installing libiconv-1.17-yurditifflzptvup5hj7ytoaswco6aav [21/57] +==> No binary for libiconv-1.17-yurditifflzptvup5hj7ytoaswco6aav found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/8f/8f74213b56238c85a50a5329f77e06198771e70dd9a739779f4c02f65d971313.tar.gz +==> No patches needed for libiconv +==> libiconv: Executing phase: 'autoreconf' +==> libiconv: Executing phase: 'configure' +==> libiconv: Executing phase: 'build' +==> libiconv: Executing phase: 'install' +==> libiconv: Successfully installed libiconv-1.17-yurditifflzptvup5hj7ytoaswco6aav + Stage: 0.24s. Autoreconf: 0.00s. Configure: 17.99s. Build: 5.75s. Install: 1.54s. Post-install: 0.02s. Total: 25.61s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/libiconv-1.17-yurditifflzptvup5hj7ytoaswco6aav +==> Installing libunwind-1.6.2-6otmcgjqj3ksscic4ffhigbltvhdbwx3 [22/57] +==> No binary for libunwind-1.6.2-6otmcgjqj3ksscic4ffhigbltvhdbwx3 found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/4a/4a6aec666991fb45d0889c44aede8ad6eb108071c3554fcdff671f9c94794976.tar.gz +==> No patches needed for libunwind +==> libunwind: Executing phase: 'autoreconf' +==> libunwind: Executing phase: 'configure' +==> libunwind: Executing phase: 'build' +==> libunwind: Executing phase: 'install' +==> libunwind: Successfully installed libunwind-1.6.2-6otmcgjqj3ksscic4ffhigbltvhdbwx3 + Stage: 0.39s. Autoreconf: 0.00s. Configure: 15.95s. Build: 2.44s. Install: 0.81s. Post-install: 0.01s. Total: 19.68s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/libunwind-1.6.2-6otmcgjqj3ksscic4ffhigbltvhdbwx3 +==> Installing libevent-2.1.12-73jyhsbj4rgjg4mf4ydazdyn6d73dgoe [23/57] +==> No binary for libevent-2.1.12-73jyhsbj4rgjg4mf4ydazdyn6d73dgoe found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/92/92e6de1be9ec176428fd2367677e61ceffc2ee1cb119035037a27d346b0403bb.tar.gz +==> Ran patch() for libevent +==> libevent: Executing phase: 'autoreconf' +==> libevent: Executing phase: 'configure' +==> libevent: Executing phase: 'build' +==> libevent: Executing phase: 'install' +==> libevent: Successfully installed libevent-2.1.12-73jyhsbj4rgjg4mf4ydazdyn6d73dgoe + Stage: 0.13s. Autoreconf: 0.00s. Configure: 15.42s. Build: 2.14s. Install: 0.66s. Post-install: 0.02s. Total: 18.42s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/libevent-2.1.12-73jyhsbj4rgjg4mf4ydazdyn6d73dgoe +==> Installing readline-8.2-qyfndow76bgnuknlhqya72ipad7f3vh5 [24/57] +==> No binary for readline-8.2-qyfndow76bgnuknlhqya72ipad7f3vh5 found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/3f/3feb7171f16a84ee82ca18a36d7b9be109a52c04f492a053331d7d1095007c35.tar.gz +==> Fetching https://mirror.spack.io/_source-cache/archive/bb/bbf97f1ec40a929edab5aa81998c1e2ef435436c597754916e6a5868f273aff7 +==> Applied patch https://ftpmirror.gnu.org/readline/readline-8.2-patches/readline82-001 +==> readline: Executing phase: 'autoreconf' +==> readline: Executing phase: 'configure' +==> readline: Executing phase: 'build' +==> readline: Executing phase: 'install' +==> readline: Successfully installed readline-8.2-qyfndow76bgnuknlhqya72ipad7f3vh5 + Stage: 0.23s. Autoreconf: 0.00s. Configure: 7.10s. Build: 1.66s. Install: 0.22s. Post-install: 0.01s. Total: 9.26s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/readline-8.2-qyfndow76bgnuknlhqya72ipad7f3vh5 +==> Installing zlib-ng-2.2.1-46skka27gwzx4san5zkrunivcm7nz564 [25/57] +==> No binary for zlib-ng-2.2.1-46skka27gwzx4san5zkrunivcm7nz564 found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/ec/ec6a76169d4214e2e8b737e0850ba4acb806c69eeace6240ed4481b9f5c57cdf.tar.gz +==> No patches needed for zlib-ng +==> zlib-ng: Executing phase: 'autoreconf' +==> zlib-ng: Executing phase: 'configure' +==> zlib-ng: Executing phase: 'build' +==> zlib-ng: Executing phase: 'install' +==> zlib-ng: Successfully installed zlib-ng-2.2.1-46skka27gwzx4san5zkrunivcm7nz564 + Stage: 0.15s. Autoreconf: 0.00s. Configure: 4.63s. Build: 0.86s. Install: 0.09s. Post-install: 0.00s. Total: 5.77s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/zlib-ng-2.2.1-46skka27gwzx4san5zkrunivcm7nz564 +==> Installing unzip-6.0-shglynoblvdrnsjdpcrqn6os3p4wrofa [26/57] +==> No binary for unzip-6.0-shglynoblvdrnsjdpcrqn6os3p4wrofa found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/03/036d96991646d0449ed0aa952e4fbe21b476ce994abc276e49d30e686708bd37.tar.gz +==> Applied patch /home/sam/code/serac_libs_dec_24/spack/var/spack/repos/builtin/packages/unzip/configure-cflags.patch +==> Applied patch /home/sam/code/serac_libs_dec_24/spack/var/spack/repos/builtin/packages/unzip/strip.patch +==> unzip: Executing phase: 'edit' +==> unzip: Executing phase: 'build' +==> unzip: Executing phase: 'install' +==> unzip: Successfully installed unzip-6.0-shglynoblvdrnsjdpcrqn6os3p4wrofa + Stage: 0.17s. Edit: 0.00s. Build: 1.59s. Install: 0.03s. Post-install: 0.01s. Total: 1.83s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/unzip-6.0-shglynoblvdrnsjdpcrqn6os3p4wrofa +==> Installing blt-0.6.2-2oxa6mfgyufajnx7lccymostfdcgq3lp [27/57] +==> No binary for blt-0.6.2-2oxa6mfgyufajnx7lccymostfdcgq3lp found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/84/84b663162957c1fe0e896ac8e94cbf2b6def4a152ccfa12a293db14fb25191c8.tar.gz +==> No patches needed for blt +==> blt: Executing phase: 'install' +==> blt: Successfully installed blt-0.6.2-2oxa6mfgyufajnx7lccymostfdcgq3lp + Stage: 0.16s. Install: 0.03s. Post-install: 0.06s. Total: 0.27s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/blt-0.6.2-2oxa6mfgyufajnx7lccymostfdcgq3lp +==> Installing pkgconf-2.2.0-yerv6onx7zaznqoipailrhm5wjj2goa2 [28/57] +==> No binary for pkgconf-2.2.0-yerv6onx7zaznqoipailrhm5wjj2goa2 found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/b0/b06ff63a83536aa8c2f6422fa80ad45e4833f590266feb14eaddfe1d4c853c69.tar.xz +==> No patches needed for pkgconf +==> pkgconf: Executing phase: 'autoreconf' +==> pkgconf: Executing phase: 'configure' +==> pkgconf: Executing phase: 'build' +==> pkgconf: Executing phase: 'install' +==> pkgconf: Successfully installed pkgconf-2.2.0-yerv6onx7zaznqoipailrhm5wjj2goa2 + Stage: 0.14s. Autoreconf: 0.00s. Configure: 4.86s. Build: 0.92s. Install: 0.40s. Post-install: 0.01s. Total: 6.37s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/pkgconf-2.2.0-yerv6onx7zaznqoipailrhm5wjj2goa2 +==> Installing openblas-0.3.27-haeuwrx5wsiflbxtqpust2bgmpf2gnpl [29/57] +==> No binary for openblas-0.3.27-haeuwrx5wsiflbxtqpust2bgmpf2gnpl found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/aa/aa2d68b1564fe2b13bc292672608e9cdeeeb6dc34995512e65c3b10f4599e897.tar.gz +==> No patches needed for openblas +==> openblas: Executing phase: 'edit' +==> openblas: Executing phase: 'build' +==> openblas: Executing phase: 'install' +==> openblas: Successfully installed openblas-0.3.27-haeuwrx5wsiflbxtqpust2bgmpf2gnpl + Stage: 0.83s. Edit: 0.00s. Build: 2m 37.46s. Install: 3.23s. Post-install: 0.04s. Total: 2m 41.83s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/openblas-0.3.27-haeuwrx5wsiflbxtqpust2bgmpf2gnpl +==> Installing numactl-2.0.18-maffne2uu3zxmwkvsojcdm53nrnpamdg [30/57] +==> No binary for numactl-2.0.18-maffne2uu3zxmwkvsojcdm53nrnpamdg found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/8c/8cd6c13f3096e9c2293c1d732f56e2aa37a7ada1a98deed3fac7bd6da1aaaaf6.tar.gz +==> No patches needed for numactl +==> numactl: Executing phase: 'autoreconf' +==> numactl: Executing phase: 'configure' +==> numactl: Executing phase: 'build' +==> numactl: Executing phase: 'install' +==> numactl: Successfully installed numactl-2.0.18-maffne2uu3zxmwkvsojcdm53nrnpamdg + Stage: 0.12s. Autoreconf: 3.47s. Configure: 4.66s. Build: 1.02s. Install: 0.39s. Post-install: 0.01s. Total: 9.71s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/numactl-2.0.18-maffne2uu3zxmwkvsojcdm53nrnpamdg +==> Installing fmt-10.2.1-i4xqurx3ohsd4qgoohzq4xvarh3bs43a [31/57] +==> No binary for fmt-10.2.1-i4xqurx3ohsd4qgoohzq4xvarh3bs43a found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/31/312151a2d13c8327f5c9c586ac6cf7cddc1658e8f53edae0ec56509c8fa516c9.zip +==> No patches needed for fmt +==> fmt: Executing phase: 'cmake' +==> fmt: Executing phase: 'build' +==> fmt: Executing phase: 'install' +==> fmt: Successfully installed fmt-10.2.1-i4xqurx3ohsd4qgoohzq4xvarh3bs43a + Stage: 0.38s. Cmake: 0.27s. Build: 2.11s. Install: 0.05s. Post-install: 0.01s. Total: 2.85s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/fmt-10.2.1-i4xqurx3ohsd4qgoohzq4xvarh3bs43a +==> Installing metis-5.1.0-2g2acji3wh53ez3bmun3glc7h3gqxtg3 [32/57] +==> No binary for metis-5.1.0-2g2acji3wh53ez3bmun3glc7h3gqxtg3 found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/76/76faebe03f6c963127dbb73c13eab58c9a3faeae48779f049066a21c087c5db2.tar.gz +==> Applied patch /home/sam/code/serac_libs_dec_24/spack/var/spack/repos/builtin/packages/metis/gklib_path.patch +==> Applied patch /home/sam/code/serac_libs_dec_24/spack/var/spack/repos/builtin/packages/metis/install_gklib_defs_rename.patch +==> Applied patch /home/sam/code/serac_libs_dec_24/spack/var/spack/repos/builtin/packages/metis/gklib_nomisleadingindentation_warning.patch +==> Ran patch() for metis +==> metis: Executing phase: 'cmake' +==> metis: Executing phase: 'build' +==> metis: Executing phase: 'install' +==> metis: Successfully installed metis-5.1.0-2g2acji3wh53ez3bmun3glc7h3gqxtg3 + Stage: 0.21s. Cmake: 0.92s. Build: 1.03s. Install: 0.12s. Post-install: 0.02s. Total: 2.34s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/metis-5.1.0-2g2acji3wh53ez3bmun3glc7h3gqxtg3 +==> Installing lua-5.4.6-4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz [33/57] +==> No binary for lua-5.4.6-4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/7d/7d5ea1b9cb6aa0b59ca3dde1c6adcb57ef83a1ba8e5432c0ecd06bf439b3ad88.tar.gz +==> Fetching https://mirror.spack.io/_source-cache/archive/56/56ab9b90f5acbc42eb7a94cf482e6c058a63e8a1effdf572b8b2a6323a06d923.tar.gz +==> Moving resource stage + source: /tmp/sam/spack-stage/resource-luarocks-4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz/spack-src/ + destination: /tmp/sam/spack-stage/spack-stage-lua-5.4.6-4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz/spack-src/luarocks/luarocks +==> No patches needed for lua +==> lua: Executing phase: 'edit' +==> lua: Executing phase: 'build' +==> lua: Executing phase: 'install' +==> lua: Successfully installed lua-5.4.6-4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz + Stage: 0.23s. Edit: 0.00s. Build: 3.02s. Install: 0.37s. Post-install: 0.02s. Total: 3.67s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/lua-5.4.6-4gqzkxqcx7g2nmoru6ks4awyyvkdsfwz +==> Installing camp-2024.02.0-v5g75d763xm5z5ohoqyp77effjwc6saz [34/57] +==> No binary for camp-2024.02.0-v5g75d763xm5z5ohoqyp77effjwc6saz found: installing from source +==> No patches needed for camp +==> camp: Executing phase: 'cmake' +==> camp: Executing phase: 'build' +==> camp: Executing phase: 'install' +==> camp: Successfully installed camp-2024.02.0-v5g75d763xm5z5ohoqyp77effjwc6saz + Stage: 0.75s. Cmake: 0.96s. Build: 0.26s. Install: 0.04s. Post-install: 0.01s. Total: 2.06s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/camp-2024.02.0-v5g75d763xm5z5ohoqyp77effjwc6saz +==> Installing pmix-5.0.3-3dzzw34om3f3egm2mvq2euhc57zsu6py [35/57] +==> No binary for pmix-5.0.3-3dzzw34om3f3egm2mvq2euhc57zsu6py found: installing from source +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.creationtime' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.lastuseddate#PS' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemTextContentLanguage' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseVersion' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseLabels' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.metadata:kMDItemKeyphraseConfidences' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +/usr/bin/tar: Ignoring unknown extended header keyword 'LIBARCHIVE.xattr.com.apple.provenance' +==> Fetching https://mirror.spack.io/_source-cache/archive/3f/3f779434ed59fc3d63e4f77f170605ac3a80cd40b1f324112214b0efbdc34f13.tar.bz2 +==> No patches needed for pmix +==> pmix: Executing phase: 'autoreconf' +==> pmix: Executing phase: 'configure' +==> Error: ProcessError: Command exited with status 1: + '/tmp/sam/spack-stage/spack-stage-pmix-5.0.3-3dzzw34om3f3egm2mvq2euhc57zsu6py/spack-src/configure' '--prefix=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/pmix-5.0.3-3dzzw34om3f3egm2mvq2euhc57zsu6py' '--enable-shared' '--enable-static' '--disable-sphinx' '--with-zlib=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/zlib-ng-2.2.1-46skka27gwzx4san5zkrunivcm7nz564' '--with-libevent=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/libevent-2.1.12-73jyhsbj4rgjg4mf4ydazdyn6d73dgoe' '--with-hwloc=/usr' '--with-hwloc-libdir=' '--disable-python-bindings' '--without-munge' + +1 error found in build log: + 450 checking if hwloc pkg-config module exists... no + 451 checking for hwloc header at /usr/include... not found + 452 configure: WARNING: PMIx requires HWLOC topology library support, but + 453 configure: WARNING: an adequate version of that library was not found. + 454 configure: WARNING: Please reconfigure and point to a location where + 455 configure: WARNING: the HWLOC library can be found. + >> 456 configure: error: Cannot continue. + +See build log for details: + /tmp/sam/spack-stage/spack-stage-pmix-5.0.3-3dzzw34om3f3egm2mvq2euhc57zsu6py/spack-build-out.txt + +==> Warning: Skipping build of openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e since pmix-5.0.3-3dzzw34om3f3egm2mvq2euhc57zsu6py failed +==> Warning: Skipping build of tribol-0.1.0.16-5rbkkltig563suvbqo4qstu7djugw5dd since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of serac-develop-l77xejhejbbfmh5b4vqtxxw3paidppuo since tribol-0.1.0.16-5rbkkltig563suvbqo4qstu7djugw5dd failed +==> Warning: Skipping build of axom-0.9.0.1-crlt4idlryebgcrsch46aoakm55a7jnf since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of adiak-0.4.0-kgt73cvn75plcq5fuk2cvxulzm4izttf since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of caliper-2.10.0-julim3sed75ysjjl4xi2wqn2oui3gogn since adiak-0.4.0-kgt73cvn75plcq5fuk2cvxulzm4izttf failed +==> Warning: Skipping build of netlib-scalapack-2.2.0-feus7pkj7yhgvqrrf635dcj6id4gpe46 since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of strumpack-7.2.0-6rmybu6moclr62zaoqs26m2sj4gvl4ru since netlib-scalapack-2.2.0-feus7pkj7yhgvqrrf635dcj6id4gpe46 failed +==> Warning: Skipping build of mfem-4.7.0.1-hg6gqwaz5i5qibpbj7f6qzq4gbf4az6i since strumpack-7.2.0-6rmybu6moclr62zaoqs26m2sj4gvl4ru failed +==> Warning: Skipping build of petsc-3.21.5-hb3kxxheevzh3emk6qc6s346zmxnevj5 since strumpack-7.2.0-6rmybu6moclr62zaoqs26m2sj4gvl4ru failed +==> Warning: Skipping build of slepc-3.21.0-hzaovye7lucyxctskz3arfluk6q75v7g since petsc-3.21.5-hb3kxxheevzh3emk6qc6s346zmxnevj5 failed +==> Warning: Skipping build of superlu-dist-8.1.2-2glyola75o2amhmctein5g2oipuynvk4 since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of conduit-0.9.2-7ymuqal4duighrautwywbotvwk4kbcub since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of hypre-2.26.0-kwxuezssmhwryylzr744fx3c5dnf6mn2 since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of sundials-6.7.0-t4m7tfitf4lv7ebf5uax4mg7jqovgv4c since hypre-2.26.0-kwxuezssmhwryylzr744fx3c5dnf6mn2 failed +==> Warning: Skipping build of parmetis-4.0.3-njvbvvpjyx2hjvel7asmtlpugntv66lt since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Warning: Skipping build of arpack-ng-3.9.0-fq3up2e27wezbrye23mrhb7hc6ktbxha since openmpi-5.0.5-gyvgslwg3a74emc456byyqhdcvrf3c7e failed +==> Installing elfutils-0.191-vtbtqmzvsgyoup5klhaeea2olssag5xo [36/57] +==> No binary for elfutils-0.191-vtbtqmzvsgyoup5klhaeea2olssag5xo found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/df/df76db71366d1d708365fc7a6c60ca48398f14367eb2b8954efc8897147ad871.tar.bz2 +==> Ran patch() for elfutils +==> elfutils: Executing phase: 'autoreconf' +==> elfutils: Executing phase: 'configure' +==> Error: ProcessError: Command exited with status 1: + '/tmp/sam/spack-stage/spack-stage-elfutils-0.191-vtbtqmzvsgyoup5klhaeea2olssag5xo/spack-src/configure' '--prefix=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/elfutils-0.191-vtbtqmzvsgyoup5klhaeea2olssag5xo' '--with-bzlib=/usr' '--with-lzma=/usr' '--with-zlib=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/zlib-ng-2.2.1-46skka27gwzx4san5zkrunivcm7nz564' '--program-prefix='"'"'eu-'"'"'' '--with-zstd=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/zstd-1.5.6-dwvdelj5psbmp2y3rv4n7q7myybsagtv' '--with-libiconv-prefix=/home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/libiconv-1.17-yurditifflzptvup5hj7ytoaswco6aav' '--without-libintl-prefix' '--disable-debuginfod' '--disable-libdebuginfod' + +1 error found in build log: + 60 checking for special C compiler options needed for large files... no + 61 checking for _FILE_OFFSET_BITS value needed for large files... no + 62 checking whether fts.h is bad when included (with LFS)... no + 63 checking whether to add -D_FORTIFY_SOURCE=2 or =3 to CFLAGS... yes -D_FORTIFY_SOURCE=3 + 64 checking for library containing gzdirect... -lz + 65 checking for library containing BZ2_bzdopen... no + >> 66 configure: error: missing -lbz2 for --with-bzlib + +See build log for details: + /tmp/sam/spack-stage/spack-stage-elfutils-0.191-vtbtqmzvsgyoup5klhaeea2olssag5xo/spack-build-out.txt + +==> Installing hdf5-1.8.23-gpzjvgu5li5br7sy2f2otmenx3cr54oy [37/57] +==> No binary for hdf5-1.8.23-gpzjvgu5li5br7sy2f2otmenx3cr54oy found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/37/37fa4eb6cd0e181eb49a10d54611cb00700e9537f805d03e6853503afe5abc27.tar.gz +==> Ran patch() for hdf5 +==> hdf5: Executing phase: 'cmake' +==> hdf5: Executing phase: 'build' +==> hdf5: Executing phase: 'install' +==> hdf5: Successfully installed hdf5-1.8.23-gpzjvgu5li5br7sy2f2otmenx3cr54oy + Stage: 0.43s. Cmake: 18.43s. Build: 11.49s. Install: 0.32s. Post-install: 0.04s. Total: 30.79s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/hdf5-1.8.23-gpzjvgu5li5br7sy2f2otmenx3cr54oy +==> Installing umpire-2024.02.0-zapeqzpd4ambdf6nzl5r7micjyabnmta [38/57] +==> No binary for umpire-2024.02.0-zapeqzpd4ambdf6nzl5r7micjyabnmta found: installing from source +==> No patches needed for umpire +==> umpire: Executing phase: 'initconfig' +==> umpire: Executing phase: 'cmake' +==> umpire: Executing phase: 'build' +==> umpire: Executing phase: 'install' +==> umpire: Successfully installed umpire-2024.02.0-zapeqzpd4ambdf6nzl5r7micjyabnmta + Stage: 0.99s. Initconfig: 0.01s. Cmake: 1.15s. Build: 4.82s. Install: 0.10s. Post-install: 0.02s. Total: 7.15s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/umpire-2024.02.0-zapeqzpd4ambdf6nzl5r7micjyabnmta +==> Installing raja-2024.02.0-5pwfb3yr4p575lhqtzhhvywvsghkdbfc [39/57] +==> No binary for raja-2024.02.0-5pwfb3yr4p575lhqtzhhvywvsghkdbfc found: installing from source +==> No patches needed for raja +==> raja: Executing phase: 'initconfig' +==> raja: Executing phase: 'cmake' +==> raja: Executing phase: 'build' +==> raja: Executing phase: 'install' +==> raja: Successfully installed raja-2024.02.0-5pwfb3yr4p575lhqtzhhvywvsghkdbfc + Stage: 1.05s. Initconfig: 0.01s. Cmake: 1.24s. Build: 0.66s. Install: 0.09s. Post-install: 0.05s. Total: 3.13s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/raja-2024.02.0-5pwfb3yr4p575lhqtzhhvywvsghkdbfc +==> Installing netcdf-c-4.7.4-o4h3fi5jvtfrikv5zvt47mw7tiut4vk6 [40/57] +==> No binary for netcdf-c-4.7.4-o4h3fi5jvtfrikv5zvt47mw7tiut4vk6 found: installing from source +==> Fetching https://mirror.spack.io/_source-cache/archive/99/99930ad7b3c4c1a8e8831fb061cb02b2170fc8e5ccaeda733bd99c3b9d31666b.tar.gz +==> No patches needed for netcdf-c +==> netcdf-c: Executing phase: 'autoreconf' +==> netcdf-c: Executing phase: 'configure' +==> netcdf-c: Executing phase: 'build' +==> netcdf-c: Executing phase: 'install' +==> netcdf-c: Successfully installed netcdf-c-4.7.4-o4h3fi5jvtfrikv5zvt47mw7tiut4vk6 + Stage: 1.27s. Autoreconf: 0.00s. Configure: 18.77s. Build: 4.50s. Install: 0.90s. Post-install: 0.02s. Total: 25.55s +[+] /home/sam/code/serac_libs_dec_24/spack/opt/spack/linux-ubuntu22.04-skylake/gcc-12.3.0/netcdf-c-4.7.4-o4h3fi5jvtfrikv5zvt47mw7tiut4vk6 +==> Error: serac-develop-l77xejhejbbfmh5b4vqtxxw3paidppuo: Package was not installed +==> Error: serac-develop-l77xejhejbbfmh5b4vqtxxw3paidppuo: Package was not installed +==> Error: Installation request failed. Refer to reported errors for failing package(s). +==> Updating view at /home/sam/code/serac_libs_dec_24/spack_env/.spack-env/view +[ERROR: Failure of spack install] diff --git a/data/meshes/one_tri.mesh b/data/meshes/one_tri.mesh new file mode 100644 index 0000000000..59d619c094 --- /dev/null +++ b/data/meshes/one_tri.mesh @@ -0,0 +1,29 @@ +MFEM mesh v1.0 + +# +# MFEM Geometry Types (see mesh/geom.hpp): +# +# POINT = 0 +# SEGMENT = 1 +# TRIANGLE = 2 +# SQUARE = 3 +# TETRAHEDRON = 4 +# CUBE = 5 +# + +dimension +2 + +elements +1 +1 2 0 1 2 + +boundary +0 + +vertices +3 +2 +0 0 +1 0 +0 1 diff --git a/data/meshes/testAttr.e b/data/meshes/testAttr.e new file mode 100644 index 0000000000..1d73cd3421 Binary files /dev/null and b/data/meshes/testAttr.e differ diff --git a/data/meshes/two_hexes.mesh b/data/meshes/two_hexes.mesh new file mode 100755 index 0000000000..7d5a65d585 --- /dev/null +++ b/data/meshes/two_hexes.mesh @@ -0,0 +1,39 @@ +MFEM mesh v1.0 + +# +# MFEM Geometry Types (see mesh/geom.hpp): +# +# POINT = 0 +# SEGMENT = 1 +# TRIANGLE = 2 +# SQUARE = 3 +# TETRAHEDRON = 4 +# CUBE = 5 +# + +dimension +3 + +elements +2 +1 5 0 1 3 2 4 5 7 6 +1 5 4 5 7 6 8 9 11 10 + +boundary +0 + +vertices +12 +3 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +0 0 1 +1 0 1 +0 1 1 +1 1 1 +0 0 2 +1 0 2 +0 1 2 +1 1 2 diff --git a/data/meshes/two_tets.mesh b/data/meshes/two_tets.mesh new file mode 100644 index 0000000000..980e6b4158 --- /dev/null +++ b/data/meshes/two_tets.mesh @@ -0,0 +1,32 @@ +MFEM mesh v1.0 + +# +# MFEM Geometry Types (see mesh/geom.hpp): +# +# POINT = 0 +# SEGMENT = 1 +# TRIANGLE = 2 +# SQUARE = 3 +# TETRAHEDRON = 4 +# CUBE = 5 +# + +dimension +3 + +elements +2 +1 4 0 1 2 3 +1 4 1 2 3 4 + +boundary +0 + +vertices +5 +3 +0 0 0 +1 0 0 +0 1 0 +0 0 1 +1 1 1 diff --git a/data/meshes/two_tris.mesh b/data/meshes/two_tris.mesh new file mode 100644 index 0000000000..054bcae7e8 --- /dev/null +++ b/data/meshes/two_tris.mesh @@ -0,0 +1,35 @@ +MFEM mesh v1.0 + +# +# MFEM Geometry Types (see mesh/geom.hpp): +# +# POINT = 0 +# SEGMENT = 1 +# TRIANGLE = 2 +# SQUARE = 3 +# TETRAHEDRON = 4 +# CUBE = 5 +# + +dimension +2 + +elements +2 +1 2 0 1 2 +1 2 1 3 2 + +boundary +4 +1 1 0 1 +1 1 1 3 +1 1 3 2 +1 1 2 0 + +vertices +4 +2 +0 0 +1 0 +0 1 +1 1 diff --git a/src/serac/numerics/CMakeLists.txt b/src/serac/numerics/CMakeLists.txt index 8ea67ec6b8..a0a2ff0e50 100644 --- a/src/serac/numerics/CMakeLists.txt +++ b/src/serac/numerics/CMakeLists.txt @@ -6,6 +6,8 @@ add_subdirectory(functional) +add_subdirectory(refactor) + set(numerics_headers equation_solver.hpp odes.hpp diff --git a/src/serac/numerics/functional/detail/hexahedron_H1.inl b/src/serac/numerics/functional/detail/hexahedron_H1.inl index 1e8d0a02b2..1e1be13ac9 100644 --- a/src/serac/numerics/functional/detail/hexahedron_H1.inl +++ b/src/serac/numerics/functional/detail/hexahedron_H1.inl @@ -209,7 +209,7 @@ struct finite_element > { union { tensor one_dimensional; tensor, tensor >, q, q, q> three_dimensional; - } output; + } output{}; for (int qz = 0; qz < q; qz++) { for (int qy = 0; qy < q; qy++) { diff --git a/src/serac/numerics/functional/detail/metaprogramming.hpp b/src/serac/numerics/functional/detail/metaprogramming.hpp index 66b7d4be30..3bd7910f89 100644 --- a/src/serac/numerics/functional/detail/metaprogramming.hpp +++ b/src/serac/numerics/functional/detail/metaprogramming.hpp @@ -98,3 +98,16 @@ SERAC_HOST_DEVICE constexpr void for_constexpr(const lambda& f) { detail::for_constexpr(f, std::make_integer_sequence{}...); } + + +namespace impl { + template < auto x > + struct value{ + constexpr operator decltype(x)() { return x; } + }; +} + +template < auto ... args, typename T > +void foreach_constexpr(T && function) { + (function(impl::value{}), ...); +} diff --git a/src/serac/numerics/functional/detail/quadrilateral_H1.inl b/src/serac/numerics/functional/detail/quadrilateral_H1.inl index b0ef136ce9..c6a544ec3e 100644 --- a/src/serac/numerics/functional/detail/quadrilateral_H1.inl +++ b/src/serac/numerics/functional/detail/quadrilateral_H1.inl @@ -226,7 +226,7 @@ struct finite_element > { union { tensor one_dimensional; tensor, tensor >, q, q> two_dimensional; - } output; + } output{}; for (int qy = 0; qy < q; qy++) { for (int qx = 0; qx < q; qx++) { diff --git a/src/serac/numerics/functional/domain.hpp b/src/serac/numerics/functional/domain.hpp index 97f5ebeb92..8721bfe0df 100644 --- a/src/serac/numerics/functional/domain.hpp +++ b/src/serac/numerics/functional/domain.hpp @@ -182,6 +182,7 @@ struct Domain { exit(1); } + /** * @brief returns how many elements of any type belong to this domain */ @@ -246,6 +247,28 @@ struct Domain { mfem::Geometry::Type element_geometry); }; +inline uint32_t spatial_dimension(const Domain & domain) { + return static_cast(domain.mesh_.SpaceDimension()); +} + +inline uint32_t geometry_dimension(const Domain & domain) { + return static_cast(domain.dim_); +} + +enum class DomainType { ISOPARAMETRIC, SPATIAL }; + +struct DomainWithType { + const Domain & domain; + const DomainType type; + + DomainWithType(const Domain & d) : domain(d), type(DomainType::SPATIAL) {}; + DomainWithType(DomainType t, const Domain & d) : domain(d), type(t) {}; +}; + +inline DomainWithType isoparametric(const Domain & domain) { + return DomainWithType(DomainType::ISOPARAMETRIC, domain); +} + /// @brief constructs a domain from all the elements in a mesh Domain EntireDomain(const mesh_t& mesh); diff --git a/src/serac/numerics/functional/element_restriction.hpp b/src/serac/numerics/functional/element_restriction.hpp index dc2e1c3360..25fa55f215 100644 --- a/src/serac/numerics/functional/element_restriction.hpp +++ b/src/serac/numerics/functional/element_restriction.hpp @@ -61,7 +61,7 @@ struct DoF { DoF() : bits{} {} /// copy ctor - DoF(const DoF& other) : bits{other.bits} {} + //DoF(const DoF& other) : bits{other.bits} {} /// create a `DoF` from the given index, sign and orientation values DoF(uint64_t index, uint64_t sign = 0, uint64_t orientation = 0) @@ -70,7 +70,7 @@ struct DoF { } /// copy assignment operator - void operator=(const DoF& other) { bits = other.bits; } + //void operator=(const DoF& other) { bits = other.bits; } /// get the sign field of this `DoF` int sign() const { return (bits & sign_mask) ? -1 : 1; } diff --git a/src/serac/numerics/functional/family.hpp b/src/serac/numerics/functional/family.hpp new file mode 100644 index 0000000000..e43254f28d --- /dev/null +++ b/src/serac/numerics/functional/family.hpp @@ -0,0 +1,23 @@ +#pragma once + +namespace serac { + +/** + * @brief Element conformity + * + * QOI denotes a "quantity of interest", implying integration with the test function "1" + * H1 denotes a function space where values are continuous across element boundaries + * HCURL denotes a vector-valued function space where only the tangential component is continuous across element + * boundaries HDIV denotes a vector-valued function space where only the normal component is continuous across element + * boundaries L2 denotes a function space where values are discontinuous across element boundaries + */ +enum class Family +{ + QOI, + H1, + HCURL, + HDIV, + L2 +}; + +} diff --git a/src/serac/numerics/functional/finite_element.hpp b/src/serac/numerics/functional/finite_element.hpp index dcbab1f8e0..15c682730f 100644 --- a/src/serac/numerics/functional/finite_element.hpp +++ b/src/serac/numerics/functional/finite_element.hpp @@ -12,6 +12,7 @@ */ #pragma once +#include "family.hpp" #include "tuple.hpp" #include "tensor.hpp" #include "geometry.hpp" @@ -169,23 +170,7 @@ SERAC_HOST_DEVICE constexpr int elements_per_block(int q) } } -/** - * @brief Element conformity - * - * QOI denotes a "quantity of interest", implying integration with the test function "1" - * H1 denotes a function space where values are continuous across element boundaries - * HCURL denotes a vector-valued function space where only the tangential component is continuous across element - * boundaries HDIV denotes a vector-valued function space where only the normal component is continuous across element - * boundaries L2 denotes a function space where values are discontinuous across element boundaries - */ -enum class Family -{ - QOI, - H1, - HCURL, - HDIV, - L2 -}; + /** * @brief H1 elements of order @p p diff --git a/src/serac/numerics/functional/tensor.hpp b/src/serac/numerics/functional/tensor.hpp index e215e486ed..22755d8172 100644 --- a/src/serac/numerics/functional/tensor.hpp +++ b/src/serac/numerics/functional/tensor.hpp @@ -73,19 +73,46 @@ struct tensor { SERAC_HOST_DEVICE constexpr auto& operator[](int i) { return data[i]; } SERAC_HOST_DEVICE constexpr const auto& operator[](int i) const { return data[i]; } - template ::type> + SERAC_HOST_DEVICE constexpr auto& operator[](uint32_t i) { return data[i]; } + SERAC_HOST_DEVICE constexpr const auto& operator[](uint32_t i) const { return data[i]; } + + T data[m]; +}; + +template +struct tensor { + + SERAC_HOST_DEVICE constexpr tensor() : data{} {} + SERAC_HOST_DEVICE constexpr tensor(T value) : data(value) {} + + template + SERAC_HOST_DEVICE constexpr auto& operator()(i_type) + { + return data; + } + template + SERAC_HOST_DEVICE constexpr auto& operator()(i_type) const + { + return data; + } + + SERAC_HOST_DEVICE constexpr auto& operator[](int) { return data; } + SERAC_HOST_DEVICE constexpr const auto& operator[](int) const { return data; } + + SERAC_HOST_DEVICE constexpr auto& operator[](uint32_t) { return data; } + SERAC_HOST_DEVICE constexpr const auto& operator[](uint32_t) const { return data; } + SERAC_HOST_DEVICE constexpr operator T() { - return data[0]; + return data; } - template ::type> SERAC_HOST_DEVICE constexpr operator T() const { - return data[0]; + return data; } - T data[m]; + T data; }; /// @endcond @@ -111,12 +138,20 @@ tensor(const T (&data)[n1]) -> tensor; template tensor(const T (&data)[n1][n2]) -> tensor; +using vec1 = tensor; ///< statically sized "vector" of 1 double using vec2 = tensor; ///< statically sized vector of 2 doubles using vec3 = tensor; ///< statically sized vector of 3 doubles +template < int n, typename T = double > +using vec = tensor; ///< statically sized vector with n components + +using mat1 = tensor; ///< statically sized 1x1 "matrix" of doubles using mat2 = tensor; ///< statically sized 2x2 matrix of doubles using mat3 = tensor; ///< statically sized 3x3 matrix of doubles +template < int m, int n, typename T = double > +using mat = tensor; ///< statically sized mxn matrix + /** * @brief A sentinel struct for eliding no-op tensor operations */ @@ -591,6 +626,15 @@ SERAC_HOST_DEVICE constexpr auto& operator-=(tensor& A, zero) return A; } +/** + * @overload + * @note this overload implements the case where both arguments are scalars + */ +SERAC_HOST_DEVICE constexpr auto outer(double A, double B) +{ + return A * B; +} + /** * @overload * @note this overload implements the case where the left argument is a scalar, and the right argument is a tensor @@ -1234,11 +1278,23 @@ SERAC_HOST_DEVICE constexpr auto I2(const tensor& A) A[2][0] * A[0][2]; } +SERAC_HOST_DEVICE constexpr auto det(const double & A) +{ + return A; +} + /** * @brief Returns the determinant of a matrix * @param[in] A The matrix to obtain the determinant of */ template +SERAC_HOST_DEVICE constexpr auto det(const tensor& A) +{ + return A[0][0]; +} + +/// @overload +template SERAC_HOST_DEVICE constexpr auto det(const tensor& A) { return A[0][0] * A[1][1] - A[0][1] * A[1][0]; @@ -1584,6 +1640,15 @@ SERAC_HOST_DEVICE constexpr auto linear_solve(const LuFactorization& /* lu return zero{}; } +/** + * @brief Inverts a (1x1) matrix + * @param[in] A The "matrix" to invert + */ +SERAC_HOST_DEVICE constexpr double inv(const double & A) +{ + return 1.0 / A; +} + /** * @brief Inverts a matrix * @param[in] A The matrix to invert diff --git a/src/serac/numerics/functional/tests/functional_basic_dg.cpp b/src/serac/numerics/functional/tests/functional_basic_dg.cpp index 6f5c205ae6..7154233a72 100644 --- a/src/serac/numerics/functional/tests/functional_basic_dg.cpp +++ b/src/serac/numerics/functional/tests/functional_basic_dg.cpp @@ -71,7 +71,7 @@ void L2_test(std::string meshfile) double t = 0.0; auto value = residual(t, U); - // check_gradient(residual, t, U); + check_gradient(residual, t, U); } TEST(basic, L2_test_tris_and_quads_linear) { L2_test<2, 1>(SERAC_REPO_DIR "/data/meshes/patch2D_tris_and_quads.mesh"); } diff --git a/src/serac/numerics/functional/typedefs.hpp b/src/serac/numerics/functional/typedefs.hpp index 7dbe070f9a..1515590c62 100644 --- a/src/serac/numerics/functional/typedefs.hpp +++ b/src/serac/numerics/functional/typedefs.hpp @@ -7,7 +7,7 @@ namespace serac { // interface change like that, so these typedefs mark the parts that would need to eventually change /// @cond -using mesh_t = mfem::Mesh; +using mesh_t = mfem::ParMesh; using fes_t = mfem::FiniteElementSpace; /// @endcond diff --git a/src/serac/numerics/refactor/CMakeLists.txt b/src/serac/numerics/refactor/CMakeLists.txt new file mode 100644 index 0000000000..7e549e3671 --- /dev/null +++ b/src/serac/numerics/refactor/CMakeLists.txt @@ -0,0 +1,62 @@ +# Copyright (c) 2019-2024, Lawrence Livermore National Security, LLC and +# other Serac Project Developers. See the top-level LICENSE file for +# details. +# +# SPDX-License-Identifier: (BSD-3-Clause) + +add_subdirectory(containers) + +set(refactor_headers + + elements/h1_edge.hpp + elements/h1_hexahedron.hpp + elements/h1_quadrilateral.hpp + elements/h1_tetrahedron.hpp + elements/h1_triangle.hpp + elements/h1_vertex.hpp + + elements/hcurl_edge.hpp + elements/hcurl_hexahedron.hpp + elements/hcurl_quadrilateral.hpp + elements/hcurl_tetrahedron.hpp + elements/hcurl_triangle.hpp + elements/hcurl_vertex.hpp + + common.hpp + evaluate.hpp + integrate.hpp + +) + +set(refactor_sources + common.cpp + evaluate.cpp + integrate_diag.cpp + integrate_spmat.cpp + integrate_residual.cpp + interpolation.cpp + quadrature.cpp + + get_nodal_coordinates.cpp + get_nodal_directions.cpp +) + +set(refactor_depends serac_physics serac_infrastructure serac_functional serac_refactor_containers) + +blt_add_library( + NAME serac_refactor + HEADERS ${refactor_headers} + SOURCES ${refactor_sources} + DEPENDS_ON ${refactor_depends} + ) + +install(FILES ${refactor_headers} DESTINATION include/serac/refactor ) + +install(TARGETS serac_refactor + EXPORT serac-targets + DESTINATION lib + ) + +if(SERAC_ENABLE_TESTS) + add_subdirectory(tests) +endif() diff --git a/src/serac/numerics/refactor/common.cpp b/src/serac/numerics/refactor/common.cpp new file mode 100644 index 0000000000..4d8c7cbd14 --- /dev/null +++ b/src/serac/numerics/refactor/common.cpp @@ -0,0 +1,61 @@ +#include "common.hpp" + +namespace refactor { + +uint32_t elements_per_block(mfem::Geometry::Type geom, Family family, int p) { + + uint32_t gid = uint32_t(geom); + uint32_t fid = uint32_t(family); + + uint32_t values[6][2][4] = { + + // vertex + {{{}}}, + + // edge + { + {0, 32, 16, 16}, // H1 + {0, 1, 1, 1}, // Hcurl + }, + + // triangle + { + {0, 32, 16, 16}, // H1 + {0, 1, 1, 1}, // Hcurl + }, + + // quadrilateral + { + {0, 32, 14, 8}, // H1 + {0, 1, 1, 1}, // Hcurl + }, + + // tetrahedron + { + {0, 12, 8, 8}, // H1 + {0, 1, 1, 1}, // Hcurl + }, + + // hexahedron + { + {0, 8, 4, 2}, // H1 + {0, 1, 1, 1}, // Hcurl + }, + }; + + return values[gid][fid][p]; + +} + +GeometryInfo geometry_counts(const Domain & domain) { + return { + 0, + uint32_t(domain.edge_ids_.size()), + uint32_t(domain.tri_ids_.size()), + uint32_t(domain.quad_ids_.size()), + uint32_t(domain.tet_ids_.size()), + uint32_t(domain.hex_ids_.size()) + }; +} + +} // namespace refactor diff --git a/src/serac/numerics/refactor/common.hpp b/src/serac/numerics/refactor/common.hpp new file mode 100644 index 0000000000..764d55a8c2 --- /dev/null +++ b/src/serac/numerics/refactor/common.hpp @@ -0,0 +1,251 @@ +#pragma once + +#include "serac/infrastructure/accelerator.hpp" +#include "serac/numerics/functional/tensor.hpp" +#include "serac/numerics/refactor/finite_element.hpp" + +namespace refactor { + +uint32_t elements_per_block(mfem::Geometry::Type geom, Family family, int p); + +GeometryInfo geometry_counts(const Domain & domain); + +template < typename T > +struct array_rank; + +template < typename T, uint32_t n > +struct array_rank< nd::view< T, n > >{ + static constexpr uint32_t value = n; +}; + +template < typename T, uint32_t n > +struct array_rank< nd::array< T, n > >{ + static constexpr uint32_t value = n; +}; + +SERAC_HOST_DEVICE constexpr uint32_t round_up_to_multiple_of_128(uint32_t n) { + return ((n + 127) / 128) * 128; +}; + +constexpr uint32_t source_shape(Family f, uint32_t gdim) { + switch(f) { + case Family::QOI: return 1; + case Family::H1: return 1; + case Family::HCURL: return gdim; + case Family::HDIV: return gdim; + case Family::L2: return 1; + } + return (1u << 31); +} + +constexpr uint32_t flux_shape(Family f, uint32_t gdim) { + switch(f) { + case Family::QOI: return 0; + case Family::H1: return gdim; + case Family::HCURL: return (gdim == 2) ? 1 : gdim; + case Family::HDIV: return (gdim == 2) ? 1 : gdim; + case Family::L2: return gdim; + } + + return (1u << 31); +} + +template < Family f, DerivedQuantity op, int dim > +auto piola_transformation(const mat & dX_dxi) { + if constexpr ((f == Family::H1 && op == DerivedQuantity::DERIVATIVE) || + (f == Family::L2 && op == DerivedQuantity::DERIVATIVE) || + (f == Family::HCURL && op == DerivedQuantity::VALUE)) { + return inv(dX_dxi); + } + + if constexpr ((f == Family::HCURL && op == DerivedQuantity::DERIVATIVE) || + (f == Family::HDIV && op == DerivedQuantity::VALUE)) { + if constexpr (dim == 2) { + return mat<1,1>{1.0 / det(dX_dxi)}; + } else { + return transpose(dX_dxi) / det(dX_dxi); + } + } + + if constexpr ((f == Family::H1 && op == DerivedQuantity::VALUE) || + (f == Family::L2 && op == DerivedQuantity::VALUE) || + (f == Family::HDIV && op == DerivedQuantity::DERIVATIVE)) { + // this should never be called, but we implement it here regardless + // to suppress a compiler warning about incompatible return values + return 1.0; + } +} + +template < Family f, DerivedQuantity op, int dim > +auto weighted_piola_transformation(const mat & dX_dxi) { + if constexpr ((f == Family::H1 && op == DerivedQuantity::DERIVATIVE) || + (f == Family::L2 && op == DerivedQuantity::DERIVATIVE) || + (f == Family::HCURL && op == DerivedQuantity::VALUE)) { + return adj(dX_dxi); + } + + if constexpr ((f == Family::HCURL && op == DerivedQuantity::DERIVATIVE) || + (f == Family::HDIV && op == DerivedQuantity::VALUE)) { + if constexpr (dim == 2) { + return mat<1,1>{1.0}; + } else { + return transpose(dX_dxi); + } + } + + if constexpr ((f == Family::H1 && op == DerivedQuantity::VALUE) || + (f == Family::L2 && op == DerivedQuantity::VALUE) || + (f == Family::HDIV && op == DerivedQuantity::DERIVATIVE)) { + return det(dX_dxi); + } +} + +// +------------+------+-------+------+----+ +// | | H1 | Hcurl | Hdiv | DG | +// +------------+------+-------+------+----+ +// | value (1D) | 1 | 1 | 1 | 1 | +// +------------+------+-------+------+----+ +// | deriv (1D) | 1 | 1 | 1 | 1 | +// +------------+------+-------+------+----+ +// | value (2D) | 1 | 2 | 2 | 1 | +// +------------+------+-------+------+----+ +// | deriv (2D) | 2 | 1 | 1 | 2 | +// +------------+------+-------+------+----+ +// | value (3D) | 1 | 3 | 3 | 1 | +// +------------+------+-------+------+----+ +// | deriv (3D) | 3 | 3 | 1 | 3 | +// +------------+------+-------+------+----+ +constexpr uint32_t qshape(Family f, DerivedQuantity op, uint32_t gdim) { + + if (op == DerivedQuantity::VALUE) { + return is_vector_valued(f) ? gdim : 1; + } + + if (op == DerivedQuantity::DERIVATIVE) { + if (f == Family::H1 || f == Family::L2) { return gdim; } + if (f == Family::HCURL) { return (gdim == 2) ? 1 : gdim; } + if (f == Family::HDIV) { return 1; } + } + + return (1u<<31); + +} + +template < typename T, uint32_t n > +stack::array remove_ones(const stack::array & x) { + uint32_t rank = 0; + stack::array copy{}; + for (uint32_t i = 0; i < n; i++) { + if (x[i] > 1) copy[rank++] = x[i]; + } + return copy; +} + +template < typename T, uint32_t m, uint32_t n > +bool compatible_shapes(const stack::array & x, + const stack::array & y) { + auto x_filtered = remove_ones(x); + auto y_filtered = remove_ones(y); + for (uint32_t i = 0; i < std::max(m, n); i++) { + auto xval = (i >= m) ? 0 : x_filtered[i]; + auto yval = (i >= n) ? 0 : y_filtered[i]; + if (xval != yval) { return false; } + } + return true; +} + +template < mfem::Geometry::Type geom > +auto quadrature_point(uint32_t q, const nd::view xi) { + + if constexpr (mfem::Geometry::SQUARE == geom) { + uint32_t q1D = xi.shape[0]; + uint32_t qx = q % q1D; + uint32_t qy = q / q1D; + return vec2{xi(qx, 0), xi(qy, 0)}; + } + + if constexpr (mfem::Geometry::CUBE == geom) { + uint32_t q1D = xi.shape[0]; + uint32_t qx = q % q1D; + uint32_t qy = (q % (q1D * q1D)) / q1D; + uint32_t qz = q / (q1D * q1D); + return vec3{xi(qx, 0), xi(qy, 0), xi(qz, 0)}; + } + + // all other geometries + constexpr int gdim = dimension(geom); + vec< gdim, double > xi_q; + for (uint32_t c = 0; c < gdim; c++) { + xi_q(c) = xi(q, c); + } + return xi_q; + +} + +namespace impl { + +template < Family family, uint32_t n > +auto value_transformation(const mat & A) { + if constexpr (family == Family::H1) { + return mat1{1.0}; + } + if constexpr (family == Family::HCURL) { + return inv(A); + } +} + +template < Family family, uint32_t n > +auto derivative_transformation(const mat & A) { + if constexpr (family == Family::H1) { + return contravariant_piola(A); + } + if constexpr (family == Family::HCURL) { + return covariant_piola(A); + } +} + +template < Family family, uint32_t n > +auto source_transformation(const mat & A) { + if constexpr (family == Family::H1) { + return det(A); + } + if constexpr (family == Family::HCURL) { + return inv(A) * det(A); + } +} + +template < Family family, uint32_t n > +auto flux_transformation(const mat & A) { + if constexpr (family == Family::H1) { + return inv(A) * det(A); + } + if constexpr (family == Family::HCURL) { + if constexpr (n <= 2) { + return vec1(1.0); + } + if constexpr (n == 3) { + return transpose(A); + } + } +} + +} + +} + +namespace nd { + +template < typename T, uint32_t n > +struct printer< serac::vec >{ + static SERAC_HOST_DEVICE void print(const serac::vec & v) { + printf("{"); + printer::print(v(0)); + for (int i = 1; i < n; i++) { + printf(","); + printer::print(v(i)); + } + printf("}"); + } +}; + +} diff --git a/src/serac/numerics/refactor/containers/CMakeLists.txt b/src/serac/numerics/refactor/containers/CMakeLists.txt new file mode 100644 index 0000000000..f517f97683 --- /dev/null +++ b/src/serac/numerics/refactor/containers/CMakeLists.txt @@ -0,0 +1,35 @@ +# Copyright (c) 2019-2024, Lawrence Livermore National Security, LLC and +# other Serac Project Developers. See the top-level LICENSE file for +# details. +# +# SPDX-License-Identifier: (BSD-3-Clause) + +set(refactor_containers_headers + ndarray.hpp + stack_array.hpp +) + +set(refactor_containers_sources + memory.cpp + relative_error.cpp +) + +set(refactor_containers_depends serac_infrastructure) + +blt_add_library( + NAME serac_refactor_containers + HEADERS ${refactor_containers_headers} + SOURCES ${refactor_containers_sources} + DEPENDS_ON ${refactor_containers_depends} + ) + +install(FILES ${refactor_containers_headers} DESTINATION include/serac/refactor/containers ) + +install(TARGETS serac_refactor_containers + EXPORT serac-targets + DESTINATION lib + ) + +if(SERAC_ENABLE_TESTS) + add_subdirectory(tests) +endif() diff --git a/src/serac/numerics/refactor/containers/memory.cpp b/src/serac/numerics/refactor/containers/memory.cpp new file mode 100644 index 0000000000..bf42b5f2a1 --- /dev/null +++ b/src/serac/numerics/refactor/containers/memory.cpp @@ -0,0 +1,23 @@ +#include "serac/numerics/refactor/containers/ndarray.hpp" + +#ifndef NDARRAY_ENABLE_CUDA +namespace memory { + + void * allocate(uint64_t n) { + return malloc(n); + } + + void deallocate(void * ptr) { + free(ptr); + } + + void memcpy(void * dest, void * src, uint64_t n) { + std::memcpy(dest, src, n); + } + + void zero(void * ptr, uint64_t n) { + std::memset(ptr, 0, n); + } + +} +#endif diff --git a/src/serac/numerics/refactor/containers/memory.cu b/src/serac/numerics/refactor/containers/memory.cu new file mode 100644 index 0000000000..827062ab43 --- /dev/null +++ b/src/serac/numerics/refactor/containers/memory.cu @@ -0,0 +1,37 @@ +#include "serac/numerics/refactor/containers/ndarray.hpp" + +#include + +#if NDARRAY_ENABLE_CUDA +#define error_check(ans) { gpuAssert((ans), __FILE__, __LINE__); } +inline void gpuAssert(cudaError_t code, const char *file, int line, bool abort=true) +{ + if (code != cudaSuccess) + { + fprintf(stderr,"GPUassert: %s %s %d\n", cudaGetErrorString(code), file, line); + if (abort) exit(code); + } +} + +namespace memory { + + void * allocate(uint64_t n) { + void * ptr; + error_check(cudaMallocManaged(&ptr, n)); + return ptr; + } + + void deallocate(void * ptr) { + error_check(cudaFree(ptr)); + } + + void memcpy(void * dest, void * src, uint64_t n) { + error_check(cudaMemcpy(dest, src, n, cudaMemcpyDefault)); + } + + void zero(void * ptr, uint64_t n) { + error_check(cudaMemset(ptr, 0, n)); + } + +} +#endif diff --git a/src/serac/numerics/refactor/containers/ndarray.hpp b/src/serac/numerics/refactor/containers/ndarray.hpp new file mode 100644 index 0000000000..d0dc692cb7 --- /dev/null +++ b/src/serac/numerics/refactor/containers/ndarray.hpp @@ -0,0 +1,579 @@ +#pragma once + +#include // for printf +#include // for std::memcpy +#include // for std::integer_sequence +#include +#include +#include + +#include "serac/infrastructure/accelerator.hpp" +#include "serac/numerics/refactor/containers/stack_array.hpp" + +namespace memory { + enum space {CPU, GPU, UNIFIED}; + + void * allocate(uint64_t n); + void deallocate(void * ptr); + void memcpy(void * dest, void * src, uint64_t n); + void zero(void * ptr, uint64_t n); + + template < typename T > + T * allocate(uint64_t n) { + return static_cast(allocate(n * sizeof(T))); + } + + template < typename T > + void deallocate(T * ptr) { + deallocate(static_cast(ptr)); + } + + template < typename T > + void memcpy(T * dest, T * src, uint64_t n) { + memcpy(static_cast(dest), static_cast(src), n * sizeof(T)); + } + + template < typename T > + void zero(T * ptr, uint64_t n) { + zero(static_cast(ptr), n * sizeof(T)); + } +} + +namespace nd { + + template < uint32_t dim > + SERAC_HOST_DEVICE uint32_t product(stack::array< uint32_t, dim > values) { + uint32_t p = values[0]; + for (uint32_t i = 1; i < dim; i++) { p *= values[i]; } + return p; + } + + enum ordering{ row_major, col_major }; + + template < uint32_t dim > + SERAC_HOST_DEVICE stack::array< uint32_t, dim > compute_strides(const stack::array< uint32_t, dim > & shape, ordering o, uint32_t m = 1) { + stack::array< uint32_t, dim > strides{}; + if (o == col_major) { + for (uint32_t i = 0; i < dim; i++) { + strides[i] = (i == 0) ? m : strides[i-1] * shape[i-1]; + } + } else { // row major + for (uint32_t i = 0; i < dim; i++) { + strides[dim-i-1] = (i == 0) ? m : strides[dim-i] * shape[dim-i]; + } + } + return strides; + } + + // used for slicing arrays and views + template < typename T > + struct range { T begin; T end; }; + + template < typename T > + range(T,T) -> range; + + template < typename T > + SERAC_HOST_DEVICE constexpr T begin(const range & r) { return r.begin; } + + template < typename T > + SERAC_HOST_DEVICE constexpr T end(const range & r) { return r.end; } + + template < typename T > + SERAC_HOST_DEVICE constexpr uint32_t is_range(T) { return 0; }; + + template < typename T > + SERAC_HOST_DEVICE constexpr uint32_t is_range(range) { return 1; }; + + SERAC_HOST_DEVICE constexpr int32_t begin(int32_t x) { return x; } + SERAC_HOST_DEVICE constexpr int64_t begin(int64_t x) { return x; } + SERAC_HOST_DEVICE constexpr uint32_t begin(uint32_t x) { return x; } + SERAC_HOST_DEVICE constexpr uint64_t begin(uint64_t x) { return x; } + + SERAC_HOST_DEVICE constexpr int32_t end(int32_t x) { return x; } + SERAC_HOST_DEVICE constexpr int64_t end(int64_t x) { return x; } + SERAC_HOST_DEVICE constexpr uint32_t end(uint32_t x) { return x; } + SERAC_HOST_DEVICE constexpr uint64_t end(uint64_t x) { return x; } + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + + template < typename T, uint32_t dim = 1 > + struct view { + static_assert(dim > 0); + + static constexpr auto iseq = std::make_integer_sequence< uint32_t, dim >(); + + SERAC_HOST_DEVICE constexpr view() { + values = nullptr; + sz = 0; + shape = {}; + stride = {}; + } + + SERAC_HOST_DEVICE constexpr view(T * input, const stack::array< uint32_t, dim > & dimensions) { + values = input; + for (uint32_t i = 0; i < dim; i++) { + uint32_t id = dim - 1 - i; + shape[id] = dimensions[id]; + stride[id] = (id == dim - 1) ? 1 : stride[id+1] * shape[id+1]; + } + sz = product(shape); + } + + SERAC_HOST_DEVICE constexpr view(T * input, const stack::array< uint32_t, dim > & dimensions, const stack::array< uint32_t, dim > & strides) { + values = input; + shape = dimensions; + stride = strides; + sz = product(shape); + } + + template < typename ... index_types > + SERAC_HOST_DEVICE uint32_t index(index_types ... indices) const { + static_assert(sizeof ... (indices) == dim); + return values[index(iseq, indices...)]; + } + + template < uint32_t ... I, typename ... index_types > + SERAC_HOST_DEVICE uint32_t index(std::integer_sequence, index_types ... indices) const { + #ifdef NDARRAY_ENABLE_BOUNDS_CHECKING + // note: the cast to int32_t is a way to avoid warnings + // about pointless comparison between unsigned integer types and 0 + if (((int32_t(indices) < 0 || indices >= shape[I]) || ... )) { + printf("array index out of bounds\n"); + }; + #endif + return ((static_cast(indices) * stride[I]) + ...); + } + + template < typename ... index_types > + SERAC_HOST_DEVICE decltype(auto) operator()(index_types ... indices) const { + constexpr uint32_t num_args = sizeof ... (indices); + static_assert(num_args <= dim); + constexpr uint32_t rank = (is_range(index_types{}) + ... ) + (dim - num_args); + if constexpr (rank == 0) { + return static_cast(values[index(iseq, indices...)]); + } else { + constexpr uint32_t is_a_range[] = {is_range(index_types{}) ... }; + stack::array slice_shape{}; + stack::array slice_stride{}; + + uint32_t beginnings[num_args] = {uint32_t(nd::begin(indices)) ... }; + uint32_t endings[num_args] = {uint32_t(nd::end(indices)) ... }; + int k = 0; + int offset = 0; + for (int i = 0; i < dim; i++) { + if (i >= num_args) { + slice_shape[k] = shape[i]; + slice_stride[k] = stride[i]; + k++; + } else { + offset += stride[i] * beginnings[i]; + if (is_a_range[i]) { + slice_shape[k] = endings[i] - beginnings[i]; + slice_stride[k] = stride[i]; + k++; + } + } + } + return view{&values[offset], slice_shape, slice_stride}; + } + } + + template < typename ... index_types > + SERAC_HOST_DEVICE decltype(auto) operator()(index_types ... indices) { + constexpr uint32_t num_args = sizeof ... (indices); + static_assert(num_args <= dim); + constexpr uint32_t rank = (is_range(index_types{}) + ... ) + (dim - num_args); + if constexpr (rank == 0) { + return static_cast(values[index(iseq, indices...)]); + } else { + constexpr uint32_t is_a_range[] = {is_range(index_types{}) ... }; + stack::array slice_shape{}; + stack::array slice_stride{}; + + uint32_t beginnings[num_args] = {uint32_t(nd::begin(indices)) ... }; + uint32_t endings[num_args] = {uint32_t(nd::end(indices)) ... }; + uint32_t k = 0; + uint32_t offset = 0; + for (uint32_t i = 0; i < dim; i++) { + if (i >= num_args) { + slice_shape[k] = shape[i]; + slice_stride[k] = stride[i]; + k++; + } else { + offset += stride[i] * beginnings[i]; + if (is_a_range[i]) { + slice_shape[k] = endings[i] - beginnings[i]; + slice_stride[k] = stride[i]; + k++; + } + } + } + return view{&values[offset], slice_shape, slice_stride}; + } + } + + template < typename index_type > + SERAC_HOST_DEVICE auto & operator[](index_type i) { return values[i]; } + + template < typename index_type > + SERAC_HOST_DEVICE auto & operator[](index_type i) const { return values[i]; } + + SERAC_HOST_DEVICE operator view() const { + return view{values, shape, stride}; + } + + SERAC_HOST_DEVICE T * data() { return &values[0]; } + SERAC_HOST_DEVICE const T * data() const { return &values[0]; } + + SERAC_HOST_DEVICE uint32_t size() const { return product(shape); } + + SERAC_HOST_DEVICE T * begin() const { return &values[0]; } + SERAC_HOST_DEVICE T * end() const { return &values[size()]; } + + T * values; + uint64_t sz; + stack::array< uint32_t, dim > shape; + stack::array< uint32_t, dim > stride; + + }; + + template < typename T, uint32_t dim > + struct view< const T, dim >{ + static_assert(dim > 0); + + static constexpr auto iseq = std::make_integer_sequence< uint32_t, dim >(); + + SERAC_HOST_DEVICE constexpr view() { + values = nullptr; + sz = 0; + shape = {}; + stride = {}; + } + + SERAC_HOST_DEVICE constexpr view(const T * input, const stack::array< uint32_t, dim > & dimensions) { + values = input; + for (uint32_t i = 0; i < dim; i++) { + uint32_t id = dim - 1 - i; + shape[id] = dimensions[id]; + stride[id] = (id == dim - 1) ? 1 : stride[id+1] * shape[id+1]; + } + sz = product(shape); + } + + SERAC_HOST_DEVICE constexpr view(const T * input, const stack::array< uint32_t, dim > & dimensions, const stack::array< uint32_t, dim > & strides) { + values = input; + shape = dimensions; + stride = strides; + sz = product(shape); + } + + template < typename ... index_types > + SERAC_HOST_DEVICE uint32_t index(index_types ... indices) const { + static_assert(sizeof ... (indices) == dim); + return values[index(iseq, indices...)]; + } + + template < uint32_t ... I, typename ... index_types > + SERAC_HOST_DEVICE uint32_t index(std::integer_sequence, index_types ... indices) const { + #ifdef NDARRAY_ENABLE_BOUNDS_CHECKING + // note: the cast to int32_t is a way to avoid warnings + // about pointless comparison between unsigned integer types and 0 + if (((int32_t(indices) < 0 || indices >= shape[I]) || ... )) { + printf("array index out of bounds\n"); + }; + #endif + return ((static_cast(indices) * stride[I]) + ...); + } + + template < typename ... index_types > + SERAC_HOST_DEVICE decltype(auto) operator()(index_types ... indices) const { + constexpr uint32_t num_args = sizeof ... (indices); + static_assert(num_args <= dim); + constexpr uint32_t rank = (is_range(index_types{}) + ... ) + (dim - num_args); + if constexpr (rank == 0) { + return static_cast(values[index(iseq, indices...)]); + } else { + constexpr uint32_t is_a_range[] = {is_range(index_types{}) ... }; + stack::array slice_shape{}; + stack::array slice_stride{}; + + uint32_t beginnings[num_args] = {uint32_t(nd::begin(indices)) ... }; + uint32_t endings[num_args] = {uint32_t(nd::end(indices)) ... }; + uint32_t k = 0; + uint32_t offset = 0; + for (uint32_t i = 0; i < dim; i++) { + if (i >= num_args) { + slice_shape[k] = shape[i]; + slice_stride[k] = stride[i]; + k++; + } else { + offset += stride[i] * beginnings[i]; + if (is_a_range[i]) { + slice_shape[k] = endings[i] - beginnings[i]; + slice_stride[k] = stride[i]; + k++; + } + } + } + return view{&values[offset], slice_shape, slice_stride}; + } + } + + template < typename index_type > + SERAC_HOST_DEVICE const T & operator[](index_type i) const { return values[i]; } + + SERAC_HOST_DEVICE const T * data() const { return &values[0]; } + + SERAC_HOST_DEVICE uint32_t size() const { return product(shape); } + + SERAC_HOST_DEVICE const T * begin() const { return &values[0]; } + SERAC_HOST_DEVICE const T * end() const { return &values[size()]; } + + const T * values; + uint64_t sz; + stack::array< uint32_t, dim > shape; + stack::array< uint32_t, dim > stride; + + }; + + template < typename T, uint32_t dim > + using const_view = view; + + template < typename T, uint32_t dim = 1 > + struct array : public view< T, dim > { + + using view::iseq; + using view::values; + using view::shape; + using view::stride; + using view::sz; + + array() : view() {} + + array(stack::array< uint32_t, dim > dimensions) : view() { resize(dimensions); } + + array(stack::array< uint32_t, dim > dimensions, + stack::array< uint32_t, dim > strides) : view() { + resize(dimensions, strides); + } + + array(const array & other) { + sz = other.sz; + shape = other.shape; + stride = other.stride; + allocate(sz); + memory::memcpy(values, other.values, other.sz); + } + + void operator=(const array & other) { + shape = other.shape; + stride = other.stride; + _resize(other.sz); + memory::memcpy(values, other.values, sz); + } + + array(array && other) { + sz = other.sz; + shape = other.shape; + values = other.values; + stride = other.stride; + other.values = nullptr; + } + + void operator=(array && other) { + sz = other.sz; + shape = other.shape; + + deallocate(); + values = other.values; + + stride = other.stride; + other.values = nullptr; + } + + ~array() { + deallocate(); + } + + void resize(uint32_t new_size) { + static_assert(dim == 1, "resize(uint32_t) only defined for 1D arrays"); + stride[0] = 1; + shape[0] = new_size; + _resize(new_size); + } + + void resize(const stack::array< uint32_t, dim > & new_shape) { + shape = new_shape; + _resize(product(shape)); + for (uint32_t i = 0; i < dim; i++) { + uint32_t id = dim - 1 - i; + stride[id] = (id == dim - 1) ? 1 : stride[id+1] * shape[id+1]; + } + } + + void resize(const stack::array< uint32_t, dim > & new_shape, + const stack::array< uint32_t, dim > & new_stride) { + shape = new_shape; + stride = new_stride; + _resize(product(shape)); + } + + private: + + void allocate(uint32_t n) { + values = memory::allocate(n); + } + + void deallocate() { + if (values) { + memory::deallocate(values); + values = nullptr; + } + } + + void _resize(uint32_t new_sz) { + if (new_sz != sz) { + deallocate(); + allocate(new_sz); + sz = new_sz; + memory::zero(values, sz); + } + } + + }; + + template < typename T, uint32_t dim > + view(T*, stack::array) -> view; + + template < typename T, uint32_t dim > + view(T*, stack::array, stack::array) -> view; + + ///////////////////////////////////////////////////////////////////////////// + + template < typename T, uint32_t dim > + void zero(array & arr) { + memory::zero(arr.data(), arr.sz); + } + +// template < typename T, uint32_t dim > +// void fill(array & arr, T value) { +// for (uint32_t i = 0; i < arr.size(); i++) { +// arr[i] = value; +// } +// } + + ///////////////////////////////////////////////////////////////////////////// + + template < typename T, uint32_t dim > + SERAC_HOST_DEVICE view flatten(const array & arr) { + return view{&arr.values[0], {product(arr.shape)}}; + } + + template < typename T, uint32_t dim > + SERAC_HOST_DEVICE view flatten(array & arr) { + return view{&arr.values[0], {product(arr.shape)}}; + } + + template < typename T, uint32_t dim > + SERAC_HOST_DEVICE view flatten(view arr) { + return view{arr.values, {product(arr.shape)}}; + } + + ///////////////////////////////////////////////////////////////////////////// + + template < uint32_t dim, typename T > + SERAC_HOST_DEVICE view reshape(view v, stack::array< uint32_t, dim > new_dimensions, ordering o = ordering::row_major) { + #ifdef NDARRAY_ENABLE_BOUNDS_CHECKING + if (product(new_dimensions) != v.shape[0]) { + printf("reshaping view into incompatible shape"); + }; + #endif + + auto strides = nd::compute_strides(new_dimensions, o, v.stride[0]); + + return view{v.data(), new_dimensions, strides}; + } + + ///////////////////////////////////////////////////////////////////////////// + +}; + +double relative_error(nd::view a, nd::view b); +double relative_error(nd::view a, nd::view b); +double relative_error(nd::view a, nd::view b); +double relative_error(nd::view a, nd::view b); + +namespace nd { +template < typename T > +struct printer; + +template <> struct printer{ static SERAC_HOST_DEVICE void print(float x) { printf("%f", static_cast(x)); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(double x) { printf("%f", x); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(int8_t x) { printf("%d", x); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(uint8_t x) { printf("%u", x); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(int32_t x) { printf("%d", x); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(uint32_t x) { printf("%u", x); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(int64_t x) { printf("%lld", x); } }; +template <> struct printer{ static SERAC_HOST_DEVICE void print(uint64_t x) { printf("%llu", x); } }; + +template < typename T, uint32_t dim > +SERAC_HOST_DEVICE void print_recursive(nd::view< T, dim > arr, int depth) { + using S = typename std::remove_const::type; + + if constexpr (dim == 1) { + for (int i = 0; i < depth; i++) printf(" "); + printf("{"); + for (uint32_t i = 0; i < arr.shape[0]; i++) { + printer::print(arr(i)); + if (i != arr.shape[0] - 1) { printf(","); } + } + printf("}"); + } else { + const T * ptr = arr.data(); + stack::array< uint32_t, dim - 1 > shape; + stack::array< uint32_t, dim - 1 > stride; + for (uint32_t i = 0; i < dim - 1; i++) { + shape[i] = arr.shape[i+1]; + stride[i] = arr.stride[i+1]; + } + nd::view slice{ptr, shape, stride}; + + for (int i = 0; i < depth; i++) printf(" "); + printf("{"); + if (arr.shape[0] == 1) { + print_recursive(slice, 0); + } else { + printf("\n"); + for (uint32_t i = 0; i < arr.shape[0]; i++) { + print_recursive(slice, depth+1); + if (i != arr.shape[0] - 1) { printf(","); } + printf("\n"); + slice.values += arr.stride[0]; + } + for (int i = 0; i < depth; i++) printf(" "); + } + printf("}"); + } + if (depth == 0) { printf("\n"); } +} + +} + +template < typename T, uint32_t dim > +SERAC_HOST_DEVICE void print(nd::view< T, dim > arr) { + nd::print_recursive(arr, 0); +} + +template < typename T, uint32_t dim > +std::ostream& operator<<(std::ostream & out, const nd::view< T, dim > & arr) { + print(out, nd::view(arr)); + return out; +} + +template < typename T, uint32_t dim > +std::ostream& operator<<(std::ostream & out, const nd::array< T, dim > & arr) { + print(out, nd::view(arr)); + return out; +} diff --git a/src/serac/numerics/refactor/containers/relative_error.cpp b/src/serac/numerics/refactor/containers/relative_error.cpp new file mode 100644 index 0000000000..3063c9c251 --- /dev/null +++ b/src/serac/numerics/refactor/containers/relative_error.cpp @@ -0,0 +1,26 @@ +#include + +#include "serac/numerics/refactor/containers/ndarray.hpp" + +template < uint32_t rank > +double relative_error_impl(nd::view x, nd::view y) { + if (x.shape != y.shape) { + std::cout << "shape mismatch" << std::endl; + } + + double norm = 0.0; + double error = 0.0; + uint32_t sz = x.size(); + for (uint32_t i = 0; i < sz; i++) { + double avg = 0.5 * (x.values[i] + y.values[i]); + double diff = x.values[i] - y.values[i]; + error += diff * diff; + norm += avg * avg; + } + return sqrt(error / norm); +} + +double relative_error(nd::view a, nd::view b) { return relative_error_impl(a, b); }; +double relative_error(nd::view a, nd::view b) { return relative_error_impl(a, b); }; +double relative_error(nd::view a, nd::view b) { return relative_error_impl(a, b); }; +double relative_error(nd::view a, nd::view b) { return relative_error_impl(a, b); }; diff --git a/src/serac/numerics/refactor/containers/stack_array.hpp b/src/serac/numerics/refactor/containers/stack_array.hpp new file mode 100644 index 0000000000..e53b1e2442 --- /dev/null +++ b/src/serac/numerics/refactor/containers/stack_array.hpp @@ -0,0 +1,42 @@ +#pragma once + +#include + +namespace stack { + + template < typename T, uint32_t dim > + struct array { + SERAC_HOST_DEVICE constexpr T & operator[](uint32_t i) { return values[i]; } + SERAC_HOST_DEVICE constexpr const T & operator[](uint32_t i) const { return values[i]; } + + SERAC_HOST_DEVICE bool operator==(const array & other) const { + for (uint32_t i = 0; i < dim; i++) { + if (values[i] != other[i]) return false; + } + return true; + } + + SERAC_HOST_DEVICE bool operator!=(const array & other) const { return !(this->operator==(other)); } + + T values[dim]; + }; + + template < typename T, uint32_t dim > + constexpr uint32_t size(array) { return dim; } + + template < typename T > + array(T, T) -> array; + + template < typename T > + array(T, T, T) -> array; + + template < typename T > + array(T, T, T, T) -> array; + + template < typename T > + array(T, T, T, T, T) -> array; + + template < typename T > + array(T, T, T, T, T, T) -> array; + +} diff --git a/src/serac/numerics/refactor/containers/tests/CMakeLists.txt b/src/serac/numerics/refactor/containers/tests/CMakeLists.txt new file mode 100644 index 0000000000..18db9725ce --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/CMakeLists.txt @@ -0,0 +1,21 @@ +# Copyright (c) 2019-2024, Lawrence Livermore National Security, LLC and +# other Serac Project Developers. See the top-level LICENSE file for +# details. +# +# SPDX-License-Identifier: (BSD-3-Clause) + +set(refactor_container_test_dependencies serac_refactor gtest) + +set(refactor_container_test_sources + accessor_tests.cpp + ctor_tests.cpp + reshape_tests.cpp + stride_tests.cpp + usage_tests.cpp +) + +# TODO register CUDA tests + +serac_add_tests( SOURCES ${refactor_container_test_sources} + DEPENDS_ON ${refactor_container_test_dependencies} + NUM_MPI_TASKS 1) diff --git a/src/serac/numerics/refactor/containers/tests/accessor_tests.cpp b/src/serac/numerics/refactor/containers/tests/accessor_tests.cpp new file mode 100644 index 0000000000..16546c51fa --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/accessor_tests.cpp @@ -0,0 +1,213 @@ +#include + +#include "common.hpp" + +TEST(UnitTest, BasicAccess) { + + nd::array< double, 2 > arr2D = make_patterned_ndarray(stack::array{7u, 8u}); + EXPECT_EQ(arr2D(0, 0), 00); + EXPECT_EQ(arr2D(1, 0), 10); + EXPECT_EQ(arr2D(2, 1), 21); + EXPECT_EQ(arr2D(4, 2), 42); + EXPECT_EQ(arr2D(6, 7), 67); + + nd::view< double, 2 > view2D = arr2D; + EXPECT_EQ(view2D(0, 0), 00); + EXPECT_EQ(view2D(1, 0), 10); + EXPECT_EQ(view2D(2, 1), 21); + EXPECT_EQ(view2D(4, 2), 42); + EXPECT_EQ(view2D(6, 7), 67); + + nd::array< double, 3 > arr3D = make_patterned_ndarray(stack::array{6u, 7u, 8u}); + EXPECT_EQ(arr3D(0, 0, 0), 000); + EXPECT_EQ(arr3D(1, 3, 0), 130); + EXPECT_EQ(arr3D(2, 0, 2), 202); + EXPECT_EQ(arr3D(3, 1, 7), 317); + EXPECT_EQ(arr3D(5, 6, 7), 567); + + //#ifdef NDARRAY_ENABLE_BOUNDS_CHECKING + // EXPECT_EQ(arr3D(10, 10, 10), 1000); + //#endif + + nd::view< double, 3 > view3D = arr3D; + EXPECT_EQ(view3D(0, 0, 0), 000); + EXPECT_EQ(view3D(1, 3, 0), 130); + EXPECT_EQ(view3D(2, 0, 2), 202); + EXPECT_EQ(view3D(3, 1, 7), 317); + EXPECT_EQ(view3D(5, 6, 7), 567); + +} + + +TEST(UnitTest, ArraySlicing) { + + nd::array< double, 3 > arr3D = make_patterned_ndarray(stack::array{6u, 7u, 8u}); + + double value = arr3D(1, 2, 3); + arr3D(1,2,3) = value; + + nd::view< double, 2 > slice1 = arr3D(nd::range{2,5}, 4); + EXPECT_EQ(slice1.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice1.stride[1], arr3D.stride[2]); + EXPECT_EQ(slice1.shape[0], 3); + EXPECT_EQ(slice1.shape[1], 8); + EXPECT_EQ(slice1(0,0), arr3D(2,4,0)); + EXPECT_EQ(slice1(1,1), arr3D(3,4,1)); + EXPECT_EQ(slice1(2,2), arr3D(4,4,2)); + + nd::view< double, 1 > slice2 = arr3D(1, 2, nd::range{2,5}); + EXPECT_EQ(slice2.stride[0], arr3D.stride[2]); + EXPECT_EQ(slice2.shape[0], 3); + EXPECT_EQ(slice2(0), arr3D(1,2,2)); + EXPECT_EQ(slice2(1), arr3D(1,2,3)); + EXPECT_EQ(slice2(2), arr3D(1,2,4)); + + nd::view< double, 2 > slice3 = arr3D(nd::range{2,5}, nd::range{1,2}, 4); + EXPECT_EQ(slice3.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice3.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice3.shape[0], 3); + EXPECT_EQ(slice3.shape[1], 1); + EXPECT_EQ(slice3(0,0), arr3D(2,1,4)); + EXPECT_EQ(slice3(1,0), arr3D(3,1,4)); + EXPECT_EQ(slice3(2,0), arr3D(4,1,4)); + + nd::view< double, 3 > slice4 = arr3D(nd::range{1, 2}, nd::range{2, 5}, nd::range{1,2}); + EXPECT_EQ(slice4.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice4.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice4.stride[2], arr3D.stride[2]); + EXPECT_EQ(slice4.shape[0], 1); + EXPECT_EQ(slice4.shape[1], 3); + EXPECT_EQ(slice4.shape[2], 1); + EXPECT_EQ(slice4(0,0,0), arr3D(1, 2, 1)); + EXPECT_EQ(slice4(0,1,0), arr3D(1, 3, 1)); + EXPECT_EQ(slice4(0,2,0), arr3D(1, 4, 1)); + +} + +TEST(UnitTest, ConstArraySlicing) { + + const nd::array< double, 3 > arr3D = make_patterned_ndarray(stack::array{6u, 7u, 8u}); + + nd::view< const double, 2 > slice1 = arr3D(nd::range{2,5}, 4); + EXPECT_EQ(slice1.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice1.stride[1], arr3D.stride[2]); + EXPECT_EQ(slice1.shape[0], 3); + EXPECT_EQ(slice1.shape[1], 8); + EXPECT_EQ(slice1(0,0), arr3D(2,4,0)); + EXPECT_EQ(slice1(1,1), arr3D(3,4,1)); + EXPECT_EQ(slice1(2,2), arr3D(4,4,2)); + + nd::view< const double, 1 > slice2 = arr3D(1, 2, nd::range{2,5}); + EXPECT_EQ(slice2.stride[0], arr3D.stride[2]); + EXPECT_EQ(slice2.shape[0], 3); + EXPECT_EQ(slice2(0), arr3D(1,2,2)); + EXPECT_EQ(slice2(1), arr3D(1,2,3)); + EXPECT_EQ(slice2(2), arr3D(1,2,4)); + + nd::view< const double, 2 > slice3 = arr3D(nd::range{2,5}, nd::range{1,2}, 4); + EXPECT_EQ(slice3.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice3.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice3.shape[0], 3); + EXPECT_EQ(slice3.shape[1], 1); + EXPECT_EQ(slice3(0,0), arr3D(2,1,4)); + EXPECT_EQ(slice3(1,0), arr3D(3,1,4)); + EXPECT_EQ(slice3(2,0), arr3D(4,1,4)); + + nd::view< const double, 3 > slice4 = arr3D(nd::range{1, 2}, nd::range{2, 5}, nd::range{1,2}); + EXPECT_EQ(slice4.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice4.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice4.stride[2], arr3D.stride[2]); + EXPECT_EQ(slice4.shape[0], 1); + EXPECT_EQ(slice4.shape[1], 3); + EXPECT_EQ(slice4.shape[2], 1); + EXPECT_EQ(slice4(0,0,0), arr3D(1, 2, 1)); + EXPECT_EQ(slice4(0,1,0), arr3D(1, 3, 1)); + EXPECT_EQ(slice4(0,2,0), arr3D(1, 4, 1)); + +} + +TEST(UnitTest, ViewConstSlicing) { + + const nd::array< double, 3 > arr3D = make_patterned_ndarray(stack::array{6u, 7u, 8u}); + nd::view< const double, 3 > view3D = arr3D; + + nd::view< const double, 2 > slice1 = view3D(nd::range{2,5}, 4); + EXPECT_EQ(slice1.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice1.stride[1], arr3D.stride[2]); + EXPECT_EQ(slice1.shape[0], 3); + EXPECT_EQ(slice1.shape[1], 8); + EXPECT_EQ(slice1(0,0), arr3D(2,4,0)); + EXPECT_EQ(slice1(1,1), arr3D(3,4,1)); + EXPECT_EQ(slice1(2,2), arr3D(4,4,2)); + + nd::view< const double, 1 > slice2 = view3D(1, 2, nd::range{2,5}); + EXPECT_EQ(slice2.stride[0], arr3D.stride[2]); + EXPECT_EQ(slice2.shape[0], 3); + EXPECT_EQ(slice2(0), arr3D(1,2,2)); + EXPECT_EQ(slice2(1), arr3D(1,2,3)); + EXPECT_EQ(slice2(2), arr3D(1,2,4)); + + nd::view< const double, 2 > slice3 = view3D(nd::range{2,5}, nd::range{1,2}, 4); + EXPECT_EQ(slice3.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice3.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice3.shape[0], 3); + EXPECT_EQ(slice3.shape[1], 1); + EXPECT_EQ(slice3(0,0), arr3D(2,1,4)); + EXPECT_EQ(slice3(1,0), arr3D(3,1,4)); + EXPECT_EQ(slice3(2,0), arr3D(4,1,4)); + + nd::view< const double, 3 > slice4 = view3D(nd::range{1, 2}, nd::range{2, 5}, nd::range{1,2}); + EXPECT_EQ(slice4.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice4.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice4.stride[2], arr3D.stride[2]); + EXPECT_EQ(slice4.shape[0], 1); + EXPECT_EQ(slice4.shape[1], 3); + EXPECT_EQ(slice4.shape[2], 1); + EXPECT_EQ(slice4(0,0,0), arr3D(1, 2, 1)); + EXPECT_EQ(slice4(0,1,0), arr3D(1, 3, 1)); + EXPECT_EQ(slice4(0,2,0), arr3D(1, 4, 1)); + +} + +TEST(UnitTest, ConstViewSlicing) { + + nd::array< double, 3 > arr3D = make_patterned_ndarray(stack::array{6u, 7u, 8u}); + const nd::view< double, 3 > view3D = arr3D; + + nd::view< double, 2 > slice1 = view3D(nd::range{2,5}, 4); + EXPECT_EQ(slice1.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice1.stride[1], arr3D.stride[2]); + EXPECT_EQ(slice1.shape[0], 3); + EXPECT_EQ(slice1.shape[1], 8); + EXPECT_EQ(slice1(0,0), arr3D(2,4,0)); + EXPECT_EQ(slice1(1,1), arr3D(3,4,1)); + EXPECT_EQ(slice1(2,2), arr3D(4,4,2)); + + nd::view< double, 1 > slice2 = view3D(1, 2, nd::range{2,5}); + EXPECT_EQ(slice2.stride[0], arr3D.stride[2]); + EXPECT_EQ(slice2.shape[0], 3); + EXPECT_EQ(slice2(0), arr3D(1,2,2)); + EXPECT_EQ(slice2(1), arr3D(1,2,3)); + EXPECT_EQ(slice2(2), arr3D(1,2,4)); + + nd::view< double, 2 > slice3 = view3D(nd::range{2,5}, nd::range{1,2}, 4); + EXPECT_EQ(slice3.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice3.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice3.shape[0], 3); + EXPECT_EQ(slice3.shape[1], 1); + EXPECT_EQ(slice3(0,0), arr3D(2,1,4)); + EXPECT_EQ(slice3(1,0), arr3D(3,1,4)); + EXPECT_EQ(slice3(2,0), arr3D(4,1,4)); + + nd::view< double, 3 > slice4 = view3D(nd::range{1, 2}, nd::range{2, 5}, nd::range{1,2}); + EXPECT_EQ(slice4.stride[0], arr3D.stride[0]); + EXPECT_EQ(slice4.stride[1], arr3D.stride[1]); + EXPECT_EQ(slice4.stride[2], arr3D.stride[2]); + EXPECT_EQ(slice4.shape[0], 1); + EXPECT_EQ(slice4.shape[1], 3); + EXPECT_EQ(slice4.shape[2], 1); + EXPECT_EQ(slice4(0,0,0), arr3D(1, 2, 1)); + EXPECT_EQ(slice4(0,1,0), arr3D(1, 3, 1)); + EXPECT_EQ(slice4(0,2,0), arr3D(1, 4, 1)); + +} \ No newline at end of file diff --git a/src/serac/numerics/refactor/containers/tests/accessor_tests.cu b/src/serac/numerics/refactor/containers/tests/accessor_tests.cu new file mode 100644 index 0000000000..acc08d2f5a --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/accessor_tests.cu @@ -0,0 +1,158 @@ +#include + +#include "common.hpp" + +TEST(UnitTest, BasicAccessOnCPU) { + + nd::array< double, 2 > arr2D = make_patterned_ndarray_on_GPU(stack::array{7u, 8u}); + EXPECT_EQ(arr2D(0, 0), 00); + EXPECT_EQ(arr2D(1, 0), 10); + EXPECT_EQ(arr2D(2, 1), 21); + EXPECT_EQ(arr2D(4, 2), 42); + EXPECT_EQ(arr2D(6, 7), 67); + + nd::view< double, 2 > view2D = arr2D; + EXPECT_EQ(view2D(0, 0), 00); + EXPECT_EQ(view2D(1, 0), 10); + EXPECT_EQ(view2D(2, 1), 21); + EXPECT_EQ(view2D(4, 2), 42); + EXPECT_EQ(view2D(6, 7), 67); + + nd::array< double, 3 > arr3D = make_patterned_ndarray_on_GPU(stack::array{6u, 7u, 8u}); + EXPECT_EQ(arr3D(0, 0, 0), 000); + EXPECT_EQ(arr3D(1, 3, 0), 130); + EXPECT_EQ(arr3D(2, 0, 2), 202); + EXPECT_EQ(arr3D(3, 1, 7), 317); + EXPECT_EQ(arr3D(5, 6, 7), 567); + + //#ifdef NDARRAY_ENABLE_BOUNDS_CHECKING + // EXPECT_EQ(arr3D(10, 10, 10), 1000); + //#endif + + nd::view< double, 3 > view3D = arr3D; + EXPECT_EQ(view3D(0, 0, 0), 000); + EXPECT_EQ(view3D(1, 3, 0), 130); + EXPECT_EQ(view3D(2, 0, 2), 202); + EXPECT_EQ(view3D(3, 1, 7), 317); + EXPECT_EQ(view3D(5, 6, 7), 567); + +} + +__global__ void accessor_kernel(int * num_errors, nd::view v) { + *num_errors += (v(0, 0) != 00); + *num_errors += (v(1, 0) != 10); + *num_errors += (v(2, 1) != 21); + *num_errors += (v(4, 2) != 42); + *num_errors += (v(6, 7) != 67); +} + +__global__ void accessor_kernel(int * num_errors, nd::view v) { + *num_errors += (v(0, 0, 0) != 000); + *num_errors += (v(1, 3, 0) != 130); + *num_errors += (v(2, 0, 2) != 202); + *num_errors += (v(3, 1, 7) != 317); + *num_errors += (v(5, 6, 7) != 567); +} + +TEST(UnitTest, BasicAccessOnGPU) { + int * errors; + cudaMallocManaged(&errors, sizeof(int)); + +//////////////////////////////////////////////////////////////////////////////// + + nd::array< double, 2 > arr2D = make_patterned_ndarray_on_GPU(stack::array{7u, 8u}); + + *errors = 0; + accessor_kernel<<<1,1>>>(errors, arr2D); + cudaDeviceSynchronize(); + EXPECT_EQ(*errors, 0); + +//////////////////////////////////////////////////////////////////////////////// + + nd::array< double, 3 > arr3D = make_patterned_ndarray_on_GPU(stack::array{6u, 7u, 8u}); + + *errors = 0; + accessor_kernel<<<1,1>>>(errors, arr3D); + cudaDeviceSynchronize(); + EXPECT_EQ(*errors, 0); + +//////////////////////////////////////////////////////////////////////////////// + + cudaFree(errors); +} + +template < typename S, typename T > +__global__ void slicing_kernel(int * num_errors, nd::view arr3D) { + + nd::view< S, 2 > slice1 = arr3D(nd::range{2,5}, 4); + *num_errors += (slice1.stride[0] != arr3D.stride[0]); + *num_errors += (slice1.stride[1] != arr3D.stride[2]); + *num_errors += (slice1.shape[0] != 3); + *num_errors += (slice1.shape[1] != 8); + *num_errors += (slice1(0,0) != arr3D(2,4,0)); + *num_errors += (slice1(1,1) != arr3D(3,4,1)); + *num_errors += (slice1(2,2) != arr3D(4,4,2)); + + nd::view< S, 1 > slice2 = arr3D(1, 2, nd::range{2,5}); + *num_errors += (slice2.stride[0] != arr3D.stride[2]); + *num_errors += (slice2.shape[0] != 3); + *num_errors += (slice2(0) != arr3D(1,2,2)); + *num_errors += (slice2(1) != arr3D(1,2,3)); + *num_errors += (slice2(2) != arr3D(1,2,4)); + + nd::view< S, 2 > slice3 = arr3D(nd::range{2,5}, nd::range{1,2}, 4); + *num_errors += (slice3.stride[0] != arr3D.stride[0]); + *num_errors += (slice3.stride[1] != arr3D.stride[1]); + *num_errors += (slice3.shape[0] != 3); + *num_errors += (slice3.shape[1] != 1); + *num_errors += (slice3(0,0) != arr3D(2,1,4)); + *num_errors += (slice3(1,0) != arr3D(3,1,4)); + *num_errors += (slice3(2,0) != arr3D(4,1,4)); + + nd::view< S, 3 > slice4 = arr3D(nd::range{1, 2}, nd::range{2, 5}, nd::range{1,2}); + *num_errors += (slice4.stride[0] != arr3D.stride[0]); + *num_errors += (slice4.stride[1] != arr3D.stride[1]); + *num_errors += (slice4.stride[2] != arr3D.stride[2]); + *num_errors += (slice4.shape[0] != 1); + *num_errors += (slice4.shape[1] != 3); + *num_errors += (slice4.shape[2] != 1); + *num_errors += (slice4(0,0,0) != arr3D(1, 2, 1)); + *num_errors += (slice4(0,1,0) != arr3D(1, 3, 1)); + *num_errors += (slice4(0,2,0) != arr3D(1, 4, 1)); +} + +TEST(UnitTest, ArraySlicingOnGPU) { + int * errors; + cudaMallocManaged(&errors, sizeof(int)); + +//////////////////////////////////////////////////////////////////////////////// + + nd::array< double, 3 > arr3D = make_patterned_ndarray_on_GPU(stack::array{6u, 7u, 8u}); + + *errors = 0; + slicing_kernel<<<1,1>>>(errors, arr3D); + cudaDeviceSynchronize(); + EXPECT_EQ(*errors, 0); + +//////////////////////////////////////////////////////////////////////////////// + + cudaFree(errors); +} + +TEST(UnitTest, ConstArraySlicingOnGPU) { + int * errors; + cudaMallocManaged(&errors, sizeof(int)); + +//////////////////////////////////////////////////////////////////////////////// + + nd::array< double, 3 > arr3D = make_patterned_ndarray_on_GPU(stack::array{6u, 7u, 8u}); + + *errors = 0; + slicing_kernel<<<1,1>>>(errors, arr3D); + cudaDeviceSynchronize(); + EXPECT_EQ(*errors, 0); + +//////////////////////////////////////////////////////////////////////////////// + + cudaFree(errors); +} diff --git a/src/serac/numerics/refactor/containers/tests/common.hpp b/src/serac/numerics/refactor/containers/tests/common.hpp new file mode 100644 index 0000000000..9697763921 --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/common.hpp @@ -0,0 +1,69 @@ +#pragma once + +#include "serac/numerics/refactor/containers/ndarray.hpp" + +#ifdef __CUDACC__ +// dimension should each be less than 10 +template < uint32_t rank > +__global__ void patterned_ndarray_kernel(nd::view output, stack::array dimensions) { + uint32_t i = threadIdx.x + blockIdx.x * blockDim.x; + if (i < dimensions[0]) { + if constexpr (rank > 1) { + for (int j = 0; j < dimensions[1]; j++) { + if constexpr (rank > 2) { + for (int k = 0; k < dimensions[2]; k++) { + output(i, j, k) = 100 * i + 10 * j + k; + } + } else { + output(i, j) = 10 * i + j; + } + } + } else { + output(i) = i; + } + } +} + +template < uint32_t rank > +nd::array make_patterned_ndarray_on_GPU(stack::array dimensions) { + static_assert(rank <= 3); + + nd::array output({dimensions}); + nd::view v = output; + + uint32_t blocksize = 64; + uint32_t gridsize = (dimensions[0] + blocksize - 1) / blocksize; + patterned_ndarray_kernel<<>>(v, dimensions); + cudaDeviceSynchronize(); + + return output; +} +#endif + +// dimension should each be less than 10 +template < uint32_t rank > +nd::array make_patterned_ndarray(stack::array dimensions) { + + static_assert(rank <= 3); + + nd::array output({dimensions}); + + for (int i = 0; i < dimensions[0]; i++) { + if constexpr (rank > 1) { + for (int j = 0; j < dimensions[1]; j++) { + if constexpr (rank > 2) { + for (int k = 0; k < dimensions[2]; k++) { + output(i, j, k) = 100 * i + 10 * j + k; + } + } else { + output(i, j) = 10 * i + j; + } + } + } else { + output(i) = i; + } + } + + return output; + +} diff --git a/src/serac/numerics/refactor/containers/tests/ctor_tests.cpp b/src/serac/numerics/refactor/containers/tests/ctor_tests.cpp new file mode 100644 index 0000000000..6197b4e1fe --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/ctor_tests.cpp @@ -0,0 +1,59 @@ +#include + +#include "common.hpp" + +TEST(UnitTest, DefaultCtor2D) { + nd::array< double, 2 > arr2D; +} + +TEST(UnitTest, DefaultCtor3D) { + nd::array< double, 3 > arr3D; +} + +TEST(UnitTest, CopyCtor2D) { + nd::array< double, 2 > arr2D({3, 4}); + nd::array< double, 2 > copy2D = arr2D; +} + +TEST(UnitTest, CopyCtor3D) { + nd::array< double, 3 > arr3D({2, 3, 4}); + nd::array< double, 3 > copy3D = arr3D; +} + +TEST(UnitTest, MoveCtor2D) { + nd::array< double, 2 > arr2D({3, 4}); + nd::array< double, 2 > copy2D = std::move(arr2D); + EXPECT_EQ(arr2D.data(), nullptr); +} + +TEST(UnitTest, MoveCtor3D) { + nd::array< double, 3 > arr3D({2, 3, 4}); + nd::array< double, 3 > copy3D = std::move(arr3D); + EXPECT_EQ(arr3D.data(), nullptr); +} + +TEST(UnitTest, CopyAssignmentCtor2D) { + nd::array< double, 2 > arr2D({3, 4}); + nd::array< double, 2 > copy2D; + copy2D = arr2D; +} + +TEST(UnitTest, CopyAssignmentCtor3D) { + nd::array< double, 3 > arr3D({2, 3, 4}); + nd::array< double, 3 > copy3D; + copy3D = arr3D; +} + +TEST(UnitTest, MoveAssignmentCtor2D) { + nd::array< double, 2 > arr2D({3, 4}); + nd::array< double, 2 > copy2D; + copy2D = std::move(arr2D); + EXPECT_EQ(arr2D.data(), nullptr); +} + +TEST(UnitTest, MoveAssignmentCtor3D) { + nd::array< double, 3 > arr3D({2, 3, 4}); + nd::array< double, 3 > copy3D; + copy3D = std::move(arr3D); + EXPECT_EQ(arr3D.data(), nullptr); +} diff --git a/src/serac/numerics/refactor/containers/tests/reshape_tests.cpp b/src/serac/numerics/refactor/containers/tests/reshape_tests.cpp new file mode 100644 index 0000000000..482fbee040 --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/reshape_tests.cpp @@ -0,0 +1,53 @@ +#include + +#include "common.hpp" + +TEST(UnitTest, Flattening2D) { + nd::array< double, 2 > arr2D = make_patterned_ndarray(stack::array{7u, 8u}); + nd::view< double > view1D = flatten(arr2D); + EXPECT_EQ(view1D(0), 0); + EXPECT_EQ(view1D(10), 12); + EXPECT_EQ(view1D(24), 30); +} + +TEST(UnitTest, Flattening3D) { + nd::array< double, 3 > arr3D = make_patterned_ndarray(stack::array{6u, 7u, 8u}); + nd::view< double > view1D = flatten(arr3D); + EXPECT_EQ(view1D(0), 0); + EXPECT_EQ(view1D(10), 12); + EXPECT_EQ(view1D(24), 30); + EXPECT_EQ(view1D(57), 101); +} + +TEST(UnitTest, Reshape) { + + nd::array< double, 2 > arr2D = make_patterned_ndarray(stack::array{8u, 3u}); + + // select column 1 from 2D array + // { + // { 0, ( 1), 2}, + // {10, (11), 12}, + // {20, (21), 22}, + // {30, (31), 32}, + // {40, (41), 42}, + // {50, (51), 52}, + // {60, (61), 62}, + // {70, (71), 72} + // } + nd::view< double > view1D = arr2D(nd::range{0,8}, 1); + EXPECT_EQ(view1D(0), 1); + EXPECT_EQ(view1D(1), 11); + EXPECT_EQ(view1D(2), 21); + + nd::view< double, 3 > view3D = nd::reshape<3>(view1D, {2,2,2}); + EXPECT_EQ(view3D(0, 0, 0), 1); + EXPECT_EQ(view3D(1, 1, 0), 61); + EXPECT_EQ(view3D(1, 0, 1), 51); + EXPECT_EQ(view3D(0, 1, 0), 21); + + view3D = nd::reshape<3>(view1D, {2,2,2}, nd::ordering::col_major); + EXPECT_EQ(view3D(0, 0, 0), 1); + EXPECT_EQ(view3D(0, 1, 1), 61); + EXPECT_EQ(view3D(1, 0, 1), 51); + EXPECT_EQ(view3D(0, 1, 0), 21); +} \ No newline at end of file diff --git a/src/serac/numerics/refactor/containers/tests/stride_tests.cpp b/src/serac/numerics/refactor/containers/tests/stride_tests.cpp new file mode 100644 index 0000000000..b11f5ed00c --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/stride_tests.cpp @@ -0,0 +1,51 @@ +#include + +#include "common.hpp" + +TEST(UnitTest, StridesColumnMajor2D) { + stack::array< uint32_t, 2 > shape = {4, 6}; + stack::array< uint32_t, 2 > strides = nd::compute_strides(shape, nd::ordering::col_major); + EXPECT_EQ(strides[0], 1); + EXPECT_EQ(strides[1], 4); + + strides = nd::compute_strides(shape, nd::ordering::col_major, 4); + EXPECT_EQ(strides[0], 4); + EXPECT_EQ(strides[1], 16); +} + +TEST(UnitTest, StridesColumnMajor3D) { + stack::array< uint32_t, 3 > shape = {4, 6, 7}; + stack::array< uint32_t, 3 > strides = nd::compute_strides(shape, nd::ordering::col_major); + EXPECT_EQ(strides[0], 1); + EXPECT_EQ(strides[1], 4); + EXPECT_EQ(strides[2], 24); + + strides = nd::compute_strides(shape, nd::ordering::col_major, 4); + EXPECT_EQ(strides[0], 4); + EXPECT_EQ(strides[1], 16); + EXPECT_EQ(strides[2], 96); +} + +TEST(UnitTest, StridesRowMajor2D) { + stack::array< uint32_t, 2 > shape = {4, 6}; + stack::array< uint32_t, 2 > strides = nd::compute_strides(shape, nd::ordering::row_major); + EXPECT_EQ(strides[0], 6); + EXPECT_EQ(strides[1], 1); + + strides = nd::compute_strides(shape, nd::ordering::row_major, 4); + EXPECT_EQ(strides[0], 24); + EXPECT_EQ(strides[1], 4); +} + +TEST(UnitTest, StridesRowMajor3D) { + stack::array< uint32_t, 3 > shape = {4, 6, 7}; + stack::array< uint32_t, 3 > strides = nd::compute_strides(shape, nd::ordering::row_major); + EXPECT_EQ(strides[0], 42); + EXPECT_EQ(strides[1], 7); + EXPECT_EQ(strides[2], 1); + + strides = nd::compute_strides(shape, nd::ordering::row_major, 4); + EXPECT_EQ(strides[0], 168); + EXPECT_EQ(strides[1], 28); + EXPECT_EQ(strides[2], 4); +} \ No newline at end of file diff --git a/src/serac/numerics/refactor/containers/tests/usage_tests.cpp b/src/serac/numerics/refactor/containers/tests/usage_tests.cpp new file mode 100644 index 0000000000..6cb9a2bdb3 --- /dev/null +++ b/src/serac/numerics/refactor/containers/tests/usage_tests.cpp @@ -0,0 +1,54 @@ +#include + +#include "common.hpp" + +void accepts_const_ndarray(const nd::array< double, 2 > & arr) {} + +void accepts_ndarray(nd::array< double, 2 > & arr) { + accepts_const_ndarray(arr); +} + +void accepts_ndview(nd::view< double, 2 > arr) {} + +void accepts_const_ndview(nd::view< const double, 2 > arr) {} + +void accepts_1dview(nd::view< double, 1 > arr) {} + +void operator*(nd::view arr, double scale) {} + +nd::array returns_ndarray() { + return nd::array{{1, 2}}; +} + +TEST(UnitTest, foo) { + + nd::array arr = returns_ndarray(); + nd::view arr_view = arr; + + accepts_ndarray(arr); + + // nd::array can implicitly convert to nd::view, but not vice versa + // accepts_ndarray(arr_view); + + accepts_ndview(arr); + accepts_ndview(arr_view); + + // implicit conversion of `nd::array &&` to `nd::view` + // is disallowed, since it would create a dangling reference + #if 0 + accepts_ndview(returns_ndarray()); + #endif + + // nd::array and nd::view can both + // implicitly convert to nd::view + accepts_const_ndview(arr); + accepts_const_ndview(arr_view); + + // nd::view conversions and transformations can be concatenated + accepts_1dview(flatten(arr)); + accepts_1dview(flatten(arr_view)); + + // implicit conversion on operator overloads + arr * 3.0; + +} diff --git a/src/serac/numerics/refactor/elements/h1_edge.hpp b/src/serac/numerics/refactor/elements/h1_edge.hpp new file mode 100644 index 0000000000..685756dd83 --- /dev/null +++ b/src/serac/numerics/refactor/elements/h1_edge.hpp @@ -0,0 +1,190 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" +#include "serac/numerics/refactor/interpolation.hpp" + +namespace refactor { + +using namespace serac; + +template <> +struct FiniteElement < mfem::Geometry::SEGMENT, Family::H1 >{ + + using source_type = vec1; + using flux_type = vec1; + + using value_type = vec1; + using grad_type = vec1; + + SERAC_HOST_DEVICE constexpr uint32_t num_nodes() const { return p + 1; } + + constexpr double shape_function(vec1 xi, uint32_t i) const { + if (p == 1 && i == 0) { return 1.0 - xi[0]; } + if (p == 1 && i == 1) { return xi[0]; } + + if (p == 2 && i == 0) { return (-1.0 + xi[0]) * (-1.0 + 2.0 * xi[0]); } + if (p == 2 && i == 1) { return -4.0 * (-1.0 + xi[0]) * xi[0]; } + if (p == 2 && i == 2) { return xi[0] * (-1.0 + 2.0 * xi[0]); } + + constexpr double sqrt5 = 2.23606797749978981; + if (p == 3 && i == 0) { return -(-1.0 + xi[0]) * (1.0 + 5.0 * (-1.0 + xi[0]) * xi[0]); } + if (p == 3 && i == 1) { return -0.5 * sqrt5 * (5.0 + sqrt5 - 10.0 * xi[0]) * (-1.0 + xi[0]) * xi[0]; } + if (p == 3 && i == 2) { return -0.5 * sqrt5 * (-1.0 + xi[0]) * xi[0] * (-5.0 + sqrt5 + 10.0 * xi[0]); } + if (p == 3 && i == 3) { return xi[0] * (1.0 + 5.0 * (-1.0 + xi[0]) * xi[0]); } + + return 7777.77; + } + + constexpr vec1 shape_function_gradient(vec1 xi, uint32_t i) const { + if (p == 1 && i == 0) { return -1.0; } + if (p == 1 && i == 1) { return +1.0; } + + if (p == 2 && i == 0) return -3.0 + 4.0 * xi[0]; + if (p == 2 && i == 1) return 4.0 - 8.0 * xi[0]; + if (p == 2 && i == 2) return -1.0 + 4.0 * xi[0]; + + constexpr double sqrt5 = 2.23606797749978981; + if (p == 3 && i == 0) return -6.0 + 5.0 * (4.0 - 3.0 * xi[0]) * xi[0]; + if (p == 3 && i == 1) return 2.5 * (1.0 + sqrt5 + 2.0 * xi[0] * (-1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * xi[0])); + if (p == 3 && i == 2) return -2.5 * (-1.0 + sqrt5 + 2.0 * xi[0] * (1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * xi[0])); + if (p == 3 && i == 3) return 1.0 + 5.0 * xi[0] * (-2.0 + 3.0 * xi[0]); + + return 7777.77; + } + + vec1 shape_function_derivative(vec1 xi, uint32_t i) const { + return shape_function_gradient(xi, i); + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space([[maybe_unused]] nd::view xi) const { + return 0; + } + + nd::array< double, 2 > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p + 1, &shape_fns(i, 0)); + } + return shape_fns; + } + + nd::array< double, 2 > evaluate_shape_function_gradients(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationDerivative(xi(i, 0), p + 1, &shape_fn_grads(i, 0)); + } + return shape_fn_grads; + } + + SERAC_HOST_DEVICE void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + double sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum += shape_fns(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + SERAC_HOST_DEVICE void gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = gradients_q.shape[0]; + for (uint32_t j = 0; j < nqpts; j++) { + double sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum += values_e(i) * shape_fn_grads(j, i); + } + gradients_q(j) = sum; + } + } + + nd::array< double, 2 > evaluate_weighted_shape_functions(nd::view xi, + nd::view weights) const { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, nnodes}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &shape_fns(i, 0)); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fns(i, j) = shape_fns(i, j) * weights(i); + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn(q, i) * source_q(q); + } + residual_e(i) = sum; + } + } + + nd::array< double, 2 > evaluate_weighted_shape_function_gradients(nd::view xi, + nd::view weights) const { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationDerivative(xi(i, 0), p + 1, &shape_fn_grads(i, 0)); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fn_grads(i, j) = shape_fn_grads(i, j) * weights(i); + } + } + return shape_fn_grads; + } + + SERAC_HOST_DEVICE void integrate_flux(nd::view output_e, nd::view flux_q, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn_grads(q, i) * flux_q(q); + } + output_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = gradients_q.shape[0]; + for (int j = threadIdx.x; j < nqpts; j += blockDim.x) { + double sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum += values_e(i) * shape_fn_grads(j, i); + } + gradients_q(j) = sum; + } + } + + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn_grads(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + #endif + + uint32_t p; + +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/h1_hexahedron.hpp b/src/serac/numerics/refactor/elements/h1_hexahedron.hpp new file mode 100644 index 0000000000..217b93985d --- /dev/null +++ b/src/serac/numerics/refactor/elements/h1_hexahedron.hpp @@ -0,0 +1,330 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" +#include "serac/numerics/refactor/interpolation.hpp" + +namespace refactor { + +template <> +struct FiniteElement { + + using value_type = vec1; + using derivative_type = vec3; + + using source_type = vec1; + using flux_type = vec3; + + SERAC_HOST_DEVICE constexpr uint32_t num_nodes() const { return (p + 1) * (p + 1) * (p + 1); } + + constexpr double phi_1D(double xi, uint32_t i) const { + return GaussLobattoInterpolation(xi, p + 1, i); + } + + constexpr double dphi_1D(double xi, uint32_t i) const { + return GaussLobattoInterpolationDerivative(xi, p + 1, i); + } + + constexpr double shape_function(vec3 xi, uint32_t i) const { + uint32_t ix = i % (p + 1); + uint32_t iy = (i % ((p + 1) * (p + 1))) / (p + 1) ; + uint32_t iz = i / ((p + 1) * (p + 1)); + return phi_1D(xi[0], ix) * phi_1D(xi[1], iy) * phi_1D(xi[2], iz); + } + + constexpr vec3 shape_function_gradient(vec3 xi, uint32_t i) const { + uint32_t ix = i % (p + 1); + uint32_t iy = (i % ((p + 1) * (p + 1))) / (p + 1) ; + uint32_t iz = i / ((p + 1) * (p + 1)); + return { + dphi_1D(xi[0], ix) * phi_1D(xi[1], iy) * phi_1D(xi[2], iz), + phi_1D(xi[0], ix) * dphi_1D(xi[1], iy) * phi_1D(xi[2], iz), + phi_1D(xi[0], ix) * phi_1D(xi[1], iy) * dphi_1D(xi[2], iz) + }; + } + + vec3 shape_function_derivative(vec3 xi, uint32_t i) const { + return shape_function_gradient(xi, i); + } + + double interpolate(vec3 xi, double * values) const { + uint32_t count = 0; + double output = 0.0; + for (uint32_t iz = 0; iz < (p+1); iz++) { + double phi_z = phi_1D(xi[2], iz); + for (uint32_t iy = 0; iy < (p+1); iy++) { + double phi_y = phi_1D(xi[1], iy); + for (uint32_t ix = 0; ix < (p+1); ix++) { + double phi_x = phi_1D(xi[0], ix); + output += phi_x * phi_y * phi_z * values[count]; + count++; + } + } + } + return output; + } + + vec3 gradient(vec3 xi, double * values) const { + vec3 output{}; + uint32_t count = 0; + for (uint32_t iz = 0; iz < (p+1); iz++) { + double phi_z = phi_1D(xi[2], iz); + double dphi_z = dphi_1D(xi[2], iz); + for (uint32_t iy = 0; iy < (p+1); iy++) { + double phi_y = phi_1D(xi[1], iy); + double dphi_y = dphi_1D(xi[1], iy); + for (uint32_t ix = 0; ix < (p+1); ix++) { + double phi_x = phi_1D(xi[0], ix); + double dphi_x = dphi_1D(xi[0], ix); + output[0] += dphi_x * phi_y * phi_z * values[count]; + output[1] += phi_x * dphi_y * phi_z * values[count]; + output[2] += phi_x * phi_y * dphi_z * values[count]; + count++; + } + } + } + return output; + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view xi) const { + uint32_t n = p + 1; + uint32_t q = xi.shape[0]; + return q * n * (n + q); + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 3 > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array buffer({1, q, p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &buffer(0, i, 0)); + } + return buffer; + } + + SERAC_HOST_DEVICE void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[1]; + + nd::view phi(&shape_fns(0,0,0), {q, n}); + nd::view A1(buffer, {q, n, n}); + nd::view A2(buffer + q * n * n, {q, q, n}); + + nd::view values_e_3D = nd::reshape<3>(values_e, {n, n, n}); + nd::view values_q_3D(static_cast(&values_q[0][0]), {q, q, q}); + contract(values_e_3D, phi, A1); + contract( A1, phi, A2); + contract( A2, phi, values_q_3D); + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 3 > evaluate_shape_function_gradients(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({2, q, p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &shape_fn_grads(0, i, 0)); + GaussLobattoInterpolationDerivative(xi(i, 0), p+1, &shape_fn_grads(1, i, 0)); + } + return shape_fn_grads; + } + + SERAC_HOST_DEVICE void gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[1]; + + nd::view B(&shape_fns(0,0,0), {q, n}); + nd::view G(&shape_fns(1,0,0), {q, n}); + nd::view A1(buffer, {q, n, n}); + nd::view A2(buffer + q * n * n, {q, q, n}); + + nd::view values_e_3D = nd::reshape<3>(values_e, {n, n, n}); + nd::view gradients_q_3D(static_cast(&gradients_q[0][0]), {q, q, q}, {3*q*q, 3*q, 3}); + + // du_dxi + contract(values_e_3D, G, A1); + contract( A1, B, A2); + contract( A2, B, gradients_q_3D); + gradients_q_3D.values++; + + // du_deta + contract(values_e_3D, B, A1); + contract( A1, G, A2); + contract( A2, B, gradients_q_3D); + gradients_q_3D.values++; + + // du_dzeta + contract(A1, B, A2); + contract(A2, G, gradients_q_3D); + gradients_q_3D.values++; + + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 2 > evaluate_weighted_shape_functions(nd::view xi, + nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array buffer({p+1, q}); + nd::array tmp({p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &tmp(0)); + for (uint32_t j = 0; j < p+1; j++) { + buffer(j, i) = tmp(j) * weights(i); + } + } + return buffer; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fn.shape[1]; + + nd::view BT = shape_fn; + nd::view A1(buffer, {n, q, q}); + nd::view A2(buffer + n*q*q, {n, n, q}); + + nd::view s3D(static_cast(&source_q[0][0]), {q, q, q}); + nd::view r3D = nd::reshape<3>(residual_e, {n, n, n}); + + // r(iz, iy, ix) = s(qz, qy, qx) * BT(ix, qx) * BT(iy, qy) * BT(iz, qz) + // + // A1(ix, qz, qy) = BT(ix, qx) * s(qz, qy, qx) + // A2(iy, ix, qz) = BT(iy, qy) * A1(ix, qz, qy) + // r(iz, iy, ix) = BT(iz, qz) * A2(iy, ix, qz) + contract(s3D, BT, A1); + contract( A1, BT, A2); + contract( A2, BT, r3D); + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 3 > evaluate_weighted_shape_function_gradients(nd::view xi, + nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array buffer({2, p+1, q}); + nd::array tmp({p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &tmp(0)); + for (uint32_t j = 0; j < p+1; j++) { + buffer(0, j, i) = tmp(j) * weights(i); + } + + GaussLobattoInterpolationDerivative(xi(i, 0), p+1, &tmp(0)); + for (uint32_t j = 0; j < p+1; j++) { + buffer(1, j, i) = tmp(j) * weights(i); + } + } + return buffer; + } + + void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[2]; + + nd::view BT = shape_fns(0); + nd::view GT = shape_fns(1); + nd::view A1(buffer, {n, q, q}); + nd::view A2(buffer+n*q*q, {n, n, q}); + + uint32_t s = flux_q.stride[0] * 3; + nd::view f3D(nullptr, {q, q, q}, {s*q*q, s*q, s}); + nd::view r3D = nd::reshape<3>(residual_e, {n, n, n}); + + f3D.values = &flux_q(0)[0]; + contract(f3D, GT, A1); + contract( A1, BT, A2); + contract( A2, BT, r3D, /* accumulate = */ false); + + f3D.values = &flux_q(0)[1]; + contract(f3D, BT, A1); + contract( A1, GT, A2); + contract( A2, BT, r3D, /* accumulate = */ true); + + f3D.values = &flux_q(0)[2]; + contract(f3D, BT, A1); + contract( A1, BT, A2); + contract( A2, GT, r3D, /* accumulate = */ true); + } + + #ifdef __CUDACC__ + __device__ void cuda_gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[1]; + + nd::view B(&shape_fns(0,0,0), {q, n}); + nd::view G(&shape_fns(1,0,0), {q, n}); + nd::view A1(buffer, {q, n, n}); + nd::view A2(buffer + q * n * n, {q, q, n}); + + nd::range All{0u, gradients_q.shape[0]}; + + nd::view values_e_3D = nd::reshape<3>(values_e, {n, n, n}); + nd::view gradients_q_3D((double*)&gradients_q[0], {q, q, q}, {3*q*q, 3*q, 3}); + + threadid tid; + tid.x = threadIdx.x % q; + tid.y = (threadIdx.x % (q * q)) / q; + tid.z = threadIdx.x / (q * q); + tid.stride = q; + + // du_dxi + cuda_contract(tid, values_e_3D, G, A1); + cuda_contract(tid, A1, B, A2); + cuda_contract(tid, A2, B, gradients_q_3D); + gradients_q_3D.values++; + + // du_deta + cuda_contract(tid, values_e_3D, B, A1); + cuda_contract(tid, A1, G, A2); + cuda_contract(tid, A2, B, gradients_q_3D); + gradients_q_3D.values++; + + // du_dzeta + cuda_contract(tid, A1, B, A2); + cuda_contract(tid, A2, G, gradients_q_3D); + gradients_q_3D.values++; + + } + + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[2]; + + nd::view BT = shape_fns(0); + nd::view GT = shape_fns(1); + nd::view A1(buffer, {n, q, q}); + nd::view A2(buffer+n*q*q, {n, n, q}); + + uint32_t s = flux_q.stride[0] * 3; + nd::view f3D(nullptr, {q, q, q}, {s*q*q, s*q, s}); + nd::view r3D = nd::reshape<3>(residual_e, {n, n, n}); + + threadid tid; + tid.x = threadIdx.x % n; + tid.y = (threadIdx.x % (n * n)) / n; + tid.z = threadIdx.x / (n * n); + tid.stride = n; + + f3D.values = &flux_q(0)[0]; + cuda_contract(tid, f3D, GT, A1); + cuda_contract(tid, A1, BT, A2); + cuda_contract(tid, A2, BT, r3D, /* accumulate = */ false); + + f3D.values = &flux_q(0)[1]; + cuda_contract(tid, f3D, BT, A1); + cuda_contract(tid, A1, GT, A2); + cuda_contract(tid, A2, BT, r3D, /* accumulate = */ true); + + f3D.values = &flux_q(0)[2]; + cuda_contract(tid, f3D, BT, A1); + cuda_contract(tid, A1, BT, A2); + cuda_contract(tid, A2, GT, r3D, /* accumulate = */ true); + } + #endif + + uint32_t p; + +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/h1_quadrilateral.hpp b/src/serac/numerics/refactor/elements/h1_quadrilateral.hpp new file mode 100644 index 0000000000..2f26c27494 --- /dev/null +++ b/src/serac/numerics/refactor/elements/h1_quadrilateral.hpp @@ -0,0 +1,295 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" +#include "serac/numerics/refactor/elements/tensor_contractions.hpp" + +namespace refactor { + +template <> +struct FiniteElement< mfem::Geometry::SQUARE, Family::H1 > { + + using source_type = vec1; + using flux_type = vec2; + + using value_type = vec1; + using grad_type = vec2; + + SERAC_HOST_DEVICE constexpr uint32_t num_nodes() const { return (p + 1) * (p + 1); } + + constexpr double phi_1D(double xi, uint32_t i) const { + return GaussLobattoInterpolation(xi, p + 1, i); + } + + constexpr double dphi_1D(double xi, uint32_t i) const { + return GaussLobattoInterpolationDerivative(xi, p + 1, i); + } + + constexpr double shape_function(vec2 xi, uint32_t i) const { + uint32_t ix = i % (p + 1); + uint32_t iy = i / (p + 1); + return phi_1D(xi[0], ix) * phi_1D(xi[1], iy); + } + + vec2 shape_function_gradient(vec2 xi, uint32_t i) const { + uint32_t ix = i % (p + 1); + uint32_t iy = i / (p + 1); + return { + dphi_1D(xi[0], ix) * phi_1D(xi[1], iy), + phi_1D(xi[0], ix) * dphi_1D(xi[1], iy) + }; + } + + vec2 shape_function_derivative(vec2 xi, uint32_t i) const { + return shape_function_gradient(xi, i); + } + + double interpolate(vec2 xi, double * values) const { + double phi[4]; + GaussLobattoInterpolation(xi[0], p+1, phi); + + double interpolated_in_xi[4]{}; + for (uint32_t i = 0; i < (p+1); i++) { + for (uint32_t j = 0; j < (p+1); j++) { + interpolated_in_xi[i] += phi[j] * values[i*(p+1)+j]; + } + } + + GaussLobattoInterpolation(xi[1], p+1, phi); + double result{}; + for (uint32_t i = 0; i < (p+1); i++) { + result += phi[i] * interpolated_in_xi[i]; + } + return result; + } + + vec2 gradient(vec2 xi, double * values) const { + vec2 output{}; + + double phi[4]; + double partially_interpolated[4]{}; + + GaussLobattoInterpolationDerivative(xi[0], p+1, phi); + for (uint32_t i = 0; i < (p+1); i++) { + for (uint32_t j = 0; j < (p+1); j++) { + partially_interpolated[i] += phi[j] * values[i*(p+1)+j]; + } + } + + GaussLobattoInterpolation(xi[1], p+1, phi); + for (uint32_t i = 0; i < (p+1); i++) { + output[0] += phi[i] * partially_interpolated[i]; + } + + //-------------------------------------------------- + + GaussLobattoInterpolation(xi[0], p+1, phi); + for (uint32_t i = 0; i < (p+1); i++) { + for (uint32_t j = 0; j < (p+1); j++) { + partially_interpolated[i] += phi[j] * values[i*(p+1)+j]; + } + } + + GaussLobattoInterpolationDerivative(xi[1], p+1, phi); + for (uint32_t i = 0; i < (p+1); i++) { + output[1] += phi[i] * partially_interpolated[i]; + } + + return output; + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view xi) const { + uint32_t q = xi.shape[0]; + return q * (p + 1); + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 2 > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p + 1, &shape_fns(i, 0)); + } + return shape_fns; + } + + void interpolate(nd::view< value_type > values_q, nd::view values_e, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[0]; + + nd::view A(buffer, {n, q}); + + nd::view values_e_2D = nd::reshape<2>(values_e, {n, n}); + nd::view values_q_2D(static_cast(&values_q[0].data), {q, q}, {1, q}); + contract<1>(values_e_2D, shape_fns, A); + contract<0>(A, shape_fns, values_q_2D); + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 3 > evaluate_shape_function_gradients(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({2, q, p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i,0), p+1, &shape_fn_grads(0, i, 0)); + GaussLobattoInterpolationDerivative(xi(i,0), p+1, &shape_fn_grads(1, i, 0)); + } + return shape_fn_grads; + } + + void gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[1]; + + nd::view B = shape_fns(0); + nd::view G = shape_fns(1); + nd::view A(buffer, {n, q}); + + nd::view values_e_2D = nd::reshape<2>(values_e, {n, n}); + nd::view gradients_q_2D(static_cast(&gradients_q[0][0]), {q, q}, {2, 2*q}); + + // du_dxi + contract<1>(values_e_2D, G, A); + contract<0>( A, B, gradients_q_2D); + gradients_q_2D.values++; + + // du_deta + contract<1>(values_e_2D, B, A); + contract<0>( A, G, gradients_q_2D); + gradients_q_2D.values++; + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 2 > evaluate_weighted_shape_functions(nd::view xi, + nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array buffer({p+1, q}); + nd::array tmp({p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &tmp(0)); + for (uint32_t j = 0; j < p+1; j++) { + buffer(j, i) = tmp(j) * weights(i); + } + } + return buffer; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[1]; + + nd::view BT = shape_fns; + nd::view A(buffer, {q, n}); + + nd::view s2D(static_cast(&source_q[0][0]), {q, q}, {1, q}); + nd::view r2D = nd::reshape<2>(residual_e, {n, n}); + + contract<1>(s2D, BT, A); + contract<0>(A, BT, r2D); + } + + // note: the return value here includes the shape function evaluations as well as + // a buffer space to hold intermediate values in the `interpolation` function + nd::array< double, 3 > evaluate_weighted_shape_function_gradients(nd::view xi, + nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array buffer({2, p+1, q}); + nd::array tmp({p+1}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolation(xi(i, 0), p+1, &tmp(0)); + for (uint32_t j = 0; j < p+1; j++) { + buffer(0, j, i) = tmp(j) * weights(i); + } + + GaussLobattoInterpolationDerivative(xi(i, 0), p+1, &tmp(0)); + for (uint32_t j = 0; j < p+1; j++) { + buffer(1, j, i) = tmp(j) * weights(i); + } + } + return buffer; + } + + void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[2]; + + nd::view BT = shape_fns(0); + nd::view GT = shape_fns(1); + nd::view A(buffer, {q, n}); + + uint32_t s = 2 * flux_q.stride[0]; + nd::view f2D(&flux_q(0)[0], {q, q}, {s, s*q}); // ? + nd::view r2D = nd::reshape<2>(residual_e, {n, n}); + + contract<1>(f2D, BT, A); + contract<0>( A, GT, r2D); + + f2D.values = &(flux_q(0)[1]); + contract<1>(f2D, GT, A); + contract<0>( A, BT, r2D, true /* accumulate */); + } + + #ifdef __CUDACC__ + __device__ void cuda_gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[1]; + + nd::view B = shape_fns(0); + nd::view G = shape_fns(1); + nd::view A(buffer, {n, q}); + + nd::range All{0u, gradients_q.shape[0]}; + nd::view values_e_2D = nd::reshape<2>(values_e, {n, n}); + nd::view gradients_q_2D((double*)&gradients_q[0], {q, q}, {2, 2*q}); + + threadid tid; + tid.x = threadIdx.x % q; + tid.y = threadIdx.x / q; + tid.stride = q; + + // du_dxi + cuda_contract<1>(tid, values_e_2D, G, A); + cuda_contract<0>(tid, A, B, gradients_q_2D); + gradients_q_2D.values++; + + // du_deta + cuda_contract<1>(tid, values_e_2D, B, A); + cuda_contract<0>(tid, A, G, gradients_q_2D); + gradients_q_2D.values++; + } + + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fns, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = shape_fns.shape[2]; + + nd::view BT = shape_fns(0); + nd::view GT = shape_fns(1); + nd::view A(buffer, {q, n}); + + uint32_t s = 2 * flux_q.stride[0]; + nd::range All{0u, flux_q.shape[0]}; + nd::view f2D(&flux_q(0)[0], {q, q}, {s, s*q}); // ? + nd::view r2D = nd::reshape<2>(residual_e, {n, n}); + + threadid tid; + tid.x = threadIdx.x % n; + tid.y = threadIdx.x / n; + tid.stride = n; + + cuda_contract<1>(tid, f2D, BT, A); + cuda_contract<0>(tid, A, GT, r2D); + + f2D.values = &(flux_q(0)[1]); + cuda_contract<1>(tid, f2D, GT, A); + cuda_contract<0>(tid, A, BT, r2D, true /* accumulate */); + } + #endif + + + + uint32_t p; + +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/h1_tetrahedron.hpp b/src/serac/numerics/refactor/elements/h1_tetrahedron.hpp new file mode 100644 index 0000000000..b5fe246e7d --- /dev/null +++ b/src/serac/numerics/refactor/elements/h1_tetrahedron.hpp @@ -0,0 +1,280 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +template <> +struct FiniteElement { + + using source_type = vec1; + using flux_type = vec3; + + using value_type = vec1; + using grad_type = vec3; + + static constexpr int dim = 3; + + SERAC_HOST_DEVICE constexpr uint32_t num_nodes() const { return Tetrahedron::number(p + 1); } + + constexpr double shape_function(vec3 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) return 1-xi[0]-xi[1]-xi[2]; + if (i == 1) return xi[0]; + if (i == 2) return xi[1]; + if (i == 3) return xi[2]; + } + if (p == 2) { + if (i == 0) return (-1+xi[0]+xi[1]+xi[2])*(-1+2*xi[0]+2*xi[1]+2*xi[2]); + if (i == 1) return -4*xi[0]*(-1+xi[0]+xi[1]+xi[2]); + if (i == 2) return xi[0]*(-1+2*xi[0]); + if (i == 3) return -4*xi[1]*(-1+xi[0]+xi[1]+xi[2]); + if (i == 4) return 4*xi[0]*xi[1]; + if (i == 5) return xi[1]*(-1+2*xi[1]); + if (i == 6) return -4*xi[2]*(-1+xi[0]+xi[1]+xi[2]); + if (i == 7) return 4*xi[0]*xi[2]; + if (i == 8) return 4*xi[1]*xi[2]; + if (i == 9) return xi[2]*(-1+2*xi[2]); + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + if (i == 0) return -((-1+xi[0]+xi[1]+xi[2])*(1+5*xi[0]*xi[0]+5*xi[1]*xi[1]+5*(-1+xi[2])*xi[2]+xi[1]*(-5+11*xi[2])+xi[0]*(-5+11*xi[1]+11*xi[2]))); + if (i == 1) return (5*xi[0]*(-1+xi[0]+xi[1]+xi[2])*(-1-sqrt5+2*sqrt5*xi[0]+(3+sqrt5)*xi[1]+(3+sqrt5)*xi[2]))/2.; + if (i == 2) return (-5*xi[0]*(-1+xi[0]+xi[1]+xi[2])*(1-sqrt5+2*sqrt5*xi[0]+(-3+sqrt5)*xi[1]+(-3+sqrt5)*xi[2]))/2.; + if (i == 3) return xi[0]*(1+5*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]+xi[2]-xi[1]*xi[2]-xi[2]*xi[2]-xi[0]*(5+xi[1]+xi[2])); + if (i == 4) return (5*xi[1]*(-1+xi[0]+xi[1]+xi[2])*(-1-sqrt5+(3+sqrt5)*xi[0]+2*sqrt5*xi[1]+(3+sqrt5)*xi[2]))/2.; + if (i == 5) return -27*xi[0]*xi[1]*(-1+xi[0]+xi[1]+xi[2]); + if (i == 6) return (5*xi[0]*xi[1]*(-2+(3+sqrt5)*xi[0]-(-3+sqrt5)*xi[1]))/2.; + if (i == 7) return (-5*xi[1]*(-1+xi[0]+xi[1]+xi[2])*(1-sqrt5+(-3+sqrt5)*xi[0]+2*sqrt5*xi[1]+(-3+sqrt5)*xi[2]))/2.; + if (i == 8) return (-5*xi[0]*xi[1]*(2+(-3+sqrt5)*xi[0]-(3+sqrt5)*xi[1]))/2.; + if (i == 9) return xi[1]*(1-xi[0]*xi[0]+5*xi[1]*xi[1]+xi[2]-xi[2]*xi[2]-xi[1]*(5+xi[2])-xi[0]*(-1+xi[1]+xi[2])); + if (i == 10) return (5*xi[2]*(-1+xi[0]+xi[1]+xi[2])*(-439204-196418*sqrt5+(710647+317811*sqrt5)*xi[0]+(710647+317811*sqrt5)*xi[1]+606965*xi[2]+271443*sqrt5*xi[2]))/(271443+121393*sqrt5); + if (i == 11) return -27*xi[0]*xi[2]*(-1+xi[0]+xi[1]+xi[2]); + if (i == 12) return (5*xi[0]*xi[2]*(-5-3*sqrt5+(15+7*sqrt5)*xi[0]+2*sqrt5*xi[2]))/(5+3*sqrt5); + if (i == 13) return -27*xi[1]*xi[2]*(-1+xi[0]+xi[1]+xi[2]); + if (i == 14) return 27*xi[0]*xi[1]*xi[2]; + if (i == 15) return (5*xi[1]*xi[2]*(-5-3*sqrt5+(15+7*sqrt5)*xi[1]+2*sqrt5*xi[2]))/(5+3*sqrt5); + if (i == 16) return (5*xi[2]*(-1+xi[0]+xi[1]+xi[2])*(88555+39603*sqrt5+(54730+24476*sqrt5)*xi[0]+(54730+24476*sqrt5)*xi[1]-5*(64079+28657*sqrt5)*xi[2]))/(143285+64079*sqrt5); + if (i == 17) return (-5*xi[0]*xi[2]*(2+(-3+sqrt5)*xi[0]-(3+sqrt5)*xi[2]))/2.; + if (i == 18) return (-5*xi[1]*xi[2]*(2+(-3+sqrt5)*xi[1]-(3+sqrt5)*xi[2]))/2.; + if (i == 19) return -(xi[2]*(-1+xi[0]*xi[0]+xi[1]*xi[1]+xi[1]*(-1+xi[2])-5*(-1+xi[2])*xi[2]+xi[0]*(-1+xi[1]+xi[2]))); + } + + return {}; + } + + vec3 shape_function_gradient(vec3 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) return {-1, -1, -1}; + if (i == 1) return {1, 0, 0}; + if (i == 2) return {0, 1, 0}; + if (i == 3) return {0, 0, 1}; + } + if (p == 2) { + if (i == 0) return {-3+4*xi[0]+4*xi[1]+4*xi[2], -3+4*xi[0]+4*xi[1]+4*xi[2], -3+4*xi[0]+4*xi[1]+4*xi[2]}; + if (i == 1) return {-4*(-1+2*xi[0]+xi[1]+xi[2]), -4*xi[0], -4*xi[0]}; + if (i == 2) return {-1+4*xi[0], 0, 0}; + if (i == 3) return {-4*xi[1], -4*(-1+xi[0]+2*xi[1]+xi[2]), -4*xi[1]}; + if (i == 4) return {4*xi[1], 4*xi[0], 0}; + if (i == 5) return {0, -1+4*xi[1], 0}; + if (i == 6) return {-4*xi[2], -4*xi[2], -4*(-1+xi[0]+xi[1]+2*xi[2])}; + if (i == 7) return {4*xi[2], 0, 4*xi[0]}; + if (i == 8) return {0, 4*xi[2], 4*xi[1]}; + if (i == 9) return {0, 0, -1+4*xi[2]}; + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + if (i == 0) return {-6-15*xi[0]*xi[0]-16*xi[1]*xi[1]+xi[1]*(21-33*xi[2])+(21-16*xi[2])*xi[2]-4*xi[0]*(-5+8*xi[1]+8*xi[2]), -6-16*xi[0]*xi[0]+20*xi[1]+xi[0]*(21-32*xi[1]-33*xi[2])+21*xi[2]-(3*xi[1]+4*xi[2])*(5*xi[1]+4*xi[2]), -6-16*xi[0]*xi[0]+21*xi[1]+xi[0]*(21-33*xi[1]-32*xi[2])+20*xi[2]-(4*xi[1]+3*xi[2])*(4*xi[1]+5*xi[2])}; + if (i == 1) return {(5*(6*sqrt5*xi[0]*xi[0]+xi[0]*(-2-6*sqrt5+6*(1+sqrt5)*xi[1]+6*(1+sqrt5)*xi[2])+(-1+xi[1]+xi[2])*(-1-sqrt5+(3+sqrt5)*xi[1]+(3+sqrt5)*xi[2])))/2., (5*xi[0]*(-4-2*sqrt5+3*(1+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2., (5*xi[0]*(-4-2*sqrt5+3*(1+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2.}; + if (i == 2) return {-15*sqrt5*xi[0]*xi[0]-(5*(-1+xi[1]+xi[2])*(1-sqrt5+(-3+sqrt5)*xi[1]+(-3+sqrt5)*xi[2]))/2.-5*xi[0]*(1-3*sqrt5+3*(-1+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2]), (-5*xi[0]*(4-2*sqrt5+3*(-1+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2., (-5*xi[0]*(4-2*sqrt5+3*(-1+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2.}; + if (i == 3) return {1+15*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]+xi[2]-xi[1]*xi[2]-xi[2]*xi[2]-2*xi[0]*(5+xi[1]+xi[2]), -(xi[0]*(-1+xi[0]+2*xi[1]+xi[2])), -(xi[0]*(-1+xi[0]+xi[1]+2*xi[2]))}; + if (i == 4) return {(5*xi[1]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+3*(1+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2., 15*sqrt5*xi[1]*xi[1]+5*xi[1]*(-1-3*sqrt5+3*(1+sqrt5)*xi[0]+3*(1+sqrt5)*xi[2])+(5*(-1+xi[0]+xi[2])*(-1-sqrt5+(3+sqrt5)*xi[0]+(3+sqrt5)*xi[2]))/2., (5*xi[1]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+3*(1+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2.}; + if (i == 5) return {-27*xi[1]*(-1+2*xi[0]+xi[1]+xi[2]), -27*xi[0]*(-1+xi[0]+2*xi[1]+xi[2]), -27*xi[0]*xi[1]}; + if (i == 6) return {(-5*xi[1]*(2-2*(3+sqrt5)*xi[0]+(-3+sqrt5)*xi[1]))/2., (5*xi[0]*(-2+(3+sqrt5)*xi[0]-2*(-3+sqrt5)*xi[1]))/2., 0}; + if (i == 7) return {(-5*xi[1]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2., -15*sqrt5*xi[1]*xi[1]-(5*(-1+xi[0]+xi[2])*(1-sqrt5+(-3+sqrt5)*xi[0]+(-3+sqrt5)*xi[2]))/2.-5*xi[1]*(1-3*sqrt5+3*(-1+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[2]), (-5*xi[1]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2.}; + if (i == 8) return {(5*xi[1]*(-2-2*(-3+sqrt5)*xi[0]+(3+sqrt5)*xi[1]))/2., (-5*xi[0]*(2+(-3+sqrt5)*xi[0]-2*(3+sqrt5)*xi[1]))/2., 0}; + if (i == 9) return {-(xi[1]*(-1+2*xi[0]+xi[1]+xi[2])), 1-xi[0]*xi[0]+15*xi[1]*xi[1]+xi[2]-xi[2]*xi[2]-2*xi[1]*(5+xi[2])-xi[0]*(-1+2*xi[1]+xi[2]), -(xi[1]*(-1+xi[0]+xi[1]+2*xi[2]))}; + if (i == 10) return {(5*xi[2]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+3*(1+sqrt5)*xi[2]))/2., (5*xi[2]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+3*(1+sqrt5)*xi[2]))/2., (5*(1+sqrt5+(3+sqrt5)*xi[0]*xi[0]-2*(2+sqrt5)*xi[1]+(3+sqrt5)*xi[1]*xi[1]+6*(1+sqrt5)*xi[1]*xi[2]+2*xi[2]*(-1-3*sqrt5+3*sqrt5*xi[2])+2*xi[0]*(-2-sqrt5+(3+sqrt5)*xi[1]+3*(1+sqrt5)*xi[2])))/2.}; + if (i == 11) return {-27*xi[2]*(-1+2*xi[0]+xi[1]+xi[2]), -27*xi[0]*xi[2], -27*xi[0]*(-1+xi[0]+xi[1]+2*xi[2])}; + if (i == 12) return {(-5*xi[2]*(2-2*(3+sqrt5)*xi[0]+(-3+sqrt5)*xi[2]))/2., 0, (5*xi[0]*(-2+(3+sqrt5)*xi[0]-2*(-3+sqrt5)*xi[2]))/2.}; + if (i == 13) return {-27*xi[1]*xi[2], -27*xi[2]*(-1+xi[0]+2*xi[1]+xi[2]), -27*xi[1]*(-1+xi[0]+xi[1]+2*xi[2])}; + if (i == 14) return {27*xi[1]*xi[2], 27*xi[0]*xi[2], 27*xi[0]*xi[1]}; + if (i == 15) return {0, (-5*xi[2]*(2-2*(3+sqrt5)*xi[1]+(-3+sqrt5)*xi[2]))/2., (5*xi[1]*(-2+(3+sqrt5)*xi[1]-2*(-3+sqrt5)*xi[2]))/2.}; + if (i == 16) return {(-5*xi[2]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2]))/2., (-5*xi[2]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2]))/2., (-5*(-3+sqrt5)*xi[0]*xi[0])/2.-5*xi[0]*(2-sqrt5+(-3+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2])-(5*(-1+sqrt5+(-3+sqrt5)*xi[1]*xi[1]+2*xi[2]*(1-3*sqrt5+3*sqrt5*xi[2])+xi[1]*(4-2*sqrt5+6*(-1+sqrt5)*xi[2])))/2.}; + if (i == 17) return {(5*xi[2]*(-2-2*(-3+sqrt5)*xi[0]+(3+sqrt5)*xi[2]))/2., 0, (-5*xi[0]*(2+(-3+sqrt5)*xi[0]-2*(3+sqrt5)*xi[2]))/2.}; + if (i == 18) return {0, (5*xi[2]*(-2-2*(-3+sqrt5)*xi[1]+(3+sqrt5)*xi[2]))/2., (-5*xi[1]*(2+(-3+sqrt5)*xi[1]-2*(3+sqrt5)*xi[2]))/2.}; + if (i == 19) return {-(xi[2]*(-1+2*xi[0]+xi[1]+xi[2])), -(xi[2]*(-1+xi[0]+2*xi[1]+xi[2])), 1+xi[0]-xi[0]*xi[0]+xi[1]-xi[0]*xi[1]-xi[1]*xi[1]-2*(5+xi[0]+xi[1])*xi[2]+15*xi[2]*xi[2]}; + } + + return {}; + } + + vec3 shape_function_derivative(vec3 xi, uint32_t i) const { + return shape_function_gradient(xi, i); + } + + double interpolate(vec3 xi, double * values) const { + double interpolated_value = 0.0; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_value += values[i] * shape_function(xi, i); + } + return interpolated_value; + } + + vec3 gradient(vec3 xi, double * values) const { + vec3 interpolated_gradient{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_gradient += values[i] * shape_function_gradient(xi, i); + } + return interpolated_gradient; + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view) const { + return 0; + } + + nd::array< double, 2 > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationTetrahedron(&xi(i, 0), p, &shape_fns(i, 0)); + } + return shape_fns; + } + + nd::array< double, 3 > evaluate_shape_function_gradients(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationDerivativeTetrahedron(&xi(i, 0), p, &shape_fn_grads(i, 0, 0)); + } + return shape_fn_grads; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + double sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum += shape_fns(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + void gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = gradients_q.shape[0]; + + for (uint32_t j = 0; j < nqpts; j++) { + grad_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += values_e(i) * shape_fn_grads(j, i, 0); + sum[1] += values_e(i) * shape_fn_grads(j, i, 1); + sum[2] += values_e(i) * shape_fn_grads(j, i, 2); + } + gradients_q(j) = sum; + } + + } + + nd::array< double, 2 > evaluate_weighted_shape_functions(nd::view xi, + nd::view weights) const { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, nnodes}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationTetrahedron(&xi(i, 0), p, &shape_fns(i, 0)); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fns(i, j) = shape_fns(i, j) * weights(i); + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn(q, i) * source_q(q); + } + residual_e(i) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_function_gradients(nd::view xi, + nd::view weights) const { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({q, nnodes, dim}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationDerivativeTetrahedron(&xi(i, 0), p, &shape_fn_grads(i, 0, 0)); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fn_grads(i, j, 0) = shape_fn_grads(i, j, 0) * weights(i); + shape_fn_grads(i, j, 1) = shape_fn_grads(i, j, 1) * weights(i); + shape_fn_grads(i, j, 2) = shape_fn_grads(i, j, 2) * weights(i); + } + } + + return shape_fn_grads; + } + + void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_grads, double * /* buffer */) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (int d = 0; d < dim; d++) { + sum += shape_fn_grads(q, i, d) * flux_q(q)[d]; + } + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = gradients_q.shape[0]; + + for (int j = threadIdx.x; j < nqpts; j += blockDim.x) { + grad_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += values_e(i) * shape_fn_grads(j, i, 0); + sum[1] += values_e(i) * shape_fn_grads(j, i, 1); + sum[2] += values_e(i) * shape_fn_grads(j, i, 2); + } + gradients_q(j) = sum; + } + } + + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (int d = 0; d < dim; d++) { + sum += shape_fn_grads(q, i, d) * flux_q(q)[d]; + } + } + residual_e(i) = sum; + } + } + #endif + + uint32_t p; + +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/h1_triangle.hpp b/src/serac/numerics/refactor/elements/h1_triangle.hpp new file mode 100644 index 0000000000..ab577f9d31 --- /dev/null +++ b/src/serac/numerics/refactor/elements/h1_triangle.hpp @@ -0,0 +1,245 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +// clang-format off +template <> +struct FiniteElement { + + using source_type = vec1; + using flux_type = vec2; + + using value_type = vec1; + using grad_type = vec2; + + static constexpr int dim = 2; + + SERAC_HOST_DEVICE constexpr uint32_t num_nodes() const { return Triangle::number(p + 1); } + + constexpr double shape_function(vec2 xi, uint32_t i) const { + if (p == 1) { + if (i == 0) return 1.0 - xi[0] - xi[1]; + if (i == 1) return xi[0]; + if (i == 2) return xi[1]; + } + if (p == 2) { + if (i == 0) return (-1+xi[0]+xi[1])*(-1+2*xi[0]+2*xi[1]); + if (i == 1) return -4*xi[0]*(-1+xi[0]+xi[1]); + if (i == 2) return xi[0]*(-1+2*xi[0]); + if (i == 3) return -4*xi[1]*(-1+xi[0]+xi[1]); + if (i == 4) return 4*xi[0]*xi[1]; + if (i == 5) return xi[1]*(-1+2*xi[1]); + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + if (i == 0) return -((-1+xi[0]+xi[1])*(1+5*xi[0]*xi[0]+5*(-1+xi[1])*xi[1]+xi[0]*(-5+11*xi[1]))); + if (i == 1) return (5*xi[0]*(-1+xi[0]+xi[1])*(-1-sqrt5+2*sqrt5*xi[0]+(3+sqrt5)*xi[1]))/2.0; + if (i == 2) return (-5*xi[0]*(-1+xi[0]+xi[1])*(1-sqrt5+2*sqrt5*xi[0]+(-3+sqrt5)*xi[1]))/2.0; + if (i == 3) return xi[0]*(1+5*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]-xi[0]*(5+xi[1])); + if (i == 4) return (5*xi[1]*(-1+xi[0]+xi[1])*(-1-sqrt5+(3+sqrt5)*xi[0]+2*sqrt5*xi[1]))/2.0; + if (i == 5) return -27*xi[0]*xi[1]*(-1+xi[0]+xi[1]); + if (i == 6) return (5*xi[0]*xi[1]*(-2+(3+sqrt5)*xi[0]-(-3+sqrt5)*xi[1]))/2.; + if (i == 7) return (5*xi[1]*(-1+xi[0]+xi[1])*(5-3*sqrt5+2*(-5+2*sqrt5)*xi[0]+5*(-1+sqrt5)*xi[1]))/(-5+sqrt5); + if (i == 8) return (-5*xi[0]*xi[1]*(2+(-3+sqrt5)*xi[0]-(3+sqrt5)*xi[1]))/2.; + if (i == 9) return xi[1]*(1+xi[0]-xi[0]*xi[0]-xi[0]*xi[1]+5*(-1+xi[1])*xi[1]); + } + + return -1.0; + } + + vec2 shape_function_gradient(vec2 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) return {-1.0, -1.0}; + if (i == 1) return { 1.0, 0.0}; + if (i == 2) return { 0.0, 1.0}; + } + if (p == 2) { + if (i == 0) return {-3+4*xi[0]+4*xi[1], -3+4*xi[0]+4*xi[1]}; + if (i == 1) return {-4*(-1+2*xi[0]+xi[1]), -4*xi[0]}; + if (i == 2) return {-1+4*xi[0], 0}; + if (i == 3) return {-4*xi[1], -4*(-1+xi[0]+2*xi[1])}; + if (i == 4) return {4*xi[1], 4*xi[0]}; + if (i == 5) return {0, -1+4*xi[1]}; + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + if (i == 0) return {-6-15*xi[0]*xi[0]+4*xi[0]*(5-8*xi[1])+(21-16*xi[1])*xi[1], -6-16*xi[0]*xi[0]+xi[0]*(21-32*xi[1])+5*(4-3*xi[1])*xi[1]}; + if (i == 1) return {(5*(6*sqrt5*xi[0]*xi[0]+xi[0]*(-2-6*sqrt5+6*(1+sqrt5)*xi[1])+(-1+xi[1])*(-1-sqrt5+(3+sqrt5)*xi[1])))/2., (5*xi[0]*(-2*(2+sqrt5)+3*(1+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]))/2.}; + if (i == 2) return {(-5*(6*sqrt5*xi[0]*xi[0]+(-1+xi[1])*(1-sqrt5+(-3+sqrt5)*xi[1])+xi[0]*(2-6*sqrt5+6*(-1+sqrt5)*xi[1])))/2., (-5*xi[0]*(4-2*sqrt5+3*(-1+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]))/2.}; + if (i == 3) return {1+15*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]-2*xi[0]*(5+xi[1]), -(xi[0]*(-1+xi[0]+2*xi[1]))}; + if (i == 4) return {(5*xi[1]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+3*(1+sqrt5)*xi[1]))/2., (5*(1+sqrt5-2*(2+sqrt5)*xi[0]+(3+sqrt5)*xi[0]*xi[0]+6*(1+sqrt5)*xi[0]*xi[1]+2*xi[1]*(-1-3*sqrt5+3*sqrt5*xi[1])))/2.}; + if (i == 5) return {-27*xi[1]*(-1+2*xi[0]+xi[1]), -27*xi[0]*(-1+xi[0]+2*xi[1])}; + if (i == 6) return {(-5*xi[1]*(2-2*(3+sqrt5)*xi[0]+(-3+sqrt5)*xi[1]))/2., (5*xi[0]*(-2+(3+sqrt5)*xi[0]-2*(-3+sqrt5)*xi[1]))/2.}; + if (i == 7) return {(-5*xi[1]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[1]))/2., (-5*(-1+sqrt5+(-3+sqrt5)*xi[0]*xi[0]+2*xi[1]*(1-3*sqrt5+3*sqrt5*xi[1])+xi[0]*(4-2*sqrt5+6*(-1+sqrt5)*xi[1])))/2.}; + if (i == 8) return {(5*xi[1]*(-2-2*(-3+sqrt5)*xi[0]+(3+sqrt5)*xi[1]))/2., (-5*xi[0]*(2+(-3+sqrt5)*xi[0]-2*(3+sqrt5)*xi[1]))/2.}; + if (i == 9) return {-(xi[1]*(-1+2*xi[0]+xi[1])), 1+xi[0]-xi[0]*xi[0]-2*(5+xi[0])*xi[1]+15*xi[1]*xi[1]}; + } + + return {}; + } + + vec2 shape_function_derivative(vec2 xi, uint32_t i) const { + return shape_function_gradient(xi, i); + } + + double interpolate(vec2 xi, const double * values) const { + double interpolated_value = 0.0; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_value += values[i] * shape_function(xi, i); + } + return interpolated_value; + } + + vec2 gradient(vec2 xi, const double * values) const { + vec2 interpolated_gradient = {0.0, 0.0}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_gradient += values[i] * shape_function_gradient(xi, i); + } + return interpolated_gradient; + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view) const { + return 0; + } + + nd::array< double, 2 > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationTriangle(&xi(i, 0), p, &shape_fns(i, 0)); + } + return shape_fns; + } + + nd::array< double, 3 > evaluate_shape_function_gradients(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationDerivativeTriangle(&xi(i, 0), p, &shape_fn_grads(i, 0, 0)); + } + return shape_fn_grads; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + double sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum += shape_fns(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + void gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = gradients_q.shape[0]; + for (uint32_t q = 0; q < nqpts; q++) { + grad_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += values_e(i) * shape_fn_grads(q, i, 0); + sum[1] += values_e(i) * shape_fn_grads(q, i, 1); + } + gradients_q(q) = sum; + } + } + + nd::array< double, 2 > evaluate_weighted_shape_functions(nd::view xi, + nd::view weights) const { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, nnodes}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationTriangle(&xi(i, 0), p, &shape_fns(i, 0)); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fns(i, j) = shape_fns(i, j) * weights(i); + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn(q, i) * source_q(q); + } + residual_e(i) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_function_gradients(nd::view xi, + nd::view weights) const { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fn_grads({q, nnodes, dim}); + for (uint32_t i = 0; i < q; i++) { + GaussLobattoInterpolationDerivativeTriangle(&xi(i, 0), p, &shape_fn_grads(i, 0, 0)); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fn_grads(i, j, 0) = shape_fn_grads(i, j, 0) * weights(i); + shape_fn_grads(i, j, 1) = shape_fn_grads(i, j, 1) * weights(i); + } + } + + return shape_fn_grads; + } + + void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (int d = 0; d < dim; d++) { + sum += shape_fn_grads(q, i, d) * flux_q(q)[d]; + } + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_gradient(nd::view gradients_q, nd::view values_e, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = gradients_q.shape[0]; + for (int j = threadIdx.x; j < nqpts; j += blockDim.x) { + grad_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += values_e(i) * shape_fn_grads(j, i, 0); + sum[1] += values_e(i) * shape_fn_grads(j, i, 1); + } + gradients_q(j) = sum; + } + } + + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_grads, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (int d = 0; d < dim; d++) { + sum += shape_fn_grads(q, i, d) * flux_q(q)[d]; + } + } + residual_e(i) = sum; + } + } + #endif + + uint32_t p; + +}; +// clang-format on + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/h1_vertex.hpp b/src/serac/numerics/refactor/elements/h1_vertex.hpp new file mode 100644 index 0000000000..83bd0478d0 --- /dev/null +++ b/src/serac/numerics/refactor/elements/h1_vertex.hpp @@ -0,0 +1,15 @@ +#pragma once + +namespace refactor { + +template <> +struct FiniteElement { + using source_type = double; + using flux_type = double; + + SERAC_HOST_DEVICE uint32_t num_nodes() const { return 1; } + + uint32_t p; +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/hcurl_edge.hpp b/src/serac/numerics/refactor/elements/hcurl_edge.hpp new file mode 100644 index 0000000000..ca74c04ad7 --- /dev/null +++ b/src/serac/numerics/refactor/elements/hcurl_edge.hpp @@ -0,0 +1,216 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +template <> +struct FiniteElement < mfem::Geometry::SEGMENT, Family::HCURL >{ + + using source_type = vec1; + using flux_type = vec1; + + static constexpr uint32_t dim = 1; + + SERAC_HOST_DEVICE uint32_t num_nodes() const { return p; } + + constexpr vec1 shape_function(vec1 xi, uint32_t i) const { + if (p == 1 && i == 0) { return GaussLegendreInterpolation01<1, 0>(xi[0]); } + + if (p == 2 && i == 0) { return GaussLegendreInterpolation01<2, 0>(xi[0]); } + if (p == 2 && i == 1) { return GaussLegendreInterpolation01<2, 1>(xi[0]); } + + if (p == 3 && i == 0) { return GaussLegendreInterpolation01<3, 0>(xi[0]); } + if (p == 3 && i == 1) { return GaussLegendreInterpolation01<3, 1>(xi[0]); } + if (p == 3 && i == 2) { return GaussLegendreInterpolation01<3, 2>(xi[0]); } + + return 1000.0; + } + + constexpr vec1 reoriented_shape_function(vec1 xi, uint32_t i, int8_t transformation) const { + if (transformation == -1) { + return -shape_function(xi, i); + } else { + return shape_function(xi, i); + } + } + + // the other Nedelec elements define this function, + // but what is the appropriate interpretation of "curl" (if any) for 1D? + // + // the implementation below is just the derivative + constexpr vec1 shape_function_curl(vec1 xi, uint32_t i) const { + if (p == 1 && i == 0) { return GaussLegendreInterpolationDerivative01<1, 0>(xi); } + + if (p == 2 && i == 0) { return GaussLegendreInterpolationDerivative01<2, 0>(xi); } + if (p == 2 && i == 1) { return GaussLegendreInterpolationDerivative01<2, 1>(xi); } + + if (p == 3 && i == 0) { return GaussLegendreInterpolationDerivative01<3, 0>(xi); } + if (p == 3 && i == 1) { return GaussLegendreInterpolationDerivative01<3, 1>(xi); } + if (p == 3 && i == 2) { return GaussLegendreInterpolationDerivative01<3, 2>(xi); } + + return 1000.0; + } + + constexpr vec1 reoriented_shape_function_curl(vec1 xi, uint32_t i, int8_t transformation) const { + if (transformation == -1) { + return -shape_function_curl(xi, i); + } else { + return shape_function_curl(xi, i); + } + } + + constexpr vec1 shape_function_derivative(vec1 xi, uint32_t i) { + return shape_function_curl(xi, i); + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view) const { + return 0; + } + + nd::array< double, 2 > evaluate_shape_functions(nd::view xi) { + uint32_t nnodes = num_nodes(); + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + vec1 xi_i = xi(i, 0); + for (uint32_t j = 0; j < nnodes; j++) { + shape_fns(i, j) = shape_function(xi_i, j); + } + } + return shape_fns; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + double sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum += shape_fns(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + void curl(nd::view values_q, nd::view values_e, nd::view shape_fn_curls, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + flux_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += shape_fn_curls(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + nd::array< double, 2 > evaluate_shape_function_curls(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + for (uint32_t j = 0; j < num_nodes(); j++) { + shape_fns(i, j) = shape_function_curl(xi(i, 0), j); + } + } + return shape_fns; + } + + #if 0 + void curl(nd::view values_q, nd::view values_e, nd::view buffer, double * /*buffer*/) { + uint32_t n = p + 1; + uint32_t q = sqrt(values_q.shape[0]); + + // 1D shape function evaluations + nd::view B1(buffer.data(), {q, p}); // legendre shape functions + nd::view B2(B1.end(), {q, n}); // lobatto shape functions + nd::view G2(B2.end(), {q, n}); // lobatto shape function derivatives + nd::view A1(G2.end(), {q, n}); // storage for intermediates + + nd::view ue(values_e.data(), {n, p}); + nd::view uq(values_q.data(), {q, q}, {2*q, 2u}); + + _contract(A1, B1, ue); // A1(qx, iy) = sum_{ix} B1(qx, ix) * ue(iy, ix) + _contract(uq, B2, A1); // uq(qy, qx) = sum_{iy} B2(qy, iy) * A1(qx, iy) + + ue = nd::view< const double, 2 >(values_e.data() + (n * p), {n, p}); + + // note: column-major strides here, since quadrature points + // are still enumerated lexicographically as {y, x} but y-component nodes are {x, y} + uq = nd::view(values_q.data() + 1, {q, q}, {2u, 2*q}); + + _contract(A1, B1, ue); // A1(qx, iy) = sum_{ix} B1(qx, ix) * ue(iy, ix) + _contract(uq, B2, A1); // uq(qy, qx) = sum_{iy} B2(qy, iy) * A1(qx, iy) + } + #endif + + nd::array< double, 2 > evaluate_weighted_shape_functions(nd::view xi, nd::view weights) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + for (uint32_t j = 0; j < num_nodes(); j++) { + shape_fns(i, j) = shape_function(xi(i, 0), j) * weights(i); + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn(q, i) * source_q(q); + } + residual_e(i) = sum; + } + } + + nd::array< double, 2 > evaluate_weighted_shape_function_curls(nd::view xi, nd::view weights) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + for (uint32_t j = 0; j < num_nodes(); j++) { + shape_fns(i, j) = shape_function_curl(xi(i, 0), j) * weights(i); + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn_curl(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + #endif + + uint32_t p; + +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/hcurl_hexahedron.hpp b/src/serac/numerics/refactor/elements/hcurl_hexahedron.hpp new file mode 100644 index 0000000000..01476f85b5 --- /dev/null +++ b/src/serac/numerics/refactor/elements/hcurl_hexahedron.hpp @@ -0,0 +1,735 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +// clang-format off +template <> +struct FiniteElement { + + using value_type = vec3; + using derivative_type = vec3; + + using source_type = vec3; + using flux_type = vec3; + + static constexpr int dim = 3; + + // clang-format off + SERAC_HOST_DEVICE uint8_t const * lexicographic_permutations(uint32_t p_) { + static constexpr uint8_t linear_lexicographic_permutation[12] = {0,5,1,4,8,9,11,10,2,7,3,6}; + static constexpr uint8_t quadratic_lexicographic_permutation[54] = {0,1,20,23,4,5,18,21,36,45,38,47,44,53,42,51,12,13,32,35,16,17,30,33,3,2,19,22,6,7,37,46,26,29,41,50,11,10,43,52,27,24,39,48,14,15,31,34,8,9,25,28,40,49}; + static constexpr uint8_t cubic_lexicographic_permutation[144] = {0,1,2,51,55,59,9,10,11,48,52,56,96,112,128,99,115,131,111,127,143,108,124,140,36,37,38,87,91,95,45,46,47,84,88,92,5,4,3,8,7,6,50,54,58,49,53,57,12,13,14,24,25,26,97,113,129,98,114,130,63,67,71,75,79,83,103,119,135,107,123,139,23,22,21,35,34,33,110,126,142,109,125,141,68,64,60,80,76,72,104,120,136,100,116,132,39,40,41,42,43,44,85,89,93,86,90,94,15,16,17,18,19,20,27,28,29,30,31,32,61,62,65,66,69,70,73,74,77,78,81,82,101,102,105,106,117,118,121,122,133,134,137,138}; + static constexpr uint8_t const * permutations[4] = {nullptr, linear_lexicographic_permutation, quadratic_lexicographic_permutation, cubic_lexicographic_permutation }; + return permutations[p_]; + } + // clang-format on + + SERAC_HOST_DEVICE uint32_t num_nodes() const { return 3 * p * (p + 1) * (p + 1); } + + constexpr vec3 shape_function(vec3 xi, uint32_t i) const { + if (p == 1) { + if (i == 0) { return vec3{(-1 + xi[1])*(-1 + xi[2]),0,0}; } + if (i == 1) { return vec3{xi[1] - xi[1]*xi[2],0,0}; } + if (i == 2) { return vec3{xi[2] - xi[1]*xi[2],0,0}; } + if (i == 3) { return vec3{xi[1]*xi[2],0,0}; } + if (i == 4) { return vec3{0,(-1 + xi[0])*(-1 + xi[2]),0}; } + if (i == 5) { return vec3{0,xi[0] - xi[0]*xi[2],0}; } + if (i == 6) { return vec3{0,xi[2] - xi[0]*xi[2],0}; } + if (i == 7) { return vec3{0,xi[0]*xi[2],0}; } + if (i == 8) { return vec3{0,0,(-1 + xi[0])*(-1 + xi[1])}; } + if (i == 9) { return vec3{0,0,xi[0] - xi[0]*xi[1]}; } + if (i == 10) { return vec3{0,0,xi[1] - xi[0]*xi[1]}; } + if (i == 11) { return vec3{0,0,xi[0]*xi[1]}; } + } + if (p == 2) { + if (i == 0) { return vec3{-1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0,0}; } + if (i == 1) { return vec3{(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0,0}; } + if (i == 2) { return vec3{6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1])*xi[1]*(-1 + xi[2])*(-1 + 2*xi[2]),0,0}; } + if (i == 3) { return vec3{-4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*xi[1]*(-1 + xi[2])*(-1 + 2*xi[2]),0,0}; } + if (i == 4) { return vec3{-1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-1 + 2*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0,0}; } + if (i == 5) { return vec3{(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1]*(-1 + 2*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0,0}; } + if (i == 6) { return vec3{6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-1 + xi[2])*xi[2],0,0}; } + if (i == 7) { return vec3{-4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-1 + xi[2])*xi[2],0,0}; } + if (i == 8) { return vec3{-27.712812921102036696439141464*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*xi[1]*(-1. + xi[2])*xi[2],0,0}; } + if (i == 9) { return vec3{27.712812921102036696439141*(-0.21132486540518711774542561 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-1. + xi[2])*xi[2],0,0}; } + if (i == 10) { return vec3{6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-1 + 2*xi[1])*(-1 + xi[2])*xi[2],0,0}; } + if (i == 11) { return vec3{-4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1]*(-1 + 2*xi[1])*(-1 + xi[2])*xi[2],0,0}; } + if (i == 12) { return vec3{-1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*xi[2]*(-1 + 2*xi[2]),0,0}; } + if (i == 13) { return vec3{(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*xi[2]*(-1 + 2*xi[2]),0,0}; } + if (i == 14) { return vec3{6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1])*xi[1]*xi[2]*(-1 + 2*xi[2]),0,0}; } + if (i == 15) { return vec3{-4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*xi[1]*xi[2]*(-1 + 2*xi[2]),0,0}; } + if (i == 16) { return vec3{-1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-1 + 2*xi[1])*xi[2]*(-1 + 2*xi[2]),0,0}; } + if (i == 17) { return vec3{(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1]*(-1 + 2*xi[1])*xi[2]*(-1 + 2*xi[2]),0,0}; } + if (i == 18) { return vec3{0,-1.7320508075688772935274463415*(-1 + xi[0])*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0}; } + if (i == 19) { return vec3{0,6.928203230275509174109785366*(-1 + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0}; } + if (i == 20) { return vec3{0,-1.7320508075688772935274463415*xi[0]*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0}; } + if (i == 21) { return vec3{0,(-1 + xi[0])*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0}; } + if (i == 22) { return vec3{0,-4*(-1 + xi[0])*xi[0]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0}; } + if (i == 23) { return vec3{0,xi[0]*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2]),0}; } + if (i == 24) { return vec3{0,6.928203230275509174109785366*(-1 + xi[0])*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1 + xi[2])*xi[2],0}; } + if (i == 25) { return vec3{0,-27.712812921102036696439141464*(-1. + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*xi[2],0}; } + if (i == 26) { return vec3{0,6.928203230275509174109785366*xi[0]*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1 + xi[2])*xi[2],0}; } + if (i == 27) { return vec3{0,-4*(-1 + xi[0])*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*xi[2],0}; } + if (i == 28) { return vec3{0,27.7128129211020366964391415*(-1. + xi[0])*xi[0]*(-0.21132486540518711774542561 + 1.*xi[1])*(-1. + xi[2])*xi[2],0}; } + if (i == 29) { return vec3{0,-4*xi[0]*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*xi[2],0}; } + if (i == 30) { return vec3{0,-1.7320508075688772935274463415*(-1 + xi[0])*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])*xi[2]*(-1 + 2*xi[2]),0}; } + if (i == 31) { return vec3{0,6.928203230275509174109785366*(-1 + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])*xi[2]*(-1 + 2*xi[2]),0}; } + if (i == 32) { return vec3{0,-1.7320508075688772935274463415*xi[0]*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])*xi[2]*(-1 + 2*xi[2]),0}; } + if (i == 33) { return vec3{0,(-1 + xi[0])*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*xi[2]*(-1 + 2*xi[2]),0}; } + if (i == 34) { return vec3{0,-4*(-1 + xi[0])*xi[0]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*xi[2]*(-1 + 2*xi[2]),0}; } + if (i == 35) { return vec3{0,xi[0]*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*xi[2]*(-1 + 2*xi[2]),0}; } + if (i == 36) { return vec3{0,0,-1.7320508075688772935274463415*(-1 + xi[0])*(-1 + 2*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 37) { return vec3{0,0,6.928203230275509174109785366*(-1 + xi[0])*xi[0]*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 38) { return vec3{0,0,-1.7320508075688772935274463415*xi[0]*(-1 + 2*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 39) { return vec3{0,0,6.928203230275509174109785366*(-1 + xi[0])*(-1 + 2*xi[0])*(-1 + xi[1])*xi[1]*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 40) { return vec3{0,0,-27.712812921102036696439141464*(-1. + xi[0])*xi[0]*(-1. + xi[1])*xi[1]*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 41) { return vec3{0,0,6.928203230275509174109785366*xi[0]*(-1 + 2*xi[0])*(-1 + xi[1])*xi[1]*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 42) { return vec3{0,0,-1.7320508075688772935274463415*(-1 + xi[0])*(-1 + 2*xi[0])*xi[1]*(-1 + 2*xi[1])*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 43) { return vec3{0,0,6.928203230275509174109785366*(-1 + xi[0])*xi[0]*xi[1]*(-1 + 2*xi[1])*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 44) { return vec3{0,0,-1.7320508075688772935274463415*xi[0]*(-1 + 2*xi[0])*xi[1]*(-1 + 2*xi[1])*(-0.7886751345948128822545743902 + xi[2])}; } + if (i == 45) { return vec3{0,0,(-1 + xi[0])*(-1 + 2*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 46) { return vec3{0,0,-4*(-1 + xi[0])*xi[0]*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 47) { return vec3{0,0,xi[0]*(-1 + 2*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 48) { return vec3{0,0,-4*(-1 + xi[0])*(-1 + 2*xi[0])*(-1 + xi[1])*xi[1]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 49) { return vec3{0,0,27.71281292110203669643914146*(-1. + xi[0])*xi[0]*(-1. + xi[1])*xi[1]*(-0.2113248654051871177454256098 + 1.*xi[2])}; } + if (i == 50) { return vec3{0,0,-4*xi[0]*(-1 + 2*xi[0])*(-1 + xi[1])*xi[1]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 51) { return vec3{0,0,(-1 + xi[0])*(-1 + 2*xi[0])*xi[1]*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 52) { return vec3{0,0,-4*(-1 + xi[0])*xi[0]*xi[1]*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + if (i == 53) { return vec3{0,0,xi[0]*(-1 + 2*xi[0])*xi[1]*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2])}; } + } + if (p == 3) { + if (i == 0) { return vec3{(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 1) { return vec3{-6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 2) { return vec3{(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 3) { return vec3{11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 4) { return vec3{-74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 5) { return vec3{11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 6) { return vec3{-11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 7) { return vec3{74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 8) { return vec3{-11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 9) { return vec3{(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 10) { return vec3{-6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 11) { return vec3{(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0,0}; } + if (i == 12) { return vec3{11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 13) { return vec3{-74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 14) { return vec3{11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 15) { return vec3{125.*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 16) { return vec3{-833.3333333333333*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 17) { return vec3{125.*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 18) { return vec3{-125.*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 19) { return vec3{833.3333333333333*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 20) { return vec3{-125.*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 21) { return vec3{11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 22) { return vec3{-74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 23) { return vec3{11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0,0}; } + if (i == 24) { return vec3{-11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 25) { return vec3{74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 26) { return vec3{-11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 27) { return vec3{-125.*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 28) { return vec3{833.3333333333333*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 29) { return vec3{-125.*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 30) { return vec3{125.*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 31) { return vec3{-833.3333333333333333*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 32) { return vec3{125.*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 33) { return vec3{-11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 34) { return vec3{74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 35) { return vec3{-11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0,0}; } + if (i == 36) { return vec3{(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 37) { return vec3{-6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 38) { return vec3{(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 39) { return vec3{11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 40) { return vec3{-74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 41) { return vec3{11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 42) { return vec3{-11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 43) { return vec3{74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 44) { return vec3{-11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 45) { return vec3{(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 46) { return vec3{-6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 47) { return vec3{(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0,0}; } + if (i == 48) { return vec3{0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 49) { return vec3{0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 50) { return vec3{0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 51) { return vec3{0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 52) { return vec3{0,-6.66666666666666666666666667*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 53) { return vec3{0,-74.53559924999299*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 54) { return vec3{0,74.53559924999298988*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 55) { return vec3{0,-6.66666666666666666666666667*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 56) { return vec3{0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 57) { return vec3{0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 58) { return vec3{0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 59) { return vec3{0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(1 + xi[2]*(-6. + (10. - 5.*xi[2])*xi[2])),0}; } + if (i == 60) { return vec3{0,11.180339887498948*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 61) { return vec3{0,125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 62) { return vec3{0,-125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 63) { return vec3{0,11.180339887498948*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 64) { return vec3{0,-74.53559924999299*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 65) { return vec3{0,-833.3333333333333*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 66) { return vec3{0,833.3333333333333*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 67) { return vec3{0,-74.53559924999299*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 68) { return vec3{0,11.180339887498948*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 69) { return vec3{0,125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 70) { return vec3{0,-125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 71) { return vec3{0,11.180339887498948*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2]),0}; } + if (i == 72) { return vec3{0,-11.180339887498948482*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 73) { return vec3{0,-125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 74) { return vec3{0,125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 75) { return vec3{0,-11.180339887498948482*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 76) { return vec3{0,74.53559924999298988*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 77) { return vec3{0,833.3333333333333*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 78) { return vec3{0,-833.3333333333333333*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 79) { return vec3{0,74.53559924999298988*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 80) { return vec3{0,-11.180339887498948482*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 81) { return vec3{0,-125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 82) { return vec3{0,125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 83) { return vec3{0,-11.180339887498948482*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2],0}; } + if (i == 84) { return vec3{0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 85) { return vec3{0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 86) { return vec3{0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 87) { return vec3{0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 88) { return vec3{0,-6.66666666666666666666666667*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 89) { return vec3{0,-74.53559924999299*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 90) { return vec3{0,74.53559924999298988*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 91) { return vec3{0,-6.66666666666666666666666667*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 92) { return vec3{0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 93) { return vec3{0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 94) { return vec3{0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 95) { return vec3{0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))*xi[2]*(1. + xi[2]*(-5. + 5.*xi[2])),0}; } + if (i == 96) { return vec3{0,0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 97) { return vec3{0,0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 98) { return vec3{0,0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 99) { return vec3{0,0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 100) { return vec3{0,0,11.180339887498948*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 101) { return vec3{0,0,125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 102) { return vec3{0,0,-125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 103) { return vec3{0,0,11.180339887498948*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 104) { return vec3{0,0,-11.180339887498948482*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 105) { return vec3{0,0,-125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 106) { return vec3{0,0,125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 107) { return vec3{0,0,-11.180339887498948482*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 108) { return vec3{0,0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 109) { return vec3{0,0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 110) { return vec3{0,0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 111) { return vec3{0,0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(1.4788305577012361475298776 + xi[2]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 112) { return vec3{0,0,-6.66666666666666666666666667*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 113) { return vec3{0,0,-74.53559924999299*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 114) { return vec3{0,0,74.53559924999298988*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 115) { return vec3{0,0,-6.66666666666666666666666667*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 116) { return vec3{0,0,-74.53559924999299*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 117) { return vec3{0,0,-833.3333333333333*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 118) { return vec3{0,0,833.3333333333333*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 119) { return vec3{0,0,-74.53559924999299*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 120) { return vec3{0,0,74.53559924999298988*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 121) { return vec3{0,0,833.3333333333333*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 122) { return vec3{0,0,-833.3333333333333333*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 123) { return vec3{0,0,74.53559924999298988*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 124) { return vec3{0,0,-6.66666666666666666666666667*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 125) { return vec3{0,0,-74.53559924999299*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 126) { return vec3{0,0,74.53559924999298988*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 127) { return vec3{0,0,-6.66666666666666666666666667*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(-0.88729833462074168851792654 + xi[2])*(-0.11270166537925831148207346 + xi[2])}; } + if (i == 128) { return vec3{0,0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 129) { return vec3{0,0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 130) { return vec3{0,0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 131) { return vec3{0,0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 132) { return vec3{0,0,11.180339887498948*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 133) { return vec3{0,0,125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 134) { return vec3{0,0,-125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 135) { return vec3{0,0,11.180339887498948*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 136) { return vec3{0,0,-11.180339887498948482*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 137) { return vec3{0,0,-125.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 138) { return vec3{0,0,125.*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 139) { return vec3{0,0,-11.180339887498948482*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 140) { return vec3{0,0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 141) { return vec3{0,0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 142) { return vec3{0,0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + if (i == 143) { return vec3{0,0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1]))*(0.1878361089654305191367891 + xi[2]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[2]))}; } + } + + return {}; + } + + constexpr vec3 shape_function_curl(vec3 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) { return vec3{0,-1 + xi[1],1 - xi[2]}; } + if (i == 1) { return vec3{0,-xi[1],-1 + xi[2]}; } + if (i == 2) { return vec3{0,1 - xi[1],xi[2]}; } + if (i == 3) { return vec3{0,xi[1],-xi[2]}; } + if (i == 4) { return vec3{1 - xi[0],0,-1 + xi[2]}; } + if (i == 5) { return vec3{xi[0],0,1 - xi[2]}; } + if (i == 6) { return vec3{-1 + xi[0],0,-xi[2]}; } + if (i == 7) { return vec3{-xi[0],0,xi[2]}; } + if (i == 8) { return vec3{-1 + xi[0],1 - xi[1],0}; } + if (i == 9) { return vec3{-xi[0],-1 + xi[1],0}; } + if (i == 10) { return vec3{1 - xi[0],xi[1],0}; } + if (i == 11) { return vec3{xi[0],-xi[1],0}; } + } + if (p == 2) { + if (i == 0) { return vec3{0,-13.8564064605510183482195707*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.75 + 1.*xi[2]),13.856406460551018348219571*(-0.7886751345948128822545743902 + xi[0])*(-0.75 + 1.*xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 1) { return vec3{0,13.85640646055101834821957*(-0.2113248654051871177454256 + 1.*xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.75 + 1.*xi[2]),-13.85640646055101834821957*(-0.2113248654051871177454256 + 1.*xi[0])*(-0.75 + 1.*xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 2) { return vec3{0,27.7128129211020366964391415*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*xi[1]*(-0.75 + 1.*xi[2]),-27.712812921102036696439141*(-0.7886751345948128822545743902 + xi[0])*(-0.5 + 1.*xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 3) { return vec3{0,-27.71281292110203669643914*(-0.2113248654051871177454256 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.75 + 1.*xi[2]),4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + 2*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2])}; } + if (i == 4) { return vec3{0,-13.8564064605510183482195707*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.75 + 1.*xi[2]),13.856406460551018348219571*(-0.7886751345948128822545743902 + xi[0])*(-0.25 + 1.*xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 5) { return vec3{0,13.85640646055101834821957*(-0.2113248654051871177454256 + 1.*xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.75 + 1.*xi[2]),(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(1 - 4*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2])}; } + if (i == 6) { return vec3{0,27.7128129211020366964391415*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.5 + 1.*xi[2]),-27.712812921102036696439141*(-0.7886751345948128822545743902 + xi[0])*(-0.75 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 7) { return vec3{0,4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(1 - 2*xi[2]),27.71281292110203669643914*(-0.2113248654051871177454256 + 1.*xi[0])*(-0.75 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 8) { return vec3{0,-55.42562584220407*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*xi[1]*(-0.5 + 1.*xi[2]),55.42562584220407*(-0.7886751345948128822545743902 + xi[0])*(-0.5 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 9) { return vec3{0,55.42562584220407*(-0.2113248654051871177454256 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.5 + 1.*xi[2]),-55.42562584220407*(-0.2113248654051871177454256 + 1.*xi[0])*(-0.5 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 10) { return vec3{0,27.7128129211020366964391415*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.5 + 1.*xi[2]),-27.712812921102036696439141*(-0.7886751345948128822545743902 + xi[0])*(-0.25 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 11) { return vec3{0,4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1]*(-1 + 2*xi[1])*(1 - 2*xi[2]),4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + 4*xi[1])*(-1 + xi[2])*xi[2]}; } + if (i == 12) { return vec3{0,-13.8564064605510183482195707*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.25 + 1.*xi[2]),13.856406460551018348219571*(-0.7886751345948128822545743902 + xi[0])*(-0.75 + 1.*xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 13) { return vec3{0,(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-1 + 4*xi[2]),-13.85640646055101834821957*(-0.2113248654051871177454256 + 1.*xi[0])*(-0.75 + 1.*xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 14) { return vec3{0,27.7128129211020366964391415*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*xi[1]*(-0.25 + 1.*xi[2]),-27.712812921102036696439141*(-0.7886751345948128822545743902 + xi[0])*(-0.5 + 1.*xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 15) { return vec3{0,4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*xi[1]*(1 - 4*xi[2]),4*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + 2*xi[1])*xi[2]*(-1 + 2*xi[2])}; } + if (i == 16) { return vec3{0,-13.8564064605510183482195707*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.25 + 1.*xi[2]),13.856406460551018348219571*(-0.7886751345948128822545743902 + xi[0])*(-0.25 + 1.*xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 17) { return vec3{0,(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1]*(-1 + 2*xi[1])*(-1 + 4*xi[2]),(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(1 - 4*xi[1])*xi[2]*(-1 + 2*xi[2])}; } + if (i == 18) { return vec3{13.8564064605510183482195707*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-0.75 + 1.*xi[2]),0,-13.856406460551018348219571*(-0.75 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 19) { return vec3{-27.7128129211020366964391415*(-1. + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])*(-0.75 + 1.*xi[2]),0,27.71281292110203669643914*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 20) { return vec3{13.8564064605510183482195707*xi[0]*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-0.75 + 1.*xi[2]),0,-13.856406460551018348219571*(-0.25 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 21) { return vec3{-13.856406460551018348219571*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.21132486540518711774542561 + 1.*xi[1])*(-0.75 + 1.*xi[2]),0,13.856406460551018348219571*(-0.75 + 1.*xi[0])*(-0.21132486540518711774542561 + 1.*xi[1])*(-1. + xi[2])*(-0.5 + 1.*xi[2])}; } + if (i == 22) { return vec3{27.712812921102036696439141*(-1. + xi[0])*xi[0]*(-0.21132486540518711774542561 + 1.*xi[1])*(-0.75 + 1.*xi[2]),0,4*(1 - 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2])}; } + if (i == 23) { return vec3{-13.856406460551018348219571*xi[0]*(-0.5 + 1.*xi[0])*(-0.21132486540518711774542561 + 1.*xi[1])*(-0.75 + 1.*xi[2]),0,(-1 + 4*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*(-1 + 2*xi[2])}; } + if (i == 24) { return vec3{-27.7128129211020366964391415*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-0.5 + 1.*xi[2]),0,27.71281292110203669643914*(-0.75 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 25) { return vec3{55.42562584220407*(-1. + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])*(-0.5 + 1.*xi[2]),0,-55.42562584220407*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 26) { return vec3{-27.7128129211020366964391415*xi[0]*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-0.5 + 1.*xi[2]),0,27.71281292110203669643914*(-0.25 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 27) { return vec3{4*(-1 + xi[0])*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + 2*xi[2]),0,-27.71281292110203669643914*(-0.75 + 1.*xi[0])*(-0.21132486540518711774542561 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 28) { return vec3{-55.42562584220407*(-1. + xi[0])*xi[0]*(-0.21132486540518711774542561 + 1.*xi[1])*(-0.5 + 1.*xi[2]),0,55.42562584220407*(-0.5 + 1.*xi[0])*(-0.21132486540518711774542561 + 1.*xi[1])*(-1. + xi[2])*xi[2]}; } + if (i == 29) { return vec3{4*xi[0]*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + 2*xi[2]),0,4*(1 - 4*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + xi[2])*xi[2]}; } + if (i == 30) { return vec3{13.8564064605510183482195707*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-0.25 + 1.*xi[2]),0,-13.856406460551018348219571*(-0.75 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 31) { return vec3{-27.7128129211020366964391415*(-1. + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])*(-0.25 + 1.*xi[2]),0,27.71281292110203669643914*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 32) { return vec3{13.8564064605510183482195707*xi[0]*(-0.5 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*(-0.25 + 1.*xi[2]),0,-13.856406460551018348219571*(-0.25 + 1.*xi[0])*(-0.7886751345948128822545743902 + xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 33) { return vec3{(-1 + xi[0])*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(1 - 4*xi[2]),0,13.856406460551018348219571*(-0.75 + 1.*xi[0])*(-0.21132486540518711774542561 + 1.*xi[1])*xi[2]*(-0.5 + 1.*xi[2])}; } + if (i == 34) { return vec3{4*(-1 + xi[0])*xi[0]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(-1 + 4*xi[2]),0,4*(1 - 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*xi[2]*(-1 + 2*xi[2])}; } + if (i == 35) { return vec3{xi[0]*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*(1 - 4*xi[2]),0,(-1 + 4*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])*xi[2]*(-1 + 2*xi[2])}; } + if (i == 36) { return vec3{-13.856406460551018348219571*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.75 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),13.856406460551018348219571*(-0.75 + 1.*xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 37) { return vec3{27.712812921102036696439141*(-1. + xi[0])*xi[0]*(-0.75 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),-27.71281292110203669643914*(-0.5 + 1.*xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 38) { return vec3{-13.856406460551018348219571*xi[0]*(-0.5 + 1.*xi[0])*(-0.75 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),13.856406460551018348219571*(-0.25 + 1.*xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 39) { return vec3{27.712812921102036696439141*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),-27.71281292110203669643914*(-0.75 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 40) { return vec3{-55.42562584220407*(-1. + xi[0])*xi[0]*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),55.42562584220407*(-0.5 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 41) { return vec3{27.712812921102036696439141*xi[0]*(-0.5 + 1.*xi[0])*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),-27.71281292110203669643914*(-0.25 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 42) { return vec3{-13.856406460551018348219571*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.25 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),13.856406460551018348219571*(-0.75 + 1.*xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 43) { return vec3{27.712812921102036696439141*(-1. + xi[0])*xi[0]*(-0.25 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),-27.71281292110203669643914*(-0.5 + 1.*xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 44) { return vec3{-13.856406460551018348219571*xi[0]*(-0.5 + 1.*xi[0])*(-0.25 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),13.856406460551018348219571*(-0.25 + 1.*xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.78867513459481288225457439 + xi[2]),0}; } + if (i == 45) { return vec3{13.856406460551018348219571*(-1. + xi[0])*(-0.5 + 1.*xi[0])*(-0.75 + 1.*xi[1])*(-0.21132486540518711774542561 + 1.*xi[2]),-13.856406460551018348219571*(-0.75 + 1.*xi[0])*(-1. + xi[1])*(-0.5 + 1.*xi[1])*(-0.21132486540518711774542561 + 1.*xi[2]),0}; } + if (i == 46) { return vec3{-27.712812921102036696439141*(-1. + xi[0])*xi[0]*(-0.75 + 1.*xi[1])*(-0.21132486540518711774542561 + 1.*xi[2]),4*(-1 + 2*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),0}; } + if (i == 47) { return vec3{13.856406460551018348219571*xi[0]*(-0.5 + 1.*xi[0])*(-0.75 + 1.*xi[1])*(-0.21132486540518711774542561 + 1.*xi[2]),(1 - 4*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),0}; } + if (i == 48) { return vec3{4*(-1 + xi[0])*(-1 + 2*xi[0])*(1 - 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),27.712812921102036696439141*(-0.75 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.21132486540518711774542561 + 1.*xi[2]),0}; } + if (i == 49) { return vec3{55.42562584220407*(-1. + xi[0])*xi[0]*(-0.5 + 1.*xi[1])*(-0.21132486540518711774542561 + 1.*xi[2]),-55.42562584220407*(-0.5 + 1.*xi[0])*(-1. + xi[1])*xi[1]*(-0.21132486540518711774542561 + 1.*xi[2]),0}; } + if (i == 50) { return vec3{4*xi[0]*(-1 + 2*xi[0])*(1 - 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),4*(-1 + 4*xi[0])*(-1 + xi[1])*xi[1]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),0}; } + if (i == 51) { return vec3{(-1 + xi[0])*(-1 + 2*xi[0])*(-1 + 4*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),-13.856406460551018348219571*(-0.75 + 1.*xi[0])*xi[1]*(-0.5 + 1.*xi[1])*(-0.21132486540518711774542561 + 1.*xi[2]),0}; } + if (i == 52) { return vec3{4*(-1 + xi[0])*xi[0]*(1 - 4*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),4*(-1 + 2*xi[0])*xi[1]*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),0}; } + if (i == 53) { return vec3{xi[0]*(-1 + 2*xi[0])*(-1 + 4*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),(1 - 4*xi[0])*xi[1]*(-1 + 2*xi[1])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[2]),0}; } + } + if (p == 3) { + if (i == 0) { return vec3{0,250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),-250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 1) { return vec3{0,-500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 2) { return vec3{0,250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),-250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 3) { return vec3{0,-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 4) { return vec3{0,1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),-1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 5) { return vec3{0,-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 6) { return vec3{0,559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 7) { return vec3{0,-1118.0339887498948*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 8) { return vec3{0,559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 9) { return vec3{0,-250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 10) { return vec3{0,500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),-500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 11) { return vec3{0,-250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 12) { return vec3{0,-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),559.0169943749474*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 13) { return vec3{0,1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),-1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 14) { return vec3{0,-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),559.0169943749474*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 15) { return vec3{0,1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),-1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 16) { return vec3{0,-2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 17) { return vec3{0,1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),-1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 18) { return vec3{0,-1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 19) { return vec3{0,2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),-2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 20) { return vec3{0,-1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 21) { return vec3{0,559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 22) { return vec3{0,-1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),1118.03398874989*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 23) { return vec3{0,559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 24) { return vec3{0,559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 25) { return vec3{0,-1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 26) { return vec3{0,559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 27) { return vec3{0,-1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 28) { return vec3{0,2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),-2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 29) { return vec3{0,-1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 30) { return vec3{0,1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),-1250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 31) { return vec3{0,-2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),2500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 32) { return vec3{0,1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),-1250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 33) { return vec3{0,-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 34) { return vec3{0,1118.03398874989*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),-1118.03398874989*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 35) { return vec3{0,-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 36) { return vec3{0,-250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 37) { return vec3{0,500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),-500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 38) { return vec3{0,-250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 39) { return vec3{0,559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 40) { return vec3{0,-1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),1118.03398874989*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 41) { return vec3{0,559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 42) { return vec3{0,-559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),559.016994374947*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 43) { return vec3{0,1118.033988749895*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),-1118.03398874989*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 44) { return vec3{0,-559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),559.016994374947*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 45) { return vec3{0,250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),-250.*(0.4436491673103708 + xi[0]*(-1.387298334620742 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 46) { return vec3{0,-500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),500.*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 47) { return vec3{0,250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),-250.*(0.05635083268962916 + xi[0]*(-0.6127016653792583 + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 48) { return vec3{-250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 49) { return vec3{559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,-559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 50) { return vec3{-559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,559.01699437495*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 51) { return vec3{250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,-250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 52) { return vec3{500.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,-500.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 53) { return vec3{-1118.03398874989*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,1118.03398874989*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 54) { return vec3{1118.0339887498948*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,-1118.033988749895*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 55) { return vec3{-500.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,500.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 56) { return vec3{-250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 57) { return vec3{559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,-559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 58) { return vec3{-559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,559.01699437495*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 59) { return vec3{250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.4 + xi[2]*(-1.333333333333333 + 1.*xi[2])),0,-250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-0.2 + xi[2]*(1.2 + xi[2]*(-2. + 1.*xi[2])))}; } + if (i == 60) { return vec3{559.016994374947*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,-559.016994374947*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 61) { return vec3{-1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 62) { return vec3{1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,-1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 63) { return vec3{-559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,559.016994374947*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 64) { return vec3{-1118.033988749895*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,1118.033988749895*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 65) { return vec3{2500.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,-2500.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 66) { return vec3{-2500.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,2500.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 67) { return vec3{1118.033988749895*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,-1118.03398874989*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 68) { return vec3{559.016994374947*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,-559.0169943749474*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 69) { return vec3{-1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 70) { return vec3{1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,-1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 71) { return vec3{-559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.2412022659166597 + xi[2]*(-1.149071198499986 + 1.*xi[2])),0,559.016994374947*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*xi[2]*(-0.723606797749979 + 1.*xi[2])}; } + if (i == 72) { return vec3{-559.0169943749474*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,559.01699437495*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 73) { return vec3{1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,-1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 74) { return vec3{-1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 75) { return vec3{559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,-559.01699437495*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 76) { return vec3{1118.033988749895*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,-1118.0339887499*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 77) { return vec3{-2500.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,2500.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 78) { return vec3{2500.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,-2500.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 79) { return vec3{-1118.03398874989*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,1118.0339887499*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 80) { return vec3{-559.0169943749474*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,559.01699437495*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 81) { return vec3{1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,-1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 82) { return vec3{-1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 83) { return vec3{559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.0921310674166737 + xi[2]*(-0.850928801500014 + 1.*xi[2])),0,-559.01699437495*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(-1. + xi[2])*(-0.2763932022500210304 + xi[2])*xi[2]}; } + if (i == 84) { return vec3{250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,-250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 85) { return vec3{-559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 86) { return vec3{559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,-559.016994374947*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 87) { return vec3{-250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.44364916731037084 + xi[1]*(-1.3872983346207417 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 88) { return vec3{-500.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,500.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 89) { return vec3{1118.03398874989*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,-1118.03398874989*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 90) { return vec3{-1118.033988749895*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,1118.033988749895*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 91) { return vec3{500.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,-500.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831 + xi[1])*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 92) { return vec3{250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,-250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 93) { return vec3{-559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 94) { return vec3{559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,-559.016994374947*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 95) { return vec3{-250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*(0.06666666666666667 + xi[2]*(-0.6666666666666667 + 1.*xi[2])),0,250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(0.05635083268962916 + xi[1]*(-0.6127016653792583 + 1.*xi[1]))*xi[2]*(0.2 + xi[2]*(-1. + 1.*xi[2]))}; } + if (i == 96) { return vec3{250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 97) { return vec3{-559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 98) { return vec3{559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-559.016994374947*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 99) { return vec3{-250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 100) { return vec3{-559.016994374947*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),559.016994374947*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 101) { return vec3{1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 102) { return vec3{-1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 103) { return vec3{559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-559.016994374947*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 104) { return vec3{559.016994374947*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-559.01699437495*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 105) { return vec3{-1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 106) { return vec3{1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 107) { return vec3{-559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),559.01699437495*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 108) { return vec3{-250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 109) { return vec3{559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 110) { return vec3{-559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),559.016994374947*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 111) { return vec3{250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.4436491673103708 + xi[2]*(-1.387298334620742 + 1.*xi[2])),-250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.443649167310371 + xi[2]*(-1.387298334620742 + 1.*xi[2])),0}; } + if (i == 112) { return vec3{-500.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),500.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 113) { return vec3{1118.03398874989*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-1118.03398874989*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 114) { return vec3{-1118.033988749895*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),1118.033988749895*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 115) { return vec3{500.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-500.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 116) { return vec3{1118.03398874989*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-1118.033988749895*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 117) { return vec3{-2500.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),2500.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 118) { return vec3{2500.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-2500.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 119) { return vec3{-1118.03398874989*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),1118.03398874989*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 120) { return vec3{-1118.033988749895*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),1118.0339887499*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 121) { return vec3{2500.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-2500.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 122) { return vec3{-2500.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),2500.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 123) { return vec3{1118.03398874989*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-1118.0339887499*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(-0.88729833462074 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 124) { return vec3{500.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),-500.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 125) { return vec3{-1118.03398874989*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),1118.03398874989*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 126) { return vec3{1118.033988749895*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.88729833462074 + xi[2])*(-0.11270166537925831 + xi[2]),-1118.033988749895*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 127) { return vec3{-500.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),500.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(-0.887298334620742 + xi[2])*(-0.11270166537925831 + xi[2]),0}; } + if (i == 128) { return vec3{250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 129) { return vec3{-559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 130) { return vec3{559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-559.01699437495*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 131) { return vec3{-250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.4 + xi[1]*(-1.3333333333333333 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-0.2 + xi[1]*(1.2 + xi[1]*(-2. + 1.*xi[1])))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 132) { return vec3{-559.016994374947*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),559.016994374947*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 133) { return vec3{1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 134) { return vec3{-1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 135) { return vec3{559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.24120226591666 + xi[1]*(-1.149071198499986 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-559.016994374947*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1])*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 136) { return vec3{559.0169943749474*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-559.01699437495*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 137) { return vec3{-1250.*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),1250.*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 138) { return vec3{1250.*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-1250.*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 139) { return vec3{-559.016994374947*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.0921310674166737 + xi[1]*(-0.850928801500014 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),559.01699437495*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1]*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 140) { return vec3{-250.*(-0.2 + xi[0]*(1.2 + xi[0]*(-2. + 1.*xi[0])))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),250.*(0.4 + xi[0]*(-1.333333333333333 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 141) { return vec3{559.016994374947*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-559.016994374947*(0.24120226591666 + xi[0]*(-1.149071198499986 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 142) { return vec3{-559.016994374947*(-1. + xi[0])*(-0.27639320225002103 + xi[0])*xi[0]*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),559.016994374947*(0.092131067416674 + xi[0]*(-0.85092880150001 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + if (i == 143) { return vec3{250.*xi[0]*(0.2 + xi[0]*(-1. + 1.*xi[0]))*(0.0666666666666667 + xi[1]*(-0.6666666666666667 + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),-250.*(0.0666666666666667 + xi[0]*(-0.666666666666667 + 1.*xi[0]))*xi[1]*(0.2 + xi[1]*(-1. + 1.*xi[1]))*(0.05635083268962916 + xi[2]*(-0.6127016653792583 + 1.*xi[2])),0}; } + } + + return {}; + } + + constexpr vec3 shape_function_derivative(vec3 xi, uint32_t i) const { + return shape_function_curl(xi, i); + } + + vec3 interpolate(vec3 xi, const double * values) { + vec3 interpolated_value{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_value += values[i] * shape_function(xi, i); + } + return interpolated_value; + } + + vec3 curl(vec3 xi, const double * values) { + vec3 interpolated_curl{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_curl += values[i] * shape_function_curl(xi, i); + } + return interpolated_curl; + } + + // TODO: set to nonzero when reenabling sum-factorization implementations + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view) const { + return 0; + } + +#if 0 + + // sum-factorization implementations + + nd::array< double > evaluate_shape_functions(nd::view xi) { + uint32_t q = xi.shape[0]; + nd::array buffer({q * (2 * p + 1)}); + for (int i = 0; i < q; i++) { + GaussLegendreInterpolation(xi(i, 0), p, &buffer(p * i)); + GaussLobattoInterpolation(xi(i, 0), p+1, &buffer(q * p + p * i)); + } + return buffer; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view buffer) { + uint32_t n = p + 1; + uint32_t q = values_q.shape[0]; + + // 1D shape function evaluations + nd::view B1(buffer.data(), {q, p}); // legendre shape functions + nd::view B2(B1.end(), {q, p+1}); // lobatto shape functions + nd::view A1(B2.end(), {q, p+1, p+1}); // storage for intermediates + nd::view A2(A1.end(), {q, q, p+1}); // storage for intermediates + + for (int d = 0; d < 3; d++) { + nd::view ue(values_e.data() + (n * n * p * d), {n, n, p}); + nd::view uq = nd::reshape<3>(values_q(d), {q, q, q}); + + contract(ue, B1, A1); // A1(qx, iz, iy) = sum_{ix} ue(iz, iy, ix) * B1(qx, ix) + contract(A1, B2, A2); // A2(qy, qx, iz) = sum_{iy} A1(qx, iz, iy) * B2(qy, iy) + contract(A2, B2, uq); // uq(qz, qy, qx) = sum_{iz} A2(qy, qx, iz) * B2(qz, iz) + } + } + + nd::array< double > evaluate_shape_function_curls(nd::view xi) { + uint32_t q = xi.shape[0]; + nd::array buffer({q * (3 * p + 2)}); + for (int i = 0; i < q; i++) { + GaussLegendreInterpolation(xi(i, 0), p, &buffer(p * i)); + GaussLobattoInterpolation(xi(i, 0), p+1, &buffer(q * p + p * i)); + GaussLobattoInterpolationDerivative(xi(i, 0), p+1, &buffer(q * p + p * i)); + } + return buffer; + } + + void curl(nd::view values_q, nd::view values_e, nd::view buffer) { + uint32_t n = p + 1; + uint32_t q = values_q.shape[0]; + + // 1D shape function evaluations + nd::view B1(buffer.data(), {q, p}); // legendre shape functions + nd::view B2(B1.end(), {q, p+1}); // lobatto shape functions + nd::view A1(B2.end(), {q, p+1, p+1}); // storage for intermediates + nd::view A2(A1.end(), {q, q, p+1}); // storage for intermediates + + for (int d = 0; d < 3; d++) { + nd::view ue(values_e.data() + (n * n * p * d), {n, n, p}); + nd::view uq = nd::reshape<3>(values_q(d), {q, q, q}); + + contract(ue, B1, A1); // A1(qx, iz, iy) = sum_{ix} ue(iz, iy, ix) * B1(qx, ix) + contract(A1, B2, A2); // A2(qy, qx, iz) = sum_{iy} A1(qx, iz, iy) * B2(qy, iy) + contract(A2, B2, uq); // uq(qz, qy, qx) = sum_{iz} A2(qy, qx, iz) * B2(qz, iz) + } + } +#else + + // non-sum-factorization implementations + + nd::array< double, 3 > evaluate_shape_functions(nd::view xi) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q * q, num_nodes(), 3}); + uint32_t qcount = 0; + for (uint32_t k = 0; k < q; k++) { + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + vec3 xi_ijk = vec3{xi(i, 0), xi(j, 0), xi(k, 0)}; + for (uint32_t l = 0; l < num_nodes(); l++) { + vec3 phi = shape_function(xi_ijk, l); + shape_fns(qcount, l, 0) = phi[0]; + shape_fns(qcount, l, 1) = phi[1]; + shape_fns(qcount, l, 2) = phi[2]; + } + qcount++; + } + } + } + return shape_fns; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + value_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + for (uint32_t c = 0; c < 3; c++) { + sum[c] += shape_fns(q, i, c) * values_e(i); + } + } + values_q(q) = sum; + } + } + + nd::array< double, 3 > evaluate_shape_function_curls(nd::view xi) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q * q, num_nodes(), 3}); + uint32_t qcount = 0; + for (uint32_t k = 0; k < q; k++) { + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + vec3 xi_ijk = vec3{xi(i, 0), xi(j, 0), xi(k, 0)}; + for (uint32_t l = 0; l < num_nodes(); l++) { + vec3 curl_phi = shape_function_curl(xi_ijk, l); + shape_fns(qcount, l, 0) = curl_phi[0]; + shape_fns(qcount, l, 1) = curl_phi[1]; + shape_fns(qcount, l, 2) = curl_phi[2]; + } + qcount++; + } + } + } + return shape_fns; + } + + void curl(nd::view values_q, nd::view values_e, nd::view shape_fn_curls, double * /*buffer*/) { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + derivative_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + for (uint32_t c = 0; c < 3; c++) { + sum[c] += shape_fn_curls(q, i, c) * values_e(i); + } + } + values_q(q) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_functions(nd::view xi, nd::view weights) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q * q, num_nodes(), dim}); + uint32_t qcount = 0; + for (uint32_t k = 0; k < q; k++) { + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + vec3 xi_ijk = vec3{xi(i, 0), xi(j, 0), xi(k, 0)}; + for (uint32_t l = 0; l < num_nodes(); l++) { + vec3 phi = shape_function(xi_ijk, l); + shape_fns(qcount, l, 0) = phi[0] * weights[i] * weights[j] * weights[k]; + shape_fns(qcount, l, 1) = phi[1] * weights[i] * weights[j] * weights[k]; + shape_fns(qcount, l, 2) = phi[2] * weights[i] * weights[j] * weights[k]; + } + qcount++; + } + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /* buffer */) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (uint32_t j = 0; j < dim; j++) { + sum += shape_fn(q, i, j) * source_q(q)[j]; + } + } + residual_e(i) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_function_curls(nd::view xi, nd::view weights) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q * q, num_nodes(), dim}); + uint32_t qcount = 0; + for (uint32_t k = 0; k < q; k++) { + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + vec3 xi_ijk = vec3{xi(i, 0), xi(j, 0), xi(k, 0)}; + for (uint32_t l = 0; l < num_nodes(); l++) { + vec3 dphi = shape_function_curl(xi_ijk, l); + shape_fns(qcount, l, 0) = dphi[0] * weights[i] * weights[j] * weights[k]; + shape_fns(qcount, l, 1) = dphi[1] * weights[i] * weights[j] * weights[k]; + shape_fns(qcount, l, 2) = dphi[2] * weights[i] * weights[j] * weights[k]; + } + qcount++; + } + } + } + return shape_fns; + } + + void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (uint32_t j = 0; j < dim; j++) { + sum += shape_fn_curl(q, i, j) * flux_q(q)[j]; + } + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + int nnodes = num_nodes(); + int nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (int q = 0; q < nqpts; q++) { + for (int d = 0; d < dim; d++) { + sum += shape_fn_curl(q, i, d) * flux_q(q)[d]; + } + } + residual_e(i) = sum; + } + } + #endif + +#endif + + uint32_t p; + +}; +// clang-format on + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/hcurl_quadrilateral.hpp b/src/serac/numerics/refactor/elements/hcurl_quadrilateral.hpp new file mode 100644 index 0000000000..b7d44200a2 --- /dev/null +++ b/src/serac/numerics/refactor/elements/hcurl_quadrilateral.hpp @@ -0,0 +1,361 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +using namespace serac; + +// clang-format off +template <> +struct FiniteElement { + + using value_type = vec2; + using derivative_type = vec1; + + using source_type = vec2; + using flux_type = vec1; + + static constexpr int dim = 2; + + SERAC_HOST_DEVICE uint32_t num_nodes() const { return 2 * p * (p + 1); } + + constexpr vec2 shape_function(vec2 xi, uint32_t i) const { + if (p == 1) { + if (i == 0) { return vec2{1 - xi[1],0}; } + if (i == 1) { return vec2{xi[1],0}; } + if (i == 2) { return vec2{0,1 - xi[0]}; } + if (i == 3) { return vec2{0,xi[0]}; } + } + if (p == 2) { + if (i == 0) { return vec2{-1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1])*(-1 + 2*xi[1]),0}; } + if (i == 1) { return vec2{(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1])*(-1 + 2*xi[1]),0}; } + if (i == 2) { return vec2{6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1])*xi[1],0}; } + if (i == 3) { return vec2{-6.92820323027550917410978537*(-0.21132486540518711774542561 + 1.*xi[0])*(-1. + xi[1])*xi[1],0}; } + if (i == 4) { return vec2{-1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*xi[1]*(-1 + 2*xi[1]),0}; } + if (i == 5) { return vec2{(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1]*(-1 + 2*xi[1]),0}; } + if (i == 6) { return vec2{0,-1.7320508075688772935274463415*(-1 + xi[0])*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])}; } + if (i == 7) { return vec2{0,(-1 + xi[0])*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])}; } + if (i == 8) { return vec2{0,6.928203230275509174109785366*(-1. + xi[0])*xi[0]*(-0.7886751345948128822545743902 + xi[1])}; } + if (i == 9) { return vec2{0,-6.92820323027550917410978537*(-1. + xi[0])*xi[0]*(-0.21132486540518711774542561 + 1.*xi[1])}; } + if (i == 10) { return vec2{0,-1.7320508075688772935274463415*xi[0]*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1])}; } + if (i == 11) { return vec2{0,xi[0]*(-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1])}; } + } + if (p == 3) { + if (i == 0) { return vec2{(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1])),0}; } + if (i == 1) { return vec2{-6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1])),0}; } + if (i == 2) { return vec2{(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(1 + xi[1]*(-6. + (10. - 5.*xi[1])*xi[1])),0}; } + if (i == 3) { return vec2{11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1]),0}; } + if (i == 4) { return vec2{-74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1]),0}; } + if (i == 5) { return vec2{11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1]*(-0.723606797749979 + 1.*xi[1]),0}; } + if (i == 6) { return vec2{-11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1],0}; } + if (i == 7) { return vec2{74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1],0}; } + if (i == 8) { return vec2{-11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1])*xi[1],0}; } + if (i == 9) { return vec2{(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1])),0}; } + if (i == 10) { return vec2{-6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1])),0}; } + if (i == 11) { return vec2{(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(1. + xi[1]*(-5. + 5.*xi[1])),0}; } + if (i == 12) { return vec2{0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 13) { return vec2{0,-6.66666666666666666666666667*(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])}; } + if (i == 14) { return vec2{0,(1 + xi[0]*(-6. + (10. - 5.*xi[0])*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 15) { return vec2{0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 16) { return vec2{0,-74.53559924999299*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])}; } + if (i == 17) { return vec2{0,11.180339887498948*(-1. + xi[0])*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 18) { return vec2{0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 19) { return vec2{0,74.53559924999298988*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])}; } + if (i == 20) { return vec2{0,-11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 21) { return vec2{0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1]))}; } + if (i == 22) { return vec2{0,-6.66666666666666666666666667*xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1])}; } + if (i == 23) { return vec2{0,xi[0]*(1. + xi[0]*(-5. + 5.*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1]))}; } + } + + return {}; + } + + constexpr vec2 reoriented_shape_function(vec2 xi, uint32_t i, int8_t transformation) const { + if (transformation == -1) { + return -shape_function(xi, i); + } else { + return shape_function(xi, i); + } + } + + vec1 shape_function_curl(vec2 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) { return 1; } + if (i == 1) { return -1; } + if (i == 2) { return -1; } + if (i == 3) { return 1; } + } + if (p == 2) { + if (i == 0) { return 3.464101615137754587054892683*(-0.7886751345948128822545743902 + xi[0])*(-1 + xi[1]) + 1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*(-1 + 2*xi[1]); } + if (i == 1) { return -2*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + xi[1]) - (-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + 2*xi[1]); } + if (i == 2) { return -6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*(-1. + xi[1]) - 6.928203230275509174109785366*(-0.7886751345948128822545743902 + xi[0])*xi[1]; } + if (i == 3) { return 6.92820323027550917410978537*(-0.21132486540518711774542561 + 1.*xi[0])*(-1. + xi[1]) + 6.92820323027550917410978537*(-0.21132486540518711774542561 + 1.*xi[0])*xi[1]; } + if (i == 4) { return 3.464101615137754587054892683*(-0.7886751345948128822545743902 + xi[0])*xi[1] + 1.7320508075688772935274463415*(-0.7886751345948128822545743902 + xi[0])*(-1 + 2*xi[1]); } + if (i == 5) { return -2*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*xi[1] - (-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[0])*(-1 + 2*xi[1]); } + if (i == 6) { return -3.464101615137754587054892683*(-1 + xi[0])*(-0.7886751345948128822545743902 + xi[1]) - 1.7320508075688772935274463415*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1]); } + if (i == 7) { return 2*(-1 + xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1]) + (-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1]); } + if (i == 8) { return 6.928203230275509174109785366*(-1. + xi[0])*(-0.7886751345948128822545743902 + xi[1]) + 6.928203230275509174109785366*xi[0]*(-0.7886751345948128822545743902 + xi[1]); } + if (i == 9) { return -6.92820323027550917410978537*(-1. + xi[0])*(-0.21132486540518711774542561 + 1.*xi[1]) - 6.92820323027550917410978537*xi[0]*(-0.21132486540518711774542561 + 1.*xi[1]); } + if (i == 10) { return -3.464101615137754587054892683*xi[0]*(-0.7886751345948128822545743902 + xi[1]) - 1.7320508075688772935274463415*(-1 + 2*xi[0])*(-0.7886751345948128822545743902 + xi[1]); } + if (i == 11) { return 2*xi[0]*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1]) + (-1 + 2*xi[0])*(-0.3660254037844386467637231708 + 1.7320508075688772935274463415*xi[1]); } + } + if (p == 3) { + if (i == 0) { return -((1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-6. + (10. - 10.*xi[1])*xi[1] + (10. - 5.*xi[1])*xi[1])); } + if (i == 1) { return 6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-6. + (10. - 10.*xi[1])*xi[1] + (10. - 5.*xi[1])*xi[1]); } + if (i == 2) { return -((0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-6. + (10. - 10.*xi[1])*xi[1] + (10. - 5.*xi[1])*xi[1])); } + if (i == 3) { return -11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1] - 11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.723606797749979 + 1.*xi[1]) - 11.180339887498948*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(-0.723606797749979 + 1.*xi[1]); } + if (i == 4) { return 74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1] + 74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.723606797749979 + 1.*xi[1]) + 74.53559924999299*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(-0.723606797749979 + 1.*xi[1]); } + if (i == 5) { return -11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1] - 11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.723606797749979 + 1.*xi[1]) - 11.180339887498948*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(-0.723606797749979 + 1.*xi[1]); } + if (i == 6) { return 11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1]) + 11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1] + 11.180339887498948482*(1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(-0.2763932022500210304 + xi[1])*xi[1]; } + if (i == 7) { return -74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*(-0.2763932022500210304 + xi[1]) - 74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-1. + xi[1])*xi[1] - 74.53559924999298988*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(-0.2763932022500210304 + xi[1])*xi[1]; } + if (i == 8) { return 11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*(-0.2763932022500210304 + xi[1]) + 11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-1. + xi[1])*xi[1] + 11.180339887498948482*(0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(-0.2763932022500210304 + xi[1])*xi[1]; } + if (i == 9) { return -((1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*xi[1]*(-5. + 10.*xi[1])) - (1.4788305577012361475298776 + xi[0]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[0]))*(1. + xi[1]*(-5. + 5.*xi[1])); } + if (i == 10) { return 6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*xi[1]*(-5. + 10.*xi[1]) + 6.66666666666666666666666667*(-0.88729833462074168851792654 + xi[0])*(-0.11270166537925831148207346 + xi[0])*(1. + xi[1]*(-5. + 5.*xi[1])); } + if (i == 11) { return -((0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*xi[1]*(-5. + 10.*xi[1])) - (0.1878361089654305191367891 + xi[0]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[0]))*(1. + xi[1]*(-5. + 5.*xi[1])); } + if (i == 12) { return (-6. + (10. - 10.*xi[0])*xi[0] + (10. - 5.*xi[0])*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])); } + if (i == 13) { return -6.66666666666666666666666667*(-6. + (10. - 10.*xi[0])*xi[0] + (10. - 5.*xi[0])*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]); } + if (i == 14) { return (-6. + (10. - 10.*xi[0])*xi[0] + (10. - 5.*xi[0])*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])); } + if (i == 15) { return 11.180339887498948*(-1. + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])) + 11.180339887498948*(-1. + xi[0])*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])) + 11.180339887498948*xi[0]*(-0.723606797749979 + 1.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])); } + if (i == 16) { return -74.53559924999299*(-1. + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]) - 74.53559924999299*(-1. + xi[0])*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]) - 74.53559924999299*xi[0]*(-0.723606797749979 + 1.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]); } + if (i == 17) { return 11.180339887498948*(-1. + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])) + 11.180339887498948*(-1. + xi[0])*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])) + 11.180339887498948*xi[0]*(-0.723606797749979 + 1.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])); } + if (i == 18) { return -11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])) - 11.180339887498948482*(-1. + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])) - 11.180339887498948482*(-0.2763932022500210304 + xi[0])*xi[0]*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])); } + if (i == 19) { return 74.53559924999298988*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]) + 74.53559924999298988*(-1. + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]) + 74.53559924999298988*(-0.2763932022500210304 + xi[0])*xi[0]*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]); } + if (i == 20) { return -11.180339887498948482*(-1. + xi[0])*(-0.2763932022500210304 + xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])) - 11.180339887498948482*(-1. + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])) - 11.180339887498948482*(-0.2763932022500210304 + xi[0])*xi[0]*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])); } + if (i == 21) { return xi[0]*(-5. + 10.*xi[0])*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])) + (1. + xi[0]*(-5. + 5.*xi[0]))*(1.4788305577012361475298776 + xi[1]*(-4.6243277820691389617264218 + 3.3333333333333333333333333*xi[1])); } + if (i == 22) { return -6.66666666666666666666666667*xi[0]*(-5. + 10.*xi[0])*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]) - 6.66666666666666666666666667*(1. + xi[0]*(-5. + 5.*xi[0]))*(-0.88729833462074168851792654 + xi[1])*(-0.11270166537925831148207346 + xi[1]); } + if (i == 23) { return xi[0]*(-5. + 10.*xi[0])*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])) + (1. + xi[0]*(-5. + 5.*xi[0]))*(0.1878361089654305191367891 + xi[1]*(-2.0423388845975277049402449 + 3.3333333333333333333333333*xi[1])); } + } + + return {}; + } + + vec1 reoriented_shape_function_curl(vec2 xi, uint32_t i, int8_t transformation) const { + if (transformation == -1) { + return -shape_function_curl(xi, i); + } else { + return shape_function_curl(xi, i); + } + } + + vec1 shape_function_derivative(vec2 xi, uint32_t i) const { + return shape_function_curl(xi, i); + } + + vec2 interpolate(vec2 xi, const double * values) const { + vec2 interpolated_value{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_value += values[i] * shape_function(xi, i); + } + return interpolated_value; + } + + vec1 curl(vec2 xi, const double * values) const { + double interpolated_curl = 0.0; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_curl += values[i] * shape_function_curl(xi, i); + } + return interpolated_curl; + } + + // TODO: this is set to nonzero for the batched interpolation, + // even though batched curl doesn't use the buffer + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view xi) const { + uint32_t q = xi.shape[0]; + return q * (p + 1); + } + + nd::array< double > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + uint32_t num_entries = 0; + num_entries += q * p; // B1 + num_entries += q * (p + 1); // B2 + nd::array buffer({num_entries}); + for (uint32_t i = 0; i < q; i++) { + GaussLegendreInterpolation(xi(i, 0), p, &buffer(p*i)); + GaussLobattoInterpolation(xi(i, 0), p+1, &buffer((p+1)*i + (p*q))); + } + return buffer; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fn, double * buffer) const { + uint32_t n = p + 1; + uint32_t q = uint32_t(sqrt(values_q.shape[0])); + + // 1D shape function evaluations + nd::view B1(shape_fn.data(), {q, p}); // legendre shape functions + nd::view B2(B1.end(), {q, n}); // lobatto shape functions + + nd::view A1(buffer, {q, n}); // storage for intermediates + + nd::view ue(values_e.data(), {n, p}); + nd::view uq(static_cast(&values_q[0][0]), {q, q}, {2*q, 2}); + + _contract(A1, B1, ue); // A1(qx, iy) = sum_{ix} B1(qx, ix) * ue(iy, ix) + _contract(uq, B2, A1); // uq(qy, qx) = sum_{iy} B2(qy, iy) * A1(qx, iy) + + ue = nd::view< const double, 2 >(values_e.data() + (n * p), {n, p}); + + // note: column-major strides here, since quadrature points are still + // enumerated lexicographically as {y, x} but y-component nodes are {x, y} + uq = nd::view(static_cast(&values_q[0][0])+1, {q, q}, {2, 2*q}); + + _contract(A1, B1, ue); // A1(qx, iy) = sum_{ix} B1(qx, ix) * ue(iy, ix) + _contract(uq, B2, A1); // uq(qy, qx) = sum_{iy} B2(qy, iy) * A1(qx, iy) + } + +#if 1 + nd::array< double, 2 > evaluate_shape_function_curls(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + for (uint32_t j = 0; j < q; j++) { + vec2 xi_ij = vec2{xi(j, 0), xi(i, 0)}; + for (uint32_t k = 0; k < num_nodes(); k++) { + shape_fns(i * q + j, k) = shape_function_curl(xi_ij, k); + } + } + } + return shape_fns; + } + + void curl(nd::view values_q, nd::view values_e, nd::view shape_fn_curls, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + derivative_type sum = 0.0; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += shape_fn_curls(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_functions(nd::view xi, nd::view weights) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q, num_nodes(), dim}); + uint32_t qcount = 0; + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + vec2 xi_ij = vec2{xi(i, 0), xi(j, 0)}; + for (uint32_t l = 0; l < num_nodes(); l++) { + vec2 phi = shape_function(xi_ij, l); + shape_fns(qcount, l, 0) = phi[0] * weights[i] * weights[j]; + shape_fns(qcount, l, 1) = phi[1] * weights[i] * weights[j]; + } + qcount++; + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (uint32_t j = 0; j < dim; j++) { + sum += shape_fn(q, i, j) * source_q(q)[j]; + } + } + residual_e(i) = sum; + } + } + + nd::array< double, 2 > evaluate_weighted_shape_function_curls(nd::view xi, nd::view weights) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q * q, num_nodes()}); + uint32_t qcount = 0; + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + vec2 xi_ij = vec2{xi(i, 0), xi(j, 0)}; + for (uint32_t l = 0; l < num_nodes(); l++) { + shape_fns(qcount, l) = shape_function_curl(xi_ij, l) * weights[i] * weights[j]; + } + qcount++; + } + } + return shape_fns; + } + + void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn_curl(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn_curl(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + #endif + +#else + // sum factorization + nd::array< double > evaluate_shape_function_curls(nd::view xi) const { + uint32_t q = xi.shape[0]; + + auto [B1, B2, G2, A1, num_entries] = scan({q*p, q*(p+1), q*(p+1), q*(p+1)}); + nd::array buffer({num_entries}); + std::cout << num_entries << std::endl; + for (uint32_t i = 0; i < q; i++) { + GaussLegendreInterpolation(xi(i, 0), p, &buffer(B1 + p * i)); + GaussLobattoInterpolation(xi(i, 0), p+1, &buffer(B2 + (p+1)*i)); + GaussLobattoInterpolation(xi(i, 0), p+1, &buffer(G2 + (p+1)*i)); + } + return buffer; + } + + void curl(nd::view values_q, nd::view values_e, nd::view buffer) const { + uint32_t n = p + 1; + uint32_t q = sqrt(values_q.shape[0]); + + // 1D shape function evaluations + nd::view B1(buffer.data(), {q, p}); // legendre shape functions + nd::view B2(B1.end(), {q, n}); // lobatto shape functions + nd::view G2(B2.end(), {q, n}); // lobatto shape function derivatives + nd::view A1(G2.end(), {q, n}); // storage for intermediates + + nd::view ue(values_e.data(), {n, p}); + nd::view uq(values_q.data(), {q, q}, {2*q, 2u}); + + _contract(A1, B1, ue); // A1(qx, iy) = sum_{ix} B1(qx, ix) * ue(iy, ix) + _contract(uq, B2, A1); // uq(qy, qx) = sum_{iy} B2(qy, iy) * A1(qx, iy) + + ue = nd::view< const double, 2 >(values_e.data() + (n * p), {n, p}); + + // note: column-major strides here, since quadrature points + // are still enumerated lexicographically as {y, x} but y-component nodes are {x, y} + uq = nd::view(values_q.data() + 1, {q, q}, {2u, 2*q}); + + _contract(A1, B1, ue); // A1(qx, iy) = sum_{ix} B1(qx, ix) * ue(iy, ix) + _contract(uq, B2, A1); // uq(qy, qx) = sum_{iy} B2(qy, iy) * A1(qx, iy) + } +#endif + + uint32_t p; + +}; +// clang-format on + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/hcurl_tetrahedron.hpp b/src/serac/numerics/refactor/elements/hcurl_tetrahedron.hpp new file mode 100644 index 0000000000..c6f8e13d24 --- /dev/null +++ b/src/serac/numerics/refactor/elements/hcurl_tetrahedron.hpp @@ -0,0 +1,1246 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + + +namespace refactor { + +using namespace serac; + +// clang-format off +template <> +struct FiniteElement { + + using value_type = vec3; + using derivative_type = vec3; + + using source_type = vec3; + using flux_type = vec3; + + static constexpr int dim = 3; + + SERAC_HOST_DEVICE constexpr uint32_t num_nodes() const { return (p * (p + 2) * (p + 3)) / 2; } + + constexpr vec3 shape_function(vec3 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) { return vec3{ 1 - xi[1] - xi[2], xi[0], xi[0] }; } + if (i == 1) { return vec3{ -xi[1], xi[0], 0 }; } + if (i == 2) { return vec3{ -xi[1], -1 + xi[0] + xi[2], -xi[1] }; } + if (i == 3) { return vec3{ xi[2], xi[2], 1 - xi[0] - xi[1] }; } + if (i == 4) { return vec3{ -xi[2], 0, xi[0] }; } + if (i == 5) { return vec3{ 0, -xi[2], xi[1] }; } + } + + if (p == 2) { + if (i == 0) { + return vec3{ + 1.3660254037844386467637231708 - 1.732050807568877293527446342*xi[0] - 3.732050807568877293527446342*xi[1] + 1.732050807568877293527446342*xi[0]*xi[1] + 2.366025403784438646763723171*xi[1]*xi[1] - 3.732050807568877293527446342*xi[2] + 1.732050807568877293527446342*xi[0]*xi[2] + 4.732050807568877293527446342*xi[1]*xi[2] + 2.366025403784438646763723171*xi[2]*xi[2], + 1.3660254037844386467637231708*xi[0] - 1.732050807568877293527446342*xi[0]*xi[0] - 2.366025403784438646763723171*xi[0]*xi[1] - 2.366025403784438646763723171*xi[0]*xi[2], + 1.3660254037844386467637231708*xi[0] - 1.732050807568877293527446342*xi[0]*xi[0] - 2.366025403784438646763723171*xi[0]*xi[1] - 2.366025403784438646763723171*xi[0]*xi[2] + }; + } + if (i == 1) { + return vec3{ + -0.3660254037844386467637231708 + 1.732050807568877293527446342*xi[0] - 0.2679491924311227064725536585*xi[1] - 1.732050807568877293527446342*xi[0]*xi[1] + 0.6339745962155613532362768292*xi[1]*xi[1] - 0.2679491924311227064725536585*xi[2] - 1.732050807568877293527446342*xi[0]*xi[2] + 1.2679491924311227064725536585*xi[1]*xi[2] + 0.6339745962155613532362768292*xi[2]*xi[2], + -0.3660254037844386467637231708*xi[0] + 1.732050807568877293527446342*xi[0]*xi[0] - 0.6339745962155613532362768292*xi[0]*xi[1] - 0.6339745962155613532362768292*xi[0]*xi[2], + -0.3660254037844386467637231708*xi[0] + 1.732050807568877293527446342*xi[0]*xi[0] - 0.633974596215561353236276829*xi[0]*xi[1] - 0.6339745962155613532362768292*xi[0]*xi[2] + }; + } + if (i == 2) { + return vec3{ + xi[1] - 2.366025403784438646763723171*xi[0]*xi[1] - 0.6339745962155613532362768292*xi[1]*xi[1], + -xi[0] + 2.366025403784438646763723171*xi[0]*xi[0] + 0.6339745962155613532362768292*xi[0]*xi[1], + 0 + }; + } + if (i == 3) { + return vec3{ + xi[1] - 0.6339745962155613532362768292*xi[0]*xi[1] - 2.366025403784438646763723171*xi[1]*xi[1], + -xi[0] + 0.6339745962155613532362768292*xi[0]*xi[0] + 2.366025403784438646763723171*xi[0]*xi[1], + 0 + }; + } + if (i == 4) { + return vec3{ + 0.3660254037844386467637231708*xi[1] + 0.6339745962155613532362768292*xi[0]*xi[1] - 1.732050807568877293527446342*xi[1]*xi[1] + 0.6339745962155613532362768292*xi[1]*xi[2], + 0.3660254037844386467637231708 + 0.2679491924311227064725536585*xi[0] - 0.6339745962155613532362768292*xi[0]*xi[0] - 1.732050807568877293527446342*xi[1] + 1.732050807568877293527446342*xi[0]*xi[1] + 0.2679491924311227064725536585*xi[2] - 1.2679491924311227064725536585*xi[0]*xi[2] + 1.732050807568877293527446342*xi[1]*xi[2] - 0.6339745962155613532362768292*xi[2]*xi[2], + 0.3660254037844386467637231708*xi[1] + 0.633974596215561353236276829*xi[0]*xi[1] - 1.732050807568877293527446342*xi[1]*xi[1] + 0.6339745962155613532362768292*xi[1]*xi[2] + }; + } + if (i == 5) { + return vec3{ + -1.3660254037844386467637231708*xi[1] + 2.366025403784438646763723171*xi[0]*xi[1] + 1.732050807568877293527446342*xi[1]*xi[1] + 2.366025403784438646763723171*xi[1]*xi[2], + -1.3660254037844386467637231708 + 3.732050807568877293527446342*xi[0] - 2.366025403784438646763723171*xi[0]*xi[0] + 1.732050807568877293527446342*xi[1] - 1.732050807568877293527446342*xi[0]*xi[1] + 3.732050807568877293527446342*xi[2] - 4.732050807568877293527446342*xi[0]*xi[2] - 1.732050807568877293527446342*xi[1]*xi[2] - 2.366025403784438646763723171*xi[2]*xi[2], + -1.3660254037844386467637231708*xi[1] + 2.366025403784438646763723171*xi[0]*xi[1] + 1.732050807568877293527446342*xi[1]*xi[1] + 2.366025403784438646763723171*xi[1]*xi[2] + }; + } + if (i == 6) { + return vec3{ + 1.3660254037844386467637231708*xi[2] - 2.366025403784438646763723171*xi[0]*xi[2] - 2.366025403784438646763723171*xi[1]*xi[2] - 1.732050807568877293527446342*xi[2]*xi[2], + 1.3660254037844386467637231708*xi[2] - 2.366025403784438646763723171*xi[0]*xi[2] - 2.366025403784438646763723171*xi[1]*xi[2] - 1.732050807568877293527446342*xi[2]*xi[2], + 1.3660254037844386467637231708 - 3.732050807568877293527446342*xi[0] + 2.366025403784438646763723171*xi[0]*xi[0] - 3.732050807568877293527446342*xi[1] + 4.732050807568877293527446342*xi[0]*xi[1] + 2.366025403784438646763723171*xi[1]*xi[1] - 1.732050807568877293527446342*xi[2] + 1.732050807568877293527446342*xi[0]*xi[2] + 1.732050807568877293527446342*xi[1]*xi[2] + }; + } + if (i == 7) { + return vec3{ + -0.3660254037844386467637231708*xi[2] - 0.6339745962155613532362768292*xi[0]*xi[2] - 0.6339745962155613532362768292*xi[1]*xi[2] + 1.732050807568877293527446342*xi[2]*xi[2], + -0.3660254037844386467637231708*xi[2] - 0.6339745962155613532362768292*xi[0]*xi[2] - 0.6339745962155613532362768292*xi[1]*xi[2] + 1.732050807568877293527446342*xi[2]*xi[2], + -0.3660254037844386467637231708 - 0.2679491924311227064725536585*xi[0] + 0.6339745962155613532362768292*xi[0]*xi[0] - 0.2679491924311227064725536585*xi[1] + 1.2679491924311227064725536585*xi[0]*xi[1] + 0.6339745962155613532362768292*xi[1]*xi[1] + 1.732050807568877293527446342*xi[2] - 1.732050807568877293527446342*xi[0]*xi[2] - 1.732050807568877293527446342*xi[1]*xi[2] + }; + } + if (i == 8) { + return vec3{ + xi[2] - 2.366025403784438646763723171*xi[0]*xi[2] - 0.6339745962155613532362768292*xi[2]*xi[2], + 0, + -xi[0] + 2.366025403784438646763723171*xi[0]*xi[0] + 0.6339745962155613532362768292*xi[0]*xi[2] + }; + } + if (i == 9) { + return vec3{ + xi[2] - 0.6339745962155613532362768292*xi[0]*xi[2] - 2.366025403784438646763723171*xi[2]*xi[2], + 0, + -xi[0] + 0.6339745962155613532362768292*xi[0]*xi[0] + 2.366025403784438646763723171*xi[0]*xi[2] + }; + } + if (i == 10) { + return vec3{ + 0, + xi[2] - 2.366025403784438646763723171*xi[1]*xi[2] - 0.6339745962155613532362768292*xi[2]*xi[2], + -xi[1] + 2.366025403784438646763723171*xi[1]*xi[1] + 0.6339745962155613532362768292*xi[1]*xi[2] + }; + } + if (i == 11) { + return vec3{ + 0, + xi[2] - 0.6339745962155613532362768292*xi[1]*xi[2] - 2.366025403784438646763723171*xi[2]*xi[2], + -xi[1] + 0.6339745962155613532362768292*xi[1]*xi[1] + 2.366025403784438646763723171*xi[1]*xi[2] + }; + } + if (i == 12) { + return vec3{ + 6*xi[1] - 3*xi[0]*xi[1] - 6*xi[1]*xi[1] - 6*xi[1]*xi[2], + -3*xi[0] + 3*xi[0]*xi[0] + 6*xi[0]*xi[1] + 3*xi[0]*xi[2], + 3*xi[0]*xi[1] + }; + } + if (i == 13) { + return vec3{ + -3*xi[1] - 3*xi[0]*xi[1] + 3*xi[1]*xi[1] + 3*xi[1]*xi[2], + -3*xi[0] + 3*xi[0]*xi[0] - 3*xi[0]*xi[1] + 3*xi[0]*xi[2], + -6*xi[0]*xi[1] + }; + } + if (i == 14) { + return vec3{ + 6*xi[2] - 3*xi[0]*xi[2] - 6*xi[1]*xi[2] - 6*xi[2]*xi[2], + 3*xi[0]*xi[2], + -3*xi[0] + 3*xi[0]*xi[0] + 3*xi[0]*xi[1] + 6*xi[0]*xi[2] + }; + } + if (i == 15) { + return vec3{ + -3*xi[2] + 6*xi[0]*xi[2] + 3*xi[1]*xi[2] + 3*xi[2]*xi[2], + 3*xi[0]*xi[2], + 6*xi[0] - 6*xi[0]*xi[0] - 6*xi[0]*xi[1] - 3*xi[0]*xi[2] + }; + } + if (i == 16) { + return vec3{ + -3*xi[1]*xi[2], + 6*xi[0]*xi[2], + -3*xi[0]*xi[1] + }; + } + if (i == 17) { + return vec3{ + -3*xi[1]*xi[2], + -3*xi[0]*xi[2], + 6*xi[0]*xi[1] + }; + } + if (i == 18) { + return vec3{ + -6*xi[1]*xi[2], + -3*xi[2] + 3*xi[0]*xi[2] - 3*xi[1]*xi[2] + 3*xi[2]*xi[2], + -3*xi[1] + 3*xi[0]*xi[1] + 3*xi[1]*xi[1] - 3*xi[1]*xi[2] + }; + } + if (i == 19) { + return vec3{ + 3*xi[1]*xi[2], + -3*xi[2] + 3*xi[0]*xi[2] + 6*xi[1]*xi[2] + 3*xi[2]*xi[2], + 6*xi[1] - 6*xi[0]*xi[1] - 6*xi[1]*xi[1] - 3*xi[1]*xi[2] + }; + } + } + + if (p == 3) { + if (i == 0) { + return vec3{ + 1.47883055770123614752987757 - 4.6243277820691389617264218*xi[0] + 10*xi[0]*xi[0]/3. - 8.9733478255330900061205269*xi[1] + 15.3577068878454845050412827*xi[0]*xi[1] - 10*xi[0]*xi[0]*xi[1]/3. + 14.3045824936940910415209517*xi[1]*xi[1] - 10.7333791057763455433148609*xi[0]*xi[1]*xi[1] - 6.8100652258622371829303024*xi[1]*xi[1]*xi[1] - 8.9733478255330900061205269*xi[2] + 15.3577068878454845050412827*xi[0]*xi[2] - 10*xi[0]*xi[0]*xi[2]/3. + 31.3609728867648172865104794*xi[1]*xi[2] - 21.4667582115526910866297217*xi[0]*xi[1]*xi[2] - 23.1820035769633467522594831*xi[1]*xi[1]*xi[2] + 14.3045824936940910415209517*xi[2]*xi[2] - 10.7333791057763455433148609*xi[0]*xi[2]*xi[2] - 23.1820035769633467522594831*xi[1]*xi[2]*xi[2] - 6.8100652258622371829303024*xi[2]*xi[2]*xi[2], + 1.47883055770123614752987757*xi[0] - 4.6243277820691389617264218*xi[0]*xi[0] + 10*xi[0]*xi[0]*xi[0]/3. - 7.4945172678318538585906493*xi[0]*xi[1] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[1] + 6.8100652258622371829303024*xi[0]*xi[1]*xi[1] - 7.4945172678318538585906493*xi[0]*xi[2] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[2] + 16.3719383511011095693291808*xi[0]*xi[1]*xi[2] + 6.8100652258622371829303024*xi[0]*xi[2]*xi[2], + 1.47883055770123614752987757*xi[0] - 4.6243277820691389617264218*xi[0]*xi[0] + 10*xi[0]*xi[0]*xi[0]/3. - 7.4945172678318538585906493*xi[0]*xi[1] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[1] + 6.8100652258622371829303024*xi[0]*xi[1]*xi[1] - 7.4945172678318538585906493*xi[0]*xi[2] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[2] + 16.3719383511011095693291808*xi[0]*xi[1]*xi[2] + 6.8100652258622371829303024*xi[0]*xi[2]*xi[2] + }; + } + if (i == 1) { + return vec3{ + -0.6666666666666666 + 20*xi[0]/3. - 20*xi[0]*xi[0]/3. - 0.303288211279566160999204378*xi[1] - 40*xi[0]*xi[1]/3. + 20*xi[0]*xi[0]*xi[1]/3. + 3.55371777595813879120445478*xi[1]*xi[1] + 20*xi[0]*xi[1]*xi[1]/3. - 2.58376289801190596353858374*xi[1]*xi[1]*xi[1] - 0.303288211279566160999204378*xi[2] - 40*xi[0]*xi[2]/3. + 20*xi[0]*xi[0]*xi[2]/3. + 8.532022983438516349581543*xi[1]*xi[2] + 40*xi[0]*xi[1]*xi[2]/3. - 9.1758761255579566577883846*xi[1]*xi[1]*xi[2] + 3.55371777595813879120445478*xi[2]*xi[2] + 20*xi[0]*xi[2]*xi[2]/3. - 9.1758761255579566577883846*xi[1]*xi[2]*xi[2] - 2.58376289801190596353858374*xi[2]*xi[2]*xi[2], + -2*xi[0]/3. + 20*xi[0]*xi[0]/3. - 20*xi[0]*xi[0]*xi[0]/3. - 0.96995487794623282766587104*xi[0]*xi[1] - 20*xi[0]*xi[0]*xi[1]/3. + 2.58376289801190596353858374*xi[0]*xi[1]*xi[1] - 0.96995487794623282766587104*xi[0]*xi[2] - 20*xi[0]*xi[0]*xi[2]/3. + 6.5921132275460506942498009*xi[0]*xi[1]*xi[2] + 2.58376289801190596353858374*xi[0]*xi[2]*xi[2], + -2*xi[0]/3. + 20*xi[0]*xi[0]/3. - 20*xi[0]*xi[0]*xi[0]/3. - 0.96995487794623282766587104*xi[0]*xi[1] - 20*xi[0]*xi[0]*xi[1]/3. + 2.5837628980119059635385837*xi[0]*xi[1]*xi[1] - 0.96995487794623282766587104*xi[0]*xi[2] - 20*xi[0]*xi[0]*xi[2]/3. + 6.5921132275460506942498009*xi[0]*xi[1]*xi[2] + 2.58376289801190596353858374*xi[0]*xi[2]*xi[2] + }; + } + if (i == 2) { + return vec3{ + 0.1878361089654305191367891 - 2.04233888459752770494024487*xi[0] + 10*xi[0]*xi[0]/3. + 1.00868684438153346064717759*xi[1] - 2.02437355451215117170794933*xi[0]*xi[1] - 10*xi[0]*xi[0]*xi[1]/3. - 1.78650349992773900683519184*xi[1]*xi[1] + 4.0667124391096788766481942*xi[0]*xi[1]*xi[1] + 0.58998054658077502705122515*xi[1]*xi[1]*xi[1] + 1.00868684438153346064717759*xi[2] - 2.02437355451215117170794933*xi[0]*xi[2] - 10*xi[0]*xi[0]*xi[2]/3. - 0.8211991004788428102018077*xi[1]*xi[2] + 8.1334248782193577532963884*xi[0]*xi[1]*xi[2] - 0.98186625963431012231490054*xi[1]*xi[1]*xi[2] - 1.78650349992773900683519184*xi[2]*xi[2] + 4.0667124391096788766481942*xi[0]*xi[2]*xi[2] - 0.98186625963431012231490054*xi[1]*xi[2]*xi[2] + 0.58998054658077502705122515*xi[2]*xi[2]*xi[2], + 0.1878361089654305191367891*xi[0] - 2.04233888459752770494024487*xi[0]*xi[0] + 10*xi[0]*xi[0]*xi[0]/3. + 1.19652295334696397978396669*xi[0]*xi[1] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[1] - 0.58998054658077502705122515*xi[0]*xi[1]*xi[1] + 1.19652295334696397978396669*xi[0]*xi[2] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[2] + 1.57184680621508514936612569*xi[0]*xi[1]*xi[2] - 0.58998054658077502705122515*xi[0]*xi[2]*xi[2], + 0.1878361089654305191367891*xi[0] - 2.04233888459752770494024487*xi[0]*xi[0] + 10*xi[0]*xi[0]*xi[0]/3. + 1.19652295334696397978396669*xi[0]*xi[1] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[1] - 0.58998054658077502705122515*xi[0]*xi[1]*xi[1] + 1.19652295334696397978396669*xi[0]*xi[2] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[2] + 1.57184680621508514936612569*xi[0]*xi[1]*xi[2] - 0.58998054658077502705122515*xi[0]*xi[2]*xi[2] + }; + } + if (i == 3) { + return vec3{ + -0.79437851573161947186953064*xi[1] + 6.1256131838926205072699555*xi[0]*xi[1] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[1] + 0.0165618601854139256815163943*xi[1]*xi[1] - 2.8867513459481288225457439*xi[0]*xi[1]*xi[1] + 0.58998054658077502705122515*xi[1]*xi[1]*xi[1] - 2.75180789937663520346857598*xi[1]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[1]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2]*xi[2], + 0.79437851573161947186953064*xi[0] - 6.1256131838926205072699555*xi[0]*xi[0] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[0] - 0.0165618601854139256815163943*xi[0]*xi[1] + 2.8867513459481288225457439*xi[0]*xi[0]*xi[1] - 0.58998054658077502705122515*xi[0]*xi[1]*xi[1] + 2.75180789937663520346857598*xi[0]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[0]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[2]*xi[2], + 0 + }; + } + if (i == 4) { + return vec3{ + -0.94714135339900646920604603*xi[1] + 4.19757091807757909941129644*xi[0]*xi[1] - 2.58376289801190596353858374*xi[0]*xi[0]*xi[1] + 4.19757091807757909941129644*xi[1]*xi[1] - 11.8341924626904785937438341*xi[0]*xi[1]*xi[1] - 2.58376289801190596353858374*xi[1]*xi[1]*xi[1] - 1.4245874315222387671726334*xi[1]*xi[2] + 1.4245874315222387671726334*xi[0]*xi[1]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[1]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[2]*xi[2], + 0.94714135339900646920604603*xi[0] - 4.19757091807757909941129644*xi[0]*xi[0] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[0] - 4.19757091807757909941129644*xi[0]*xi[1] + 11.8341924626904785937438341*xi[0]*xi[0]*xi[1] + 2.58376289801190596353858374*xi[0]*xi[1]*xi[1] + 1.4245874315222387671726334*xi[0]*xi[2] - 1.4245874315222387671726334*xi[0]*xi[0]*xi[2] - 1.4245874315222387671726334*xi[0]*xi[1]*xi[2] - 1.4245874315222387671726334*xi[0]*xi[2]*xi[2], + 0 + }; + } + if (i == 5) { + return vec3{ + -0.79437851573161947186953064*xi[1] + 0.0165618601854139256815163945*xi[0]*xi[1] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[1] + 6.1256131838926205072699555*xi[1]*xi[1] - 2.8867513459481288225457439*xi[0]*xi[1]*xi[1] - 6.8100652258622371829303024*xi[1]*xi[1]*xi[1] - 2.75180789937663520346857598*xi[1]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[1]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2]*xi[2], + 0.79437851573161947186953064*xi[0] - 0.0165618601854139256815163945*xi[0]*xi[0] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[0] - 6.1256131838926205072699555*xi[0]*xi[1] + 2.8867513459481288225457439*xi[0]*xi[0]*xi[1] + 6.8100652258622371829303024*xi[0]*xi[1]*xi[1] + 2.75180789937663520346857598*xi[0]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[0]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[2]*xi[2], + 0 + }; + } + if (i == 6) { + return vec3{ + -0.1878361089654305191367891*xi[1] - 1.19652295334696397978396669*xi[0]*xi[1] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[1] + 2.04233888459752770494024487*xi[1]*xi[1] + 4.0667124391096788766481942*xi[0]*xi[1]*xi[1] - 10*xi[1]*xi[1]*xi[1]/3. - 1.19652295334696397978396669*xi[1]*xi[2] - 1.57184680621508514936612569*xi[0]*xi[1]*xi[2] + 4.0667124391096788766481942*xi[1]*xi[1]*xi[2] + 0.58998054658077502705122515*xi[1]*xi[2]*xi[2], + -0.1878361089654305191367891 - 1.00868684438153346064717759*xi[0] + 1.78650349992773900683519184*xi[0]*xi[0] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[0] + 2.04233888459752770494024487*xi[1] + 2.02437355451215117170794934*xi[0]*xi[1] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[1] - 10*xi[1]*xi[1]/3. + 10*xi[0]*xi[1]*xi[1]/3. - 1.00868684438153346064717759*xi[2] + 0.8211991004788428102018077*xi[0]*xi[2] + 0.98186625963431012231490054*xi[0]*xi[0]*xi[2] + 2.02437355451215117170794934*xi[1]*xi[2] - 8.1334248782193577532963884*xi[0]*xi[1]*xi[2] + 10*xi[1]*xi[1]*xi[2]/3. + 1.78650349992773900683519184*xi[2]*xi[2] + 0.98186625963431012231490054*xi[0]*xi[2]*xi[2] - 4.0667124391096788766481942*xi[1]*xi[2]*xi[2] - 0.58998054658077502705122515*xi[2]*xi[2]*xi[2], + -0.1878361089654305191367891*xi[1] - 1.19652295334696397978396669*xi[0]*xi[1] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[1] + 2.04233888459752770494024487*xi[1]*xi[1] + 4.0667124391096788766481942*xi[0]*xi[1]*xi[1] - 10*xi[1]*xi[1]*xi[1]/3. - 1.19652295334696397978396669*xi[1]*xi[2] - 1.57184680621508514936612569*xi[0]*xi[1]*xi[2] + 4.0667124391096788766481942*xi[1]*xi[1]*xi[2] + 0.58998054658077502705122515*xi[1]*xi[2]*xi[2] + }; + } + if (i == 7) { + return vec3{ + 2*xi[1]/3. + 0.96995487794623282766587105*xi[0]*xi[1] - 2.58376289801190596353858374*xi[0]*xi[0]*xi[1] - 20*xi[1]*xi[1]/3. + 20*xi[0]*xi[1]*xi[1]/3. + 20*xi[1]*xi[1]*xi[1]/3. + 0.96995487794623282766587105*xi[1]*xi[2] - 6.5921132275460506942498009*xi[0]*xi[1]*xi[2] + 20*xi[1]*xi[1]*xi[2]/3. - 2.58376289801190596353858374*xi[1]*xi[2]*xi[2], + 0.6666666666666666 + 0.303288211279566160999204379*xi[0] - 3.55371777595813879120445479*xi[0]*xi[0] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[0] - 20*xi[1]/3. + 40*xi[0]*xi[1]/3. - 20*xi[0]*xi[0]*xi[1]/3. + 20*xi[1]*xi[1]/3. - 20*xi[0]*xi[1]*xi[1]/3. + 0.303288211279566160999204379*xi[2] - 8.532022983438516349581543*xi[0]*xi[2] + 9.1758761255579566577883846*xi[0]*xi[0]*xi[2] + 40*xi[1]*xi[2]/3. - 40*xi[0]*xi[1]*xi[2]/3. - 20*xi[1]*xi[1]*xi[2]/3. - 3.55371777595813879120445479*xi[2]*xi[2] + 9.1758761255579566577883846*xi[0]*xi[2]*xi[2] - 20*xi[1]*xi[2]*xi[2]/3. + 2.58376289801190596353858374*xi[2]*xi[2]*xi[2], + 2*xi[1]/3. + 0.96995487794623282766587105*xi[0]*xi[1] - 2.5837628980119059635385837*xi[0]*xi[0]*xi[1] - 20*xi[1]*xi[1]/3. + 20*xi[0]*xi[1]*xi[1]/3. + 20*xi[1]*xi[1]*xi[1]/3. + 0.96995487794623282766587105*xi[1]*xi[2] - 6.5921132275460506942498009*xi[0]*xi[1]*xi[2] + 20*xi[1]*xi[1]*xi[2]/3. - 2.58376289801190596353858374*xi[1]*xi[2]*xi[2] + }; + } + if (i == 8) { + return vec3{ + -1.47883055770123614752987757*xi[1] + 7.4945172678318538585906493*xi[0]*xi[1] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[1] + 4.6243277820691389617264218*xi[1]*xi[1] - 10.7333791057763455433148609*xi[0]*xi[1]*xi[1] - 10*xi[1]*xi[1]*xi[1]/3. + 7.4945172678318538585906493*xi[1]*xi[2] - 16.3719383511011095693291808*xi[0]*xi[1]*xi[2] - 10.7333791057763455433148609*xi[1]*xi[1]*xi[2] - 6.8100652258622371829303024*xi[1]*xi[2]*xi[2], + -1.47883055770123614752987757 + 8.9733478255330900061205269*xi[0] - 14.3045824936940910415209517*xi[0]*xi[0] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[0] + 4.6243277820691389617264218*xi[1] - 15.3577068878454845050412827*xi[0]*xi[1] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[1] - 10*xi[1]*xi[1]/3. + 10*xi[0]*xi[1]*xi[1]/3. + 8.9733478255330900061205269*xi[2] - 31.3609728867648172865104794*xi[0]*xi[2] + 23.1820035769633467522594831*xi[0]*xi[0]*xi[2] - 15.3577068878454845050412827*xi[1]*xi[2] + 21.4667582115526910866297217*xi[0]*xi[1]*xi[2] + 10*xi[1]*xi[1]*xi[2]/3. - 14.3045824936940910415209517*xi[2]*xi[2] + 23.1820035769633467522594831*xi[0]*xi[2]*xi[2] + 10.7333791057763455433148609*xi[1]*xi[2]*xi[2] + 6.8100652258622371829303024*xi[2]*xi[2]*xi[2], + -1.47883055770123614752987757*xi[1] + 7.4945172678318538585906493*xi[0]*xi[1] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[1] + 4.6243277820691389617264218*xi[1]*xi[1] - 10.7333791057763455433148609*xi[0]*xi[1]*xi[1] - 10*xi[1]*xi[1]*xi[1]/3. + 7.4945172678318538585906493*xi[1]*xi[2] - 16.3719383511011095693291808*xi[0]*xi[1]*xi[2] - 10.7333791057763455433148609*xi[1]*xi[1]*xi[2] - 6.8100652258622371829303024*xi[1]*xi[2]*xi[2] + }; + } + if (i == 9) { + return vec3{ + 1.47883055770123614752987757*xi[2] - 7.4945172678318538585906493*xi[0]*xi[2] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[2] - 7.4945172678318538585906493*xi[1]*xi[2] + 16.3719383511011095693291808*xi[0]*xi[1]*xi[2] + 6.8100652258622371829303024*xi[1]*xi[1]*xi[2] - 4.6243277820691389617264218*xi[2]*xi[2] + 10.7333791057763455433148609*xi[0]*xi[2]*xi[2] + 10.7333791057763455433148609*xi[1]*xi[2]*xi[2] + 10*xi[2]*xi[2]*xi[2]/3., + 1.47883055770123614752987757*xi[2] - 7.4945172678318538585906493*xi[0]*xi[2] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[2] - 7.4945172678318538585906493*xi[1]*xi[2] + 16.3719383511011095693291808*xi[0]*xi[1]*xi[2] + 6.8100652258622371829303024*xi[1]*xi[1]*xi[2] - 4.6243277820691389617264218*xi[2]*xi[2] + 10.7333791057763455433148609*xi[0]*xi[2]*xi[2] + 10.7333791057763455433148609*xi[1]*xi[2]*xi[2] + 10*xi[2]*xi[2]*xi[2]/3., + 1.47883055770123614752987757 - 8.9733478255330900061205269*xi[0] + 14.3045824936940910415209517*xi[0]*xi[0] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[0] - 8.9733478255330900061205269*xi[1] + 31.3609728867648172865104794*xi[0]*xi[1] - 23.1820035769633467522594831*xi[0]*xi[0]*xi[1] + 14.3045824936940910415209517*xi[1]*xi[1] - 23.1820035769633467522594831*xi[0]*xi[1]*xi[1] - 6.8100652258622371829303024*xi[1]*xi[1]*xi[1] - 4.6243277820691389617264218*xi[2] + 15.3577068878454845050412827*xi[0]*xi[2] - 10.7333791057763455433148609*xi[0]*xi[0]*xi[2] + 15.3577068878454845050412827*xi[1]*xi[2] - 21.4667582115526910866297217*xi[0]*xi[1]*xi[2] - 10.7333791057763455433148609*xi[1]*xi[1]*xi[2] + 10*xi[2]*xi[2]/3. - 10*xi[0]*xi[2]*xi[2]/3. - 10*xi[1]*xi[2]*xi[2]/3. + }; + } + if (i == 10) { + return vec3{ + -2*xi[2]/3. - 0.96995487794623282766587104*xi[0]*xi[2] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[2] - 0.96995487794623282766587104*xi[1]*xi[2] + 6.5921132275460506942498009*xi[0]*xi[1]*xi[2] + 2.58376289801190596353858374*xi[1]*xi[1]*xi[2] + 20*xi[2]*xi[2]/3. - 20*xi[0]*xi[2]*xi[2]/3. - 20*xi[1]*xi[2]*xi[2]/3. - 20*xi[2]*xi[2]*xi[2]/3., + -2*xi[2]/3. - 0.96995487794623282766587104*xi[0]*xi[2] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[2] - 0.96995487794623282766587104*xi[1]*xi[2] + 6.5921132275460506942498009*xi[0]*xi[1]*xi[2] + 2.58376289801190596353858374*xi[1]*xi[1]*xi[2] + 20*xi[2]*xi[2]/3. - 20*xi[0]*xi[2]*xi[2]/3. - 20*xi[1]*xi[2]*xi[2]/3. - 20*xi[2]*xi[2]*xi[2]/3., + -0.6666666666666666 - 0.303288211279566160999204378*xi[0] + 3.55371777595813879120445478*xi[0]*xi[0] - 2.58376289801190596353858374*xi[0]*xi[0]*xi[0] - 0.303288211279566160999204378*xi[1] + 8.532022983438516349581543*xi[0]*xi[1] - 9.1758761255579566577883846*xi[0]*xi[0]*xi[1] + 3.55371777595813879120445478*xi[1]*xi[1] - 9.1758761255579566577883846*xi[0]*xi[1]*xi[1] - 2.58376289801190596353858374*xi[1]*xi[1]*xi[1] + 20*xi[2]/3. - 40*xi[0]*xi[2]/3. + 20*xi[0]*xi[0]*xi[2]/3. - 40*xi[1]*xi[2]/3. + 40*xi[0]*xi[1]*xi[2]/3. + 20*xi[1]*xi[1]*xi[2]/3. - 20*xi[2]*xi[2]/3. + 20*xi[0]*xi[2]*xi[2]/3. + 20*xi[1]*xi[2]*xi[2]/3. + }; + } + if (i == 11) { + return vec3{ + 0.1878361089654305191367891*xi[2] + 1.19652295334696397978396669*xi[0]*xi[2] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[2] + 1.19652295334696397978396669*xi[1]*xi[2] + 1.57184680621508514936612569*xi[0]*xi[1]*xi[2] - 0.58998054658077502705122515*xi[1]*xi[1]*xi[2] - 2.04233888459752770494024487*xi[2]*xi[2] - 4.0667124391096788766481942*xi[0]*xi[2]*xi[2] - 4.0667124391096788766481942*xi[1]*xi[2]*xi[2] + 10*xi[2]*xi[2]*xi[2]/3., + 0.1878361089654305191367891*xi[2] + 1.19652295334696397978396669*xi[0]*xi[2] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[2] + 1.19652295334696397978396669*xi[1]*xi[2] + 1.57184680621508514936612569*xi[0]*xi[1]*xi[2] - 0.58998054658077502705122515*xi[1]*xi[1]*xi[2] - 2.04233888459752770494024487*xi[2]*xi[2] - 4.0667124391096788766481942*xi[0]*xi[2]*xi[2] - 4.0667124391096788766481942*xi[1]*xi[2]*xi[2] + 10*xi[2]*xi[2]*xi[2]/3., + 0.1878361089654305191367891 + 1.00868684438153346064717759*xi[0] - 1.78650349992773900683519184*xi[0]*xi[0] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[0] + 1.00868684438153346064717759*xi[1] - 0.8211991004788428102018077*xi[0]*xi[1] - 0.98186625963431012231490054*xi[0]*xi[0]*xi[1] - 1.78650349992773900683519184*xi[1]*xi[1] - 0.98186625963431012231490054*xi[0]*xi[1]*xi[1] + 0.58998054658077502705122515*xi[1]*xi[1]*xi[1] - 2.04233888459752770494024487*xi[2] - 2.02437355451215117170794933*xi[0]*xi[2] + 4.0667124391096788766481942*xi[0]*xi[0]*xi[2] - 2.02437355451215117170794933*xi[1]*xi[2] + 8.1334248782193577532963884*xi[0]*xi[1]*xi[2] + 4.0667124391096788766481942*xi[1]*xi[1]*xi[2] + 10*xi[2]*xi[2]/3. - 10*xi[0]*xi[2]*xi[2]/3. - 10*xi[1]*xi[2]*xi[2]/3. + }; + } + if (i == 12) { + return vec3{ + -0.79437851573161947186953064*xi[2] + 6.1256131838926205072699555*xi[0]*xi[2] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[2] - 2.75180789937663520346857598*xi[1]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[1]*xi[2] + 0.0165618601854139256815163943*xi[2]*xi[2] - 2.8867513459481288225457439*xi[0]*xi[2]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2]*xi[2] + 0.58998054658077502705122515*xi[2]*xi[2]*xi[2], + 0, + 0.79437851573161947186953064*xi[0] - 6.1256131838926205072699555*xi[0]*xi[0] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[0] + 2.75180789937663520346857598*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[1] - 0.0165618601854139256815163943*xi[0]*xi[2] + 2.8867513459481288225457439*xi[0]*xi[0]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] - 0.58998054658077502705122515*xi[0]*xi[2]*xi[2] + }; + } + if (i == 13) { + return vec3{ + -0.94714135339900646920604603*xi[2] + 4.19757091807757909941129644*xi[0]*xi[2] - 2.58376289801190596353858374*xi[0]*xi[0]*xi[2] - 1.4245874315222387671726334*xi[1]*xi[2] + 1.4245874315222387671726334*xi[0]*xi[1]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[1]*xi[2] + 4.19757091807757909941129644*xi[2]*xi[2] - 11.8341924626904785937438341*xi[0]*xi[2]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[2]*xi[2] - 2.58376289801190596353858374*xi[2]*xi[2]*xi[2], + 0, + 0.94714135339900646920604603*xi[0] - 4.19757091807757909941129644*xi[0]*xi[0] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[0] + 1.4245874315222387671726334*xi[0]*xi[1] - 1.4245874315222387671726334*xi[0]*xi[0]*xi[1] - 1.4245874315222387671726334*xi[0]*xi[1]*xi[1] - 4.19757091807757909941129644*xi[0]*xi[2] + 11.8341924626904785937438341*xi[0]*xi[0]*xi[2] - 1.4245874315222387671726334*xi[0]*xi[1]*xi[2] + 2.58376289801190596353858374*xi[0]*xi[2]*xi[2] + }; + } + if (i == 14) { + return vec3{ + -0.79437851573161947186953064*xi[2] + 0.0165618601854139256815163945*xi[0]*xi[2] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[2] - 2.75180789937663520346857598*xi[1]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[1]*xi[2] + 6.1256131838926205072699555*xi[2]*xi[2] - 2.8867513459481288225457439*xi[0]*xi[2]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2]*xi[2] - 6.8100652258622371829303024*xi[2]*xi[2]*xi[2], + 0, + 0.79437851573161947186953064*xi[0] - 0.0165618601854139256815163945*xi[0]*xi[0] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[0] + 2.75180789937663520346857598*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[1] - 6.1256131838926205072699555*xi[0]*xi[2] + 2.8867513459481288225457439*xi[0]*xi[0]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 6.8100652258622371829303024*xi[0]*xi[2]*xi[2] + }; + } + if (i == 15) { + return vec3{ + 0, + -0.79437851573161947186953064*xi[2] - 2.75180789937663520346857598*xi[0]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[0]*xi[2] + 6.1256131838926205072699555*xi[1]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] - 6.8100652258622371829303024*xi[1]*xi[1]*xi[2] + 0.0165618601854139256815163943*xi[2]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[2]*xi[2] - 2.8867513459481288225457439*xi[1]*xi[2]*xi[2] + 0.58998054658077502705122515*xi[2]*xi[2]*xi[2], + 0.79437851573161947186953064*xi[1] + 2.75180789937663520346857598*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[0]*xi[1] - 6.1256131838926205072699555*xi[1]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[1] + 6.8100652258622371829303024*xi[1]*xi[1]*xi[1] - 0.0165618601854139256815163943*xi[1]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 2.8867513459481288225457439*xi[1]*xi[1]*xi[2] - 0.58998054658077502705122515*xi[1]*xi[2]*xi[2] + }; + } + if (i == 16) { + return vec3{ + 0, + -0.94714135339900646920604603*xi[2] - 1.4245874315222387671726334*xi[0]*xi[2] + 1.4245874315222387671726334*xi[0]*xi[0]*xi[2] + 4.19757091807757909941129644*xi[1]*xi[2] + 1.4245874315222387671726334*xi[0]*xi[1]*xi[2] - 2.58376289801190596353858374*xi[1]*xi[1]*xi[2] + 4.19757091807757909941129644*xi[2]*xi[2] + 1.4245874315222387671726334*xi[0]*xi[2]*xi[2] - 11.8341924626904785937438341*xi[1]*xi[2]*xi[2] - 2.58376289801190596353858374*xi[2]*xi[2]*xi[2], + 0.94714135339900646920604603*xi[1] + 1.4245874315222387671726334*xi[0]*xi[1] - 1.4245874315222387671726334*xi[0]*xi[0]*xi[1] - 4.19757091807757909941129644*xi[1]*xi[1] - 1.4245874315222387671726334*xi[0]*xi[1]*xi[1] + 2.58376289801190596353858374*xi[1]*xi[1]*xi[1] - 4.19757091807757909941129644*xi[1]*xi[2] - 1.4245874315222387671726334*xi[0]*xi[1]*xi[2] + 11.8341924626904785937438341*xi[1]*xi[1]*xi[2] + 2.58376289801190596353858374*xi[1]*xi[2]*xi[2] + }; + } + if (i == 17) { + return vec3{ + 0, + -0.79437851573161947186953064*xi[2] - 2.75180789937663520346857598*xi[0]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[0]*xi[2] + 0.0165618601854139256815163945*xi[1]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 0.58998054658077502705122515*xi[1]*xi[1]*xi[2] + 6.1256131838926205072699555*xi[2]*xi[2] + 2.75180789937663520346857598*xi[0]*xi[2]*xi[2] - 2.8867513459481288225457439*xi[1]*xi[2]*xi[2] - 6.8100652258622371829303024*xi[2]*xi[2]*xi[2], + 0.79437851573161947186953064*xi[1] + 2.75180789937663520346857598*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[0]*xi[1] - 0.0165618601854139256815163945*xi[1]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[1] - 0.58998054658077502705122515*xi[1]*xi[1]*xi[1] - 6.1256131838926205072699555*xi[1]*xi[2] - 2.75180789937663520346857598*xi[0]*xi[1]*xi[2] + 2.8867513459481288225457439*xi[1]*xi[1]*xi[2] + 6.8100652258622371829303024*xi[1]*xi[2]*xi[2] + }; + } + if (i == 18) { + return vec3{ + -2.66025403784438646763723171*xi[1] + 2.09807621135331594029116951*xi[0]*xi[1] + 17.9089653438086685770214805*xi[1]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[1]*xi[1] - 15.2487113059642821093842488*xi[1]*xi[1]*xi[1] - 1.94744111674234977119809024*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 10.6410161513775458705489268*xi[1]*xi[1]*xi[2] + 4.60769515458673623883532195*xi[1]*xi[2]*xi[2], + 2.09807621135331594029116951*xi[0] - 2.09807621135331594029116951*xi[0]*xi[0] - 14.6865334794732115820381866*xi[0]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + 15.2487113059642821093842488*xi[0]*xi[1]*xi[1] + 1.53589838486224541294510732*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] + 7.4185842870420888755656329*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2]*xi[2], + -0.5621778264910705273460622*xi[0]*xi[1] + 3.2224318643354569949832939*xi[0]*xi[1]*xi[1] - 0.9737205583711748855990451*xi[0]*xi[1]*xi[2] + }; + } + if (i == 19) { + return vec3{ + 0.5621778264910705273460622*xi[1] + 2.09807621135331594029116951*xi[0]*xi[1] - 3.7846096908265275223293561*xi[1]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[1]*xi[1] + 3.2224318643354569949832939*xi[1]*xi[1]*xi[1] + 0.411542731880104358252982926*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] + 2.24871130596428210938424878*xi[1]*xi[1]*xi[2] - 0.97372055837117488559904512*xi[1]*xi[2]*xi[2], + 2.09807621135331594029116951*xi[0] - 2.09807621135331594029116951*xi[0]*xi[0] - 11.4641016151377545870548927*xi[0]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] - 3.2224318643354569949832939*xi[0]*xi[1]*xi[1] + 1.53589838486224541294510732*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] + 13*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2]*xi[2], + 2.66025403784438646763723171*xi[0]*xi[1] - 15.2487113059642821093842488*xi[0]*xi[1]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] + }; + } + if (i == 20) { + return vec3{ + -4.19615242270663188058233902*xi[1] + 26.1506350946109661690930793*xi[0]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + 4.19615242270663188058233902*xi[1]*xi[1] - 24.0525588832576502288019098*xi[0]*xi[1]*xi[1] - 3.07179676972449082589021463*xi[1]*xi[2] - 20.4185842870420888755656329*xi[0]*xi[1]*xi[2] + 7.2679491924311227064725537*xi[1]*xi[1]*xi[2] + 7.2679491924311227064725537*xi[1]*xi[2]*xi[2], + 2.09807621135331594029116951*xi[0] - 14.1243556529821410546921244*xi[0]*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[0] - 4.19615242270663188058233902*xi[0]*xi[1] + 24.0525588832576502288019098*xi[0]*xi[0]*xi[1] + 1.53589838486224541294510732*xi[0]*xi[2] + 8.392304845413263761164678*xi[0]*xi[0]*xi[2] - 7.2679491924311227064725537*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2]*xi[2], + -2.09807621135331594029116951*xi[0]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[1]*xi[2] + }; + } + if (i == 21) { + return vec3{ + 2.09807621135331594029116951*xi[1] - 11.4641016151377545870548927*xi[0]*xi[1] - 3.2224318643354569949832939*xi[0]*xi[0]*xi[1] - 2.09807621135331594029116951*xi[1]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[1]*xi[1] + 1.53589838486224541294510732*xi[1]*xi[2] + 13*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]*xi[2], + 0.5621778264910705273460622*xi[0] - 3.7846096908265275223293561*xi[0]*xi[0] + 3.2224318643354569949832939*xi[0]*xi[0]*xi[0] + 2.09807621135331594029116951*xi[0]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + 0.411542731880104358252982926*xi[0]*xi[2] + 2.24871130596428210938424878*xi[0]*xi[0]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[2]*xi[2], + 2.66025403784438646763723171*xi[0]*xi[1] - 15.2487113059642821093842488*xi[0]*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] + }; + } + if (i == 22) { + return vec3{ + 12.5884572681198956417470171*xi[1] - 17.9089653438086685770214805*xi[0]*xi[1] + 3.2224318643354569949832939*xi[0]*xi[0]*xi[1] - 27.8371685740841777511312659*xi[1]*xi[1] + 18.4711431702997391043675427*xi[0]*xi[1]*xi[1] + 15.2487113059642821093842488*xi[1]*xi[1]*xi[1] - 32.4448637286709139899665878*xi[1]*xi[2] + 19.4448637286709139899665878*xi[0]*xi[1]*xi[2] + 35.1051177665153004576038195*xi[1]*xi[1]*xi[2] + 19.8564064605510183482195707*xi[1]*xi[2]*xi[2], + -2.66025403784438646763723171*xi[0] + 5.8826859021798434626205256*xi[0]*xi[0] - 3.2224318643354569949832939*xi[0]*xi[0]*xi[0] + 15.810889132455352636730311*xi[0]*xi[1] - 18.4711431702997391043675427*xi[0]*xi[0]*xi[1] - 15.2487113059642821093842488*xi[0]*xi[1]*xi[1] + 6.8564064605510183482195707*xi[0]*xi[2] - 7.4185842870420888755656329*xi[0]*xi[0]*xi[2] - 23.0788383248864753432028646*xi[0]*xi[1]*xi[2] - 4.19615242270663188058233902*xi[0]*xi[2]*xi[2], + 9.9282032302755091741097854*xi[0]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] - 12.026279441628825114400955*xi[0]*xi[1]*xi[1] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] + }; + } + if (i == 23) { + return vec3{ + -9.9282032302755091741097854*xi[1] + 2.09807621135331594029116951*xi[0]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + 21.9544826719043342885107402*xi[1]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1]*xi[1] + 25.5884572681198956417470171*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 27.6865334794732115820381866*xi[1]*xi[1]*xi[2] - 15.6602540378443864676372317*xi[1]*xi[2]*xi[2], + -9.9282032302755091741097854*xi[0] + 21.9544826719043342885107402*xi[0]*xi[0] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[0] + 2.09807621135331594029116951*xi[0]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[1]*xi[1] + 25.5884572681198956417470171*xi[0]*xi[2] - 27.6865334794732115820381866*xi[0]*xi[0]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[2]*xi[2], + -19.8564064605510183482195707*xi[0]*xi[1] + 24.0525588832576502288019098*xi[0]*xi[0]*xi[1] + 24.0525588832576502288019098*xi[0]*xi[1]*xi[1] + 31.3205080756887729352744634*xi[0]*xi[1]*xi[2] + }; + } + if (i == 24) { + return vec3{ + 12.5884572681198956417470171*xi[2] - 17.9089653438086685770214805*xi[0]*xi[2] + 3.2224318643354569949832939*xi[0]*xi[0]*xi[2] - 32.4448637286709139899665878*xi[1]*xi[2] + 19.4448637286709139899665878*xi[0]*xi[1]*xi[2] + 19.8564064605510183482195707*xi[1]*xi[1]*xi[2] - 27.8371685740841777511312659*xi[2]*xi[2] + 18.4711431702997391043675427*xi[0]*xi[2]*xi[2] + 35.1051177665153004576038195*xi[1]*xi[2]*xi[2] + 15.2487113059642821093842488*xi[2]*xi[2]*xi[2], + 9.9282032302755091741097854*xi[0]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[2]*xi[2], + -2.66025403784438646763723171*xi[0] + 5.8826859021798434626205256*xi[0]*xi[0] - 3.2224318643354569949832939*xi[0]*xi[0]*xi[0] + 6.8564064605510183482195707*xi[0]*xi[1] - 7.4185842870420888755656329*xi[0]*xi[0]*xi[1] - 4.196152422706631880582339*xi[0]*xi[1]*xi[1] + 15.810889132455352636730311*xi[0]*xi[2] - 18.4711431702997391043675427*xi[0]*xi[0]*xi[2] - 23.0788383248864753432028646*xi[0]*xi[1]*xi[2] - 15.2487113059642821093842488*xi[0]*xi[2]*xi[2] + }; + } + if (i == 25) { + return vec3{ + -2.66025403784438646763723171*xi[2] + 15.810889132455352636730311*xi[0]*xi[2] - 15.2487113059642821093842488*xi[0]*xi[0]*xi[2] + 6.8564064605510183482195707*xi[1]*xi[2] - 23.0788383248864753432028646*xi[0]*xi[1]*xi[2] - 4.19615242270663188058233902*xi[1]*xi[1]*xi[2] + 5.8826859021798434626205256*xi[2]*xi[2] - 18.4711431702997391043675427*xi[0]*xi[2]*xi[2] - 7.4185842870420888755656329*xi[1]*xi[2]*xi[2] - 3.2224318643354569949832939*xi[2]*xi[2]*xi[2], + 9.9282032302755091741097854*xi[0]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[2]*xi[2], + 12.5884572681198956417470171*xi[0] - 27.8371685740841777511312659*xi[0]*xi[0] + 15.2487113059642821093842488*xi[0]*xi[0]*xi[0] - 32.4448637286709139899665878*xi[0]*xi[1] + 35.1051177665153004576038195*xi[0]*xi[0]*xi[1] + 19.8564064605510183482195707*xi[0]*xi[1]*xi[1] - 17.9089653438086685770214805*xi[0]*xi[2] + 18.4711431702997391043675427*xi[0]*xi[0]*xi[2] + 19.4448637286709139899665878*xi[0]*xi[1]*xi[2] + 3.2224318643354569949832939*xi[0]*xi[2]*xi[2] + }; + } + if (i == 26) { + return vec3{ + -4.19615242270663188058233902*xi[2] + 26.1506350946109661690930793*xi[0]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[2] - 3.07179676972449082589021463*xi[1]*xi[2] - 20.4185842870420888755656329*xi[0]*xi[1]*xi[2] + 7.2679491924311227064725537*xi[1]*xi[1]*xi[2] + 4.19615242270663188058233902*xi[2]*xi[2] - 24.0525588832576502288019098*xi[0]*xi[2]*xi[2] + 7.2679491924311227064725537*xi[1]*xi[2]*xi[2], + -2.09807621135331594029116951*xi[0]*xi[2] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[2], + 2.09807621135331594029116951*xi[0] - 14.1243556529821410546921244*xi[0]*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[0] + 1.53589838486224541294510732*xi[0]*xi[1] + 8.392304845413263761164678*xi[0]*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[1]*xi[1] - 4.19615242270663188058233902*xi[0]*xi[2] + 24.0525588832576502288019098*xi[0]*xi[0]*xi[2] - 7.2679491924311227064725537*xi[0]*xi[1]*xi[2] + }; + } + if (i == 27) { + return vec3{ + 2.09807621135331594029116951*xi[2] - 14.6865334794732115820381866*xi[0]*xi[2] + 15.2487113059642821093842488*xi[0]*xi[0]*xi[2] + 1.53589838486224541294510732*xi[1]*xi[2] + 7.4185842870420888755656329*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[1]*xi[2] - 2.09807621135331594029116951*xi[2]*xi[2] + 12.0262794416288251144009549*xi[0]*xi[2]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]*xi[2], + -0.5621778264910705273460622*xi[0]*xi[2] + 3.2224318643354569949832939*xi[0]*xi[0]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[1]*xi[2], + -2.66025403784438646763723171*xi[0] + 17.9089653438086685770214805*xi[0]*xi[0] - 15.2487113059642821093842488*xi[0]*xi[0]*xi[0] - 1.94744111674234977119809024*xi[0]*xi[1] - 10.6410161513775458705489268*xi[0]*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[1] + 2.09807621135331594029116951*xi[0]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] + }; + } + if (i == 28) { + return vec3{ + -2.66025403784438646763723171*xi[2] + 2.09807621135331594029116951*xi[0]*xi[2] - 1.94744111674234977119809024*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] + 4.60769515458673623883532195*xi[1]*xi[1]*xi[2] + 17.9089653438086685770214805*xi[2]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[2]*xi[2] - 10.6410161513775458705489268*xi[1]*xi[2]*xi[2] - 15.2487113059642821093842488*xi[2]*xi[2]*xi[2], + -0.5621778264910705273460622*xi[0]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[1]*xi[2] + 3.2224318643354569949832939*xi[0]*xi[2]*xi[2], + 2.09807621135331594029116951*xi[0] - 2.09807621135331594029116951*xi[0]*xi[0] + 1.53589838486224541294510732*xi[0]*xi[1] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[1]*xi[1] - 14.6865334794732115820381866*xi[0]*xi[2] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[2] + 7.4185842870420888755656329*xi[0]*xi[1]*xi[2] + 15.2487113059642821093842488*xi[0]*xi[2]*xi[2] + }; + } + if (i == 29) { + return vec3{ + 2.09807621135331594029116951*xi[2] - 4.19615242270663188058233902*xi[0]*xi[2] + 1.53589838486224541294510732*xi[1]*xi[2] - 7.2679491924311227064725537*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[1]*xi[2] - 14.1243556529821410546921244*xi[2]*xi[2] + 24.0525588832576502288019098*xi[0]*xi[2]*xi[2] + 8.392304845413263761164678*xi[1]*xi[2]*xi[2] + 12.0262794416288251144009549*xi[2]*xi[2]*xi[2], + -2.09807621135331594029116951*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] + 12.0262794416288251144009549*xi[0]*xi[2]*xi[2], + -4.19615242270663188058233902*xi[0] + 4.19615242270663188058233902*xi[0]*xi[0] - 3.07179676972449082589021463*xi[0]*xi[1] + 7.2679491924311227064725537*xi[0]*xi[0]*xi[1] + 7.2679491924311227064725537*xi[0]*xi[1]*xi[1] + 26.1506350946109661690930793*xi[0]*xi[2] - 24.0525588832576502288019098*xi[0]*xi[0]*xi[2] - 20.4185842870420888755656329*xi[0]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[0]*xi[2]*xi[2] + }; + } + if (i == 30) { + return vec3{ + 5.7320508075688772935274463*xi[1]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]*xi[2], + -7.2679491924311227064725537*xi[0]*xi[2] + 19.8564064605510183482195707*xi[0]*xi[0]*xi[2] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] + 4.60769515458673623883532195*xi[0]*xi[2]*xi[2], + 1.53589838486224541294510732*xi[0]*xi[1] - 4.196152422706631880582339*xi[0]*xi[0]*xi[1] - 0.9737205583711748855990451*xi[0]*xi[1]*xi[1] - 0.9737205583711748855990451*xi[0]*xi[1]*xi[2] + }; + } + if (i == 31) { + return vec3{ + 5.7320508075688772935274463*xi[1]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]*xi[2], + 1.53589838486224541294510732*xi[0]*xi[2] - 4.19615242270663188058233902*xi[0]*xi[0]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[1]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[2]*xi[2], + -7.2679491924311227064725537*xi[0]*xi[1] + 19.8564064605510183482195707*xi[0]*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] + }; + } + if (i == 32) { + return vec3{ + 5.7320508075688772935274463*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 15.6602540378443864676372317*xi[1]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]*xi[2], + -11.4641016151377545870548927*xi[0]*xi[2] + 7.2679491924311227064725537*xi[0]*xi[0]*xi[2] + 31.3205080756887729352744634*xi[0]*xi[1]*xi[2] + 7.2679491924311227064725537*xi[0]*xi[2]*xi[2], + 5.7320508075688772935274463*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[0]*xi[1] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[1]*xi[2] + }; + } + if (i == 33) { + return vec3{ + 1.53589838486224541294510732*xi[1]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[1]*xi[2] - 4.19615242270663188058233902*xi[1]*xi[1]*xi[2] - 0.97372055837117488559904512*xi[1]*xi[2]*xi[2], + 5.7320508075688772935274463*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2]*xi[2], + -7.2679491924311227064725537*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[0]*xi[1] + 19.8564064605510183482195707*xi[0]*xi[1]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] + }; + } + if (i == 34) { + return vec3{ + 1.53589838486224541294510732*xi[1]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[1]*xi[2] - 0.97372055837117488559904512*xi[1]*xi[1]*xi[2] - 4.19615242270663188058233902*xi[1]*xi[2]*xi[2], + -7.2679491924311227064725537*xi[0]*xi[2] + 4.60769515458673623883532195*xi[0]*xi[0]*xi[2] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] + 19.8564064605510183482195707*xi[0]*xi[2]*xi[2], + 5.7320508075688772935274463*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[1]*xi[1] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] + }; + } + if (i == 35) { + return vec3{ + 5.7320508075688772935274463*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[1]*xi[2] - 15.6602540378443864676372317*xi[1]*xi[2]*xi[2], + 5.7320508075688772935274463*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[2]*xi[2], + -11.4641016151377545870548927*xi[0]*xi[1] + 7.2679491924311227064725537*xi[0]*xi[0]*xi[1] + 7.2679491924311227064725537*xi[0]*xi[1]*xi[1] + 31.3205080756887729352744634*xi[0]*xi[1]*xi[2] + }; + } + if (i == 36) { + return vec3{ + 2.66025403784438646763723171*xi[1]*xi[2] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] - 15.2487113059642821093842488*xi[1]*xi[1]*xi[2], + 2.09807621135331594029116951*xi[2] + 1.53589838486224541294510732*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] - 11.4641016151377545870548927*xi[1]*xi[2] + 13*xi[0]*xi[1]*xi[2] - 3.2224318643354569949832939*xi[1]*xi[1]*xi[2] - 2.09807621135331594029116951*xi[2]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2]*xi[2] + 12.0262794416288251144009549*xi[1]*xi[2]*xi[2], + 0.5621778264910705273460622*xi[1] + 0.411542731880104358252982926*xi[0]*xi[1] - 0.9737205583711748855990451*xi[0]*xi[0]*xi[1] - 3.7846096908265275223293561*xi[1]*xi[1] + 2.2487113059642821093842488*xi[0]*xi[1]*xi[1] + 3.2224318643354569949832939*xi[1]*xi[1]*xi[1] + 2.09807621135331594029116951*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[1]*xi[1]*xi[2] + }; + } + if (i == 37) { + return vec3{ + -0.5621778264910705273460622*xi[1]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[1]*xi[2] + 3.2224318643354569949832939*xi[1]*xi[1]*xi[2], + 2.09807621135331594029116951*xi[2] + 1.53589838486224541294510732*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] - 14.6865334794732115820381866*xi[1]*xi[2] + 7.4185842870420888755656329*xi[0]*xi[1]*xi[2] + 15.2487113059642821093842488*xi[1]*xi[1]*xi[2] - 2.09807621135331594029116951*xi[2]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2]*xi[2] + 12.0262794416288251144009549*xi[1]*xi[2]*xi[2], + -2.66025403784438646763723171*xi[1] - 1.94744111674234977119809024*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[0]*xi[1] + 17.9089653438086685770214805*xi[1]*xi[1] - 10.6410161513775458705489268*xi[0]*xi[1]*xi[1] - 15.2487113059642821093842488*xi[1]*xi[1]*xi[1] + 2.09807621135331594029116951*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[1]*xi[1]*xi[2] + }; + } + if (i == 38) { + return vec3{ + -19.8564064605510183482195707*xi[1]*xi[2] + 31.3205080756887729352744634*xi[0]*xi[1]*xi[2] + 24.0525588832576502288019098*xi[1]*xi[1]*xi[2] + 24.0525588832576502288019098*xi[1]*xi[2]*xi[2], + -9.9282032302755091741097854*xi[2] + 25.5884572681198956417470171*xi[0]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[0]*xi[2] + 2.09807621135331594029116951*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] + 12.0262794416288251144009549*xi[1]*xi[1]*xi[2] + 21.9544826719043342885107402*xi[2]*xi[2] - 27.6865334794732115820381866*xi[0]*xi[2]*xi[2] - 12.0262794416288251144009549*xi[2]*xi[2]*xi[2], + -9.9282032302755091741097854*xi[1] + 25.5884572681198956417470171*xi[0]*xi[1] - 15.6602540378443864676372317*xi[0]*xi[0]*xi[1] + 21.9544826719043342885107402*xi[1]*xi[1] - 27.6865334794732115820381866*xi[0]*xi[1]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1]*xi[1] + 2.09807621135331594029116951*xi[1]*xi[2] + 3.633974596215561353236277*xi[0]*xi[1]*xi[2] + 12.0262794416288251144009549*xi[1]*xi[2]*xi[2] + }; + } + if (i == 39) { + return vec3{ + 9.9282032302755091741097854*xi[1]*xi[2] - 15.6602540378443864676372317*xi[0]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[1]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[1]*xi[2]*xi[2], + -2.66025403784438646763723171*xi[2] + 6.8564064605510183482195707*xi[0]*xi[2] - 4.19615242270663188058233902*xi[0]*xi[0]*xi[2] + 15.810889132455352636730311*xi[1]*xi[2] - 23.0788383248864753432028646*xi[0]*xi[1]*xi[2] - 15.2487113059642821093842488*xi[1]*xi[1]*xi[2] + 5.8826859021798434626205256*xi[2]*xi[2] - 7.4185842870420888755656329*xi[0]*xi[2]*xi[2] - 18.4711431702997391043675427*xi[1]*xi[2]*xi[2] - 3.2224318643354569949832939*xi[2]*xi[2]*xi[2], + 12.5884572681198956417470171*xi[1] - 32.4448637286709139899665878*xi[0]*xi[1] + 19.8564064605510183482195707*xi[0]*xi[0]*xi[1] - 27.8371685740841777511312659*xi[1]*xi[1] + 35.1051177665153004576038195*xi[0]*xi[1]*xi[1] + 15.2487113059642821093842488*xi[1]*xi[1]*xi[1] - 17.9089653438086685770214805*xi[1]*xi[2] + 19.4448637286709139899665878*xi[0]*xi[1]*xi[2] + 18.4711431702997391043675427*xi[1]*xi[1]*xi[2] + 3.2224318643354569949832939*xi[1]*xi[2]*xi[2] + }; + } + if (i == 40) { + return vec3{ + 2.66025403784438646763723171*xi[1]*xi[2] + 4.60769515458673623883532195*xi[0]*xi[1]*xi[2] - 15.2487113059642821093842488*xi[1]*xi[2]*xi[2], + 0.5621778264910705273460622*xi[2] + 0.411542731880104358252982926*xi[0]*xi[2] - 0.97372055837117488559904512*xi[0]*xi[0]*xi[2] + 2.09807621135331594029116951*xi[1]*xi[2] + 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] - 3.7846096908265275223293561*xi[2]*xi[2] + 2.24871130596428210938424878*xi[0]*xi[2]*xi[2] - 12.0262794416288251144009549*xi[1]*xi[2]*xi[2] + 3.2224318643354569949832939*xi[2]*xi[2]*xi[2], + 2.09807621135331594029116951*xi[1] + 1.53589838486224541294510732*xi[0]*xi[1] - 3.6339745962155613532362768*xi[0]*xi[0]*xi[1] - 2.09807621135331594029116951*xi[1]*xi[1] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[1] - 11.4641016151377545870548927*xi[1]*xi[2] + 13*xi[0]*xi[1]*xi[2] + 12.0262794416288251144009549*xi[1]*xi[1]*xi[2] - 3.2224318643354569949832939*xi[1]*xi[2]*xi[2] + }; + } + if (i == 41) { + return vec3{ + -2.09807621135331594029116951*xi[1]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[1]*xi[2] + 12.0262794416288251144009549*xi[1]*xi[2]*xi[2], + 2.09807621135331594029116951*xi[2] + 1.53589838486224541294510732*xi[0]*xi[2] - 3.63397459621556135323627683*xi[0]*xi[0]*xi[2] - 4.19615242270663188058233902*xi[1]*xi[2] - 7.2679491924311227064725537*xi[0]*xi[1]*xi[2] - 14.1243556529821410546921244*xi[2]*xi[2] + 8.392304845413263761164678*xi[0]*xi[2]*xi[2] + 24.0525588832576502288019098*xi[1]*xi[2]*xi[2] + 12.0262794416288251144009549*xi[2]*xi[2]*xi[2], + -4.19615242270663188058233902*xi[1] - 3.07179676972449082589021463*xi[0]*xi[1] + 7.2679491924311227064725537*xi[0]*xi[0]*xi[1] + 4.19615242270663188058233902*xi[1]*xi[1] + 7.2679491924311227064725537*xi[0]*xi[1]*xi[1] + 26.1506350946109661690930793*xi[1]*xi[2] - 20.4185842870420888755656329*xi[0]*xi[1]*xi[2] - 24.0525588832576502288019098*xi[1]*xi[1]*xi[2] - 12.0262794416288251144009549*xi[1]*xi[2]*xi[2] + }; + } + if (i == 42) { + return vec3{ + 48*xi[1]*xi[2] - 32*xi[0]*xi[1]*xi[2] - 48*xi[1]*xi[1]*xi[2] - 48*xi[1]*xi[2]*xi[2], + -16*xi[0]*xi[2] + 16*xi[0]*xi[0]*xi[2] + 32*xi[0]*xi[1]*xi[2] + 16*xi[0]*xi[2]*xi[2], + -16*xi[0]*xi[1] + 16*xi[0]*xi[0]*xi[1] + 16*xi[0]*xi[1]*xi[1] + 32*xi[0]*xi[1]*xi[2] + }; + } + if (i == 43) { + return vec3{ + -16*xi[1]*xi[2] + 32*xi[0]*xi[1]*xi[2] + 16*xi[1]*xi[1]*xi[2] + 16*xi[1]*xi[2]*xi[2], + 48*xi[0]*xi[2] - 48*xi[0]*xi[0]*xi[2] - 32*xi[0]*xi[1]*xi[2] - 48*xi[0]*xi[2]*xi[2], + -16*xi[0]*xi[1] + 16*xi[0]*xi[0]*xi[1] + 16*xi[0]*xi[1]*xi[1] + 32*xi[0]*xi[1]*xi[2] + }; + } + if (i == 44) { + return vec3{ + -16*xi[1]*xi[2] + 32*xi[0]*xi[1]*xi[2] + 16*xi[1]*xi[1]*xi[2] + 16*xi[1]*xi[2]*xi[2], + -16*xi[0]*xi[2] + 16*xi[0]*xi[0]*xi[2] + 32*xi[0]*xi[1]*xi[2] + 16*xi[0]*xi[2]*xi[2], + 48*xi[0]*xi[1] - 48*xi[0]*xi[0]*xi[1] - 48*xi[0]*xi[1]*xi[1] - 32*xi[0]*xi[1]*xi[2] + }; + } + } + + return {}; + } + + constexpr vec3 reoriented_shape_function(vec3 xi, uint32_t i, int8_t transformation) const { + switch (transformation) { + case -1: return -shape_function(xi, i); + case 0: return shape_function(xi, i); + default: + // the way this element numbers its local dofs + // the first dof in that pair is always even + uint32_t ix = (i & 0xFFFFFFFE) + 0; + uint32_t iy = (i & 0xFFFFFFFE) + 1; + vec2 weights = face_transformation(transformation)[i % 2]; + return shape_function(xi, ix) * weights[0] + shape_function(xi, iy) * weights[1]; + } + } + + constexpr vec3 shape_function_curl(vec3 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + if (i == 0) { return vec3{ 0, -2, 2 }; } + if (i == 1) { return vec3{ 0, 0, 2 }; } + if (i == 2) { return vec3{ -2, 0, 2 }; } + if (i == 3) { return vec3{ -2, 2, 0 }; } + if (i == 4) { return vec3{ 0, -2, 0 }; } + if (i == 5) { return vec3{ 2, 0, 0 }; } + } + + if (p == 2) { + if (i == 0) { + return vec3{ + 0, + -5.098076211353315940291169512 + 5.196152422706631880582339025*xi[0] + 7.098076211353315940291169512*xi[1] + 7.098076211353315940291169512*xi[2], + 5.098076211353315940291169512 - 5.196152422706631880582339025*xi[0] - 7.098076211353315940291169512*xi[1] - 7.098076211353315940291169512*xi[2] + }; + } + if (i == 1) { + return vec3{ + 0, + 0.0980762113533159402911695123 - 5.196152422706631880582339025*xi[0] + 1.901923788646684059708830488*xi[1] + 1.901923788646684059708830488*xi[2], + -0.0980762113533159402911695123 + 5.196152422706631880582339025*xi[0] - 1.901923788646684059708830488*xi[1] - 1.901923788646684059708830488*xi[2] + }; + } + if (i == 2) { + return vec3{ + 0, + 0, + -2 + 7.098076211353315940291169512*xi[0] + 1.901923788646684059708830488*xi[1] + }; + } + if (i == 3) { + return vec3{ + 0, + 0, + -2 + 1.901923788646684059708830488*xi[0] + 7.098076211353315940291169512*xi[1] + }; + } + if (i == 4) { + return vec3{ + 0.0980762113533159402911695123 + 1.901923788646684059708830488*xi[0] - 5.196152422706631880582339025*xi[1] + 1.901923788646684059708830488*xi[2], + 0, + -0.0980762113533159402911695123 - 1.901923788646684059708830488*xi[0] + 5.196152422706631880582339025*xi[1] - 1.901923788646684059708830488*xi[2] + }; + } + if (i == 5) { + return vec3{ + -5.098076211353315940291169512 + 7.098076211353315940291169512*xi[0] + 5.196152422706631880582339025*xi[1] + 7.098076211353315940291169512*xi[2], + 0, + 5.098076211353315940291169512 - 7.098076211353315940291169512*xi[0] - 5.196152422706631880582339025*xi[1] - 7.098076211353315940291169512*xi[2] + }; + } + if (i == 6) { + return vec3{ + -5.098076211353315940291169512 + 7.098076211353315940291169512*xi[0] + 7.098076211353315940291169512*xi[1] + 5.196152422706631880582339025*xi[2], + 5.098076211353315940291169512 - 7.098076211353315940291169512*xi[0] - 7.098076211353315940291169512*xi[1] - 5.196152422706631880582339025*xi[2], + 0 + }; + } + if (i == 7) { + return vec3{ + 0.0980762113533159402911695123 + 1.901923788646684059708830488*xi[0] + 1.901923788646684059708830488*xi[1] - 5.196152422706631880582339025*xi[2], + -0.0980762113533159402911695123 - 1.901923788646684059708830488*xi[0] - 1.901923788646684059708830488*xi[1] + 5.196152422706631880582339025*xi[2], + 0 + }; + } + if (i == 8) { + return vec3{ + 0, + 2 - 7.098076211353315940291169512*xi[0] - 1.901923788646684059708830488*xi[2], + 0 + }; + } + if (i == 9) { + return vec3{ + 0, + 2 - 1.901923788646684059708830488*xi[0] - 7.098076211353315940291169512*xi[2], + 0 + }; + } + if (i == 10) { + return vec3{ + -2 + 7.098076211353315940291169512*xi[1] + 1.901923788646684059708830488*xi[2], + 0, + 0 + }; + } + if (i == 11) { + return vec3{ + -2 + 1.901923788646684059708830488*xi[1] + 7.098076211353315940291169512*xi[2], + 0, + 0 + }; + } + if (i == 12) { + return vec3{ + 0, + -9*xi[1], + -9 + 9*xi[0] + 18*xi[1] + 9*xi[2] + }; + } + if (i == 13) { + return vec3{ + -9*xi[0], + 9*xi[1], + 9*xi[0] - 9*xi[1] + }; + } + if (i == 14) { + return vec3{ + 0, + 9 - 9*xi[0] - 9*xi[1] - 18*xi[2], + 9*xi[2] + }; + } + if (i == 15) { + return vec3{ + -9*xi[0], + -9 + 18*xi[0] + 9*xi[1] + 9*xi[2], + 0 + }; + } + if (i == 16) { + return vec3{ + -9*xi[0], + 0, + 9*xi[2] + }; + } + if (i == 17) { + return vec3{ + 9*xi[0], + -9*xi[1], + 0 + }; + } + if (i == 18) { + return vec3{ + 9*xi[1] - 9*xi[2], + -9*xi[1], + 9*xi[2] + }; + } + if (i == 19) { + return vec3{ + 9 - 9*xi[0] - 18*xi[1] - 9*xi[2], + 9*xi[1], + 0 + }; + } + } + + if (p == 3) { + if (i == 0) { + return vec3{ + -2.751807899376635203468576*xi[0]*xi[1] + 2.751807899376635203468576*xi[0]*xi[2], + -10.4521783832343261536504044 + 24.6063624519837624284941263*xi[0] - 40*xi[0]*xi[0]/3. + 38.8554901545966711451011287*xi[1] - 42.933516423105382173259443*xi[0]*xi[1] - 29.992068802825583935189786*xi[1]*xi[1] + 36.1036822552200359416325527*xi[2] - 42.9335164231053821732594435*xi[0]*xi[2] - 62.735945505027803073848147*xi[1]*xi[2] - 27.2402609034489487317212095*xi[2]*xi[2], + 10.4521783832343261536504044 - 24.6063624519837624284941263*xi[0] + 40*xi[0]*xi[0]/3. - 36.1036822552200359416325527*xi[1] + 42.9335164231053821732594435*xi[0]*xi[1] + 27.2402609034489487317212095*xi[1]*xi[1] - 38.8554901545966711451011287*xi[2] + 42.9335164231053821732594435*xi[0]*xi[2] + 62.735945505027803073848147*xi[1]*xi[2] + 29.9920688028255839351897855*xi[2]*xi[2] + }; + } + if (i == 1) { + return vec3{ + -1.4245874315222387671726334*xi[0]*xi[1] + 1.4245874315222387671726334*xi[0]*xi[2], + 0.36337845538710050566746229 - 80*xi[0]/3. + 80*xi[0]*xi[0]/3. + 9.501977861384749177247414*xi[1] + 80*xi[0]*xi[1]/3. - 11.7596390235698626213269684*xi[1]*xi[1] + 8.0773904298625104100747806*xi[2] + 80*xi[0]*xi[2]/3. - 24.9438654786619640098265701*xi[1]*xi[2] - 10.335051592047623854154335*xi[2]*xi[2], + -0.36337845538710050566746229 + 80*xi[0]/3. - 80*xi[0]*xi[0]/3. - 8.0773904298625104100747806*xi[1] - 80*xi[0]*xi[1]/3. + 10.335051592047623854154335*xi[1]*xi[1] - 9.501977861384749177247414*xi[2] - 80*xi[0]*xi[2]/3. + 24.9438654786619640098265701*xi[1]*xi[2] + 11.7596390235698626213269684*xi[2]*xi[2] + }; + } + if (i == 2) { + return vec3{ + -2.751807899376635203468576*xi[0]*xi[1] + 2.75180789937663520346857598*xi[0]*xi[2], + 0.82085073541610294151038849 + 2.0603042146829042381725404*xi[0] - 40*xi[0]*xi[0]/3. - 2.0177220538258067899857744*xi[1] + 16.2668497564387155065927768*xi[0]*xi[1] - 0.39188571305353509526367539*xi[1]*xi[1] - 4.76952995320244199345435038*xi[2] + 16.2668497564387155065927768*xi[0]*xi[2] - 3.53557932548370539399592676*xi[1]*xi[2] + 2.3599221863231001082049006*xi[2]*xi[2], + -0.82085073541610294151038849 - 2.0603042146829042381725404*xi[0] + 40*xi[0]*xi[0]/3. + 4.76952995320244199345435038*xi[1] - 16.2668497564387155065927768*xi[0]*xi[1] - 2.3599221863231001082049006*xi[1]*xi[1] + 2.0177220538258067899857744*xi[2] - 16.2668497564387155065927768*xi[0]*xi[2] + 3.53557932548370539399592676*xi[1]*xi[2] + 0.39188571305353509526367539*xi[2]*xi[2] + }; + } + if (i == 3) { + return vec3{ + -2.75180789937663520346857598*xi[0] + 2.75180789937663520346857598*xi[0]*xi[0] + 2.75180789937663520346857598*xi[0]*xi[1] + 5.503615798753270406937152*xi[0]*xi[2], + -2.75180789937663520346857598*xi[1] + 2.75180789937663520346857598*xi[0]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[1] + 5.503615798753270406937152*xi[1]*xi[2], + 1.58875703146323894373906129 - 18.3768395516778615218098664*xi[0] + 27.2402609034489487317212095*xi[0]*xi[0] - 0.049685580556241777044549183*xi[1] + 11.5470053837925152901829756*xi[0]*xi[1] - 2.3599221863231001082049006*xi[1]*xi[1] + 5.503615798753270406937152*xi[2] - 8.255423698129905610405728*xi[0]*xi[2] - 8.255423698129905610405728*xi[1]*xi[2] - 5.503615798753270406937152*xi[2]*xi[2] + }; + } + if (i == 4) { + return vec3{ + -1.4245874315222387671726334*xi[0] + 1.4245874315222387671726334*xi[0]*xi[0] + 1.4245874315222387671726334*xi[0]*xi[1] + 2.84917486304447753434526679*xi[0]*xi[2], + -1.4245874315222387671726334*xi[1] + 1.4245874315222387671726334*xi[0]*xi[1] + 1.4245874315222387671726334*xi[1]*xi[1] + 2.84917486304447753434526679*xi[1]*xi[2], + 1.89428270679801293841209206 - 12.5927127542327372982338893*xi[0] + 10.335051592047623854154335*xi[0]*xi[0] - 12.5927127542327372982338893*xi[1] + 47.3367698507619143749753366*xi[0]*xi[1] + 10.335051592047623854154335*xi[1]*xi[1] + 2.84917486304447753434526679*xi[2] - 4.27376229456671630151790019*xi[0]*xi[2] - 4.27376229456671630151790019*xi[1]*xi[2] - 2.84917486304447753434526679*xi[2]*xi[2] + }; + } + if (i == 5) { + return vec3{ + -2.75180789937663520346857598*xi[0] + 2.75180789937663520346857598*xi[0]*xi[0] + 2.75180789937663520346857598*xi[0]*xi[1] + 5.503615798753270406937152*xi[0]*xi[2], + -2.75180789937663520346857598*xi[1] + 2.75180789937663520346857598*xi[0]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[1] + 5.503615798753270406937152*xi[1]*xi[2], + 1.58875703146323894373906129 - 0.0496855805562417770445491834*xi[0] - 2.3599221863231001082049006*xi[0]*xi[0] - 18.3768395516778615218098664*xi[1] + 11.5470053837925152901829756*xi[0]*xi[1] + 27.2402609034489487317212095*xi[1]*xi[1] + 5.503615798753270406937152*xi[2] - 8.255423698129905610405728*xi[0]*xi[2] - 8.255423698129905610405728*xi[1]*xi[2] - 5.503615798753270406937152*xi[2]*xi[2] + }; + } + if (i == 6) { + return vec3{ + 0.82085073541610294151038849 - 2.0177220538258067899857744*xi[0] - 0.39188571305353509526367539*xi[0]*xi[0] + 2.0603042146829042381725404*xi[1] + 16.2668497564387155065927768*xi[0]*xi[1] - 40*xi[1]*xi[1]/3. - 4.76952995320244199345435038*xi[2] - 3.53557932548370539399592676*xi[0]*xi[2] + 16.2668497564387155065927768*xi[1]*xi[2] + 2.3599221863231001082049006*xi[2]*xi[2], + -2.751807899376635203468576*xi[0]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[2], + -0.82085073541610294151038849 + 4.76952995320244199345435038*xi[0] - 2.3599221863231001082049006*xi[0]*xi[0] - 2.0603042146829042381725404*xi[1] - 16.2668497564387155065927768*xi[0]*xi[1] + 40*xi[1]*xi[1]/3. + 2.0177220538258067899857744*xi[2] + 3.53557932548370539399592676*xi[0]*xi[2] - 16.2668497564387155065927768*xi[1]*xi[2] + 0.39188571305353509526367539*xi[2]*xi[2] + }; + } + if (i == 7) { + return vec3{ + 0.36337845538710050566746229 + 9.501977861384749177247414*xi[0] - 11.7596390235698626213269684*xi[0]*xi[0] - 80*xi[1]/3. + 80*xi[0]*xi[1]/3. + 80*xi[1]*xi[1]/3. + 8.0773904298625104100747806*xi[2] - 24.9438654786619640098265701*xi[0]*xi[2] + 80*xi[1]*xi[2]/3. - 10.335051592047623854154335*xi[2]*xi[2], + -1.4245874315222387671726334*xi[0]*xi[1] + 1.4245874315222387671726334*xi[1]*xi[2], + -0.36337845538710050566746229 - 8.0773904298625104100747806*xi[0] + 10.335051592047623854154335*xi[0]*xi[0] + 80*xi[1]/3. - 80*xi[0]*xi[1]/3. - 80*xi[1]*xi[1]/3. - 9.501977861384749177247414*xi[2] + 24.9438654786619640098265701*xi[0]*xi[2] - 80*xi[1]*xi[2]/3. + 11.7596390235698626213269684*xi[2]*xi[2] + }; + } + if (i == 8) { + return vec3{ + -10.4521783832343261536504044 + 38.8554901545966711451011287*xi[0] - 29.992068802825583935189786*xi[0]*xi[0] + 24.6063624519837624284941263*xi[1] - 42.933516423105382173259443*xi[0]*xi[1] - 40*xi[1]*xi[1]/3. + 36.1036822552200359416325527*xi[2] - 62.735945505027803073848147*xi[0]*xi[2] - 42.9335164231053821732594435*xi[1]*xi[2] - 27.2402609034489487317212095*xi[2]*xi[2], + -2.751807899376635203468576*xi[0]*xi[1] + 2.751807899376635203468576*xi[1]*xi[2], + 10.4521783832343261536504044 - 36.1036822552200359416325527*xi[0] + 27.2402609034489487317212095*xi[0]*xi[0] - 24.6063624519837624284941263*xi[1] + 42.9335164231053821732594435*xi[0]*xi[1] + 40*xi[1]*xi[1]/3. - 38.8554901545966711451011287*xi[2] + 62.735945505027803073848147*xi[0]*xi[2] + 42.9335164231053821732594435*xi[1]*xi[2] + 29.9920688028255839351897855*xi[2]*xi[2] + }; + } + if (i == 9) { + return vec3{ + -10.4521783832343261536504044 + 38.8554901545966711451011287*xi[0] - 29.9920688028255839351897855*xi[0]*xi[0] + 36.1036822552200359416325527*xi[1] - 62.735945505027803073848147*xi[0]*xi[1] - 27.2402609034489487317212095*xi[1]*xi[1] + 24.6063624519837624284941263*xi[2] - 42.9335164231053821732594435*xi[0]*xi[2] - 42.9335164231053821732594435*xi[1]*xi[2] - 40*xi[2]*xi[2]/3., + 10.4521783832343261536504044 - 36.1036822552200359416325527*xi[0] + 27.2402609034489487317212095*xi[0]*xi[0] - 38.8554901545966711451011287*xi[1] + 62.735945505027803073848147*xi[0]*xi[1] + 29.9920688028255839351897855*xi[1]*xi[1] - 24.6063624519837624284941263*xi[2] + 42.9335164231053821732594435*xi[0]*xi[2] + 42.9335164231053821732594435*xi[1]*xi[2] + 40*xi[2]*xi[2]/3., + -2.751807899376635203468576*xi[0]*xi[2] + 2.751807899376635203468576*xi[1]*xi[2] + }; + } + if (i == 10) { + return vec3{ + 0.36337845538710050566746229 + 9.501977861384749177247414*xi[0] - 11.7596390235698626213269684*xi[0]*xi[0] + 8.0773904298625104100747806*xi[1] - 24.9438654786619640098265701*xi[0]*xi[1] - 10.335051592047623854154335*xi[1]*xi[1] - 80*xi[2]/3. + 80*xi[0]*xi[2]/3. + 80*xi[1]*xi[2]/3. + 80*xi[2]*xi[2]/3., + -0.36337845538710050566746229 - 8.0773904298625104100747806*xi[0] + 10.335051592047623854154335*xi[0]*xi[0] - 9.501977861384749177247414*xi[1] + 24.9438654786619640098265701*xi[0]*xi[1] + 11.7596390235698626213269684*xi[1]*xi[1] + 80*xi[2]/3. - 80*xi[0]*xi[2]/3. - 80*xi[1]*xi[2]/3. - 80*xi[2]*xi[2]/3., + -1.4245874315222387671726334*xi[0]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[2] + }; + } + if (i == 11) { + return vec3{ + 0.82085073541610294151038849 - 2.0177220538258067899857744*xi[0] - 0.39188571305353509526367539*xi[0]*xi[0] - 4.76952995320244199345435038*xi[1] - 3.5355793254837053939959268*xi[0]*xi[1] + 2.3599221863231001082049006*xi[1]*xi[1] + 2.0603042146829042381725404*xi[2] + 16.2668497564387155065927768*xi[0]*xi[2] + 16.2668497564387155065927768*xi[1]*xi[2] - 40*xi[2]*xi[2]/3., + -0.82085073541610294151038849 + 4.76952995320244199345435038*xi[0] - 2.3599221863231001082049006*xi[0]*xi[0] + 2.0177220538258067899857744*xi[1] + 3.5355793254837053939959268*xi[0]*xi[1] + 0.39188571305353509526367539*xi[1]*xi[1] - 2.0603042146829042381725404*xi[2] - 16.2668497564387155065927768*xi[0]*xi[2] - 16.2668497564387155065927768*xi[1]*xi[2] + 40*xi[2]*xi[2]/3., + -2.75180789937663520346857598*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2] + }; + } + if (i == 12) { + return vec3{ + 2.75180789937663520346857598*xi[0] - 2.75180789937663520346857598*xi[0]*xi[0] - 5.503615798753270406937152*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[2], + -1.58875703146323894373906129 + 18.3768395516778615218098664*xi[0] - 27.2402609034489487317212095*xi[0]*xi[0] - 5.503615798753270406937152*xi[1] + 8.255423698129905610405728*xi[0]*xi[1] + 5.503615798753270406937152*xi[1]*xi[1] + 0.049685580556241777044549183*xi[2] - 11.5470053837925152901829756*xi[0]*xi[2] + 8.255423698129905610405728*xi[1]*xi[2] + 2.3599221863231001082049006*xi[2]*xi[2], + 2.75180789937663520346857598*xi[2] - 2.75180789937663520346857598*xi[0]*xi[2] - 5.503615798753270406937152*xi[1]*xi[2] - 2.75180789937663520346857598*xi[2]*xi[2] + }; + } + if (i == 13) { + return vec3{ + 1.4245874315222387671726334*xi[0] - 1.4245874315222387671726334*xi[0]*xi[0] - 2.84917486304447753434526679*xi[0]*xi[1] - 1.4245874315222387671726334*xi[0]*xi[2], + -1.89428270679801293841209206 + 12.5927127542327372982338893*xi[0] - 10.335051592047623854154335*xi[0]*xi[0] - 2.84917486304447753434526679*xi[1] + 4.27376229456671630151790019*xi[0]*xi[1] + 2.84917486304447753434526679*xi[1]*xi[1] + 12.5927127542327372982338893*xi[2] - 47.3367698507619143749753366*xi[0]*xi[2] + 4.27376229456671630151790019*xi[1]*xi[2] - 10.335051592047623854154335*xi[2]*xi[2], + 1.4245874315222387671726334*xi[2] - 1.4245874315222387671726334*xi[0]*xi[2] - 2.84917486304447753434526679*xi[1]*xi[2] - 1.4245874315222387671726334*xi[2]*xi[2] + }; + } + if (i == 14) { + return vec3{ + 2.75180789937663520346857598*xi[0] - 2.75180789937663520346857598*xi[0]*xi[0] - 5.503615798753270406937152*xi[0]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[2], + -1.58875703146323894373906129 + 0.0496855805562417770445491834*xi[0] + 2.3599221863231001082049006*xi[0]*xi[0] - 5.503615798753270406937152*xi[1] + 8.255423698129905610405728*xi[0]*xi[1] + 5.503615798753270406937152*xi[1]*xi[1] + 18.3768395516778615218098664*xi[2] - 11.5470053837925152901829756*xi[0]*xi[2] + 8.255423698129905610405728*xi[1]*xi[2] - 27.2402609034489487317212095*xi[2]*xi[2], + 2.75180789937663520346857598*xi[2] - 2.75180789937663520346857598*xi[0]*xi[2] - 5.503615798753270406937152*xi[1]*xi[2] - 2.75180789937663520346857598*xi[2]*xi[2] + }; + } + if (i == 15) { + return vec3{ + 1.58875703146323894373906129 + 5.503615798753270406937152*xi[0] - 5.503615798753270406937152*xi[0]*xi[0] - 18.3768395516778615218098664*xi[1] - 8.255423698129905610405728*xi[0]*xi[1] + 27.2402609034489487317212095*xi[1]*xi[1] - 0.049685580556241777044549183*xi[2] - 8.255423698129905610405728*xi[0]*xi[2] + 11.5470053837925152901829756*xi[1]*xi[2] - 2.3599221863231001082049006*xi[2]*xi[2], + -2.75180789937663520346857598*xi[1] + 5.503615798753270406937152*xi[0]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[2], + -2.75180789937663520346857598*xi[2] + 5.503615798753270406937152*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2] + 2.75180789937663520346857598*xi[2]*xi[2] + }; + } + if (i == 16) { + return vec3{ + 1.89428270679801293841209206 + 2.84917486304447753434526679*xi[0] - 2.84917486304447753434526679*xi[0]*xi[0] - 12.5927127542327372982338893*xi[1] - 4.27376229456671630151790019*xi[0]*xi[1] + 10.335051592047623854154335*xi[1]*xi[1] - 12.5927127542327372982338893*xi[2] - 4.27376229456671630151790019*xi[0]*xi[2] + 47.3367698507619143749753366*xi[1]*xi[2] + 10.335051592047623854154335*xi[2]*xi[2], + -1.4245874315222387671726334*xi[1] + 2.84917486304447753434526679*xi[0]*xi[1] + 1.4245874315222387671726334*xi[1]*xi[1] + 1.4245874315222387671726334*xi[1]*xi[2], + -1.4245874315222387671726334*xi[2] + 2.84917486304447753434526679*xi[0]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[2] + 1.4245874315222387671726334*xi[2]*xi[2] + }; + } + if (i == 17) { + return vec3{ + 1.58875703146323894373906129 + 5.503615798753270406937152*xi[0] - 5.503615798753270406937152*xi[0]*xi[0] - 0.0496855805562417770445491834*xi[1] - 8.255423698129905610405728*xi[0]*xi[1] - 2.3599221863231001082049006*xi[1]*xi[1] - 18.3768395516778615218098664*xi[2] - 8.255423698129905610405728*xi[0]*xi[2] + 11.5470053837925152901829756*xi[1]*xi[2] + 27.2402609034489487317212095*xi[2]*xi[2], + -2.75180789937663520346857598*xi[1] + 5.503615798753270406937152*xi[0]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[1] + 2.75180789937663520346857598*xi[1]*xi[2], + -2.75180789937663520346857598*xi[2] + 5.503615798753270406937152*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2] + 2.75180789937663520346857598*xi[2]*xi[2] + }; + } + if (i == 18) { + return vec3{ + -2.09807621135331594029116951*xi[0] + 3.63397459621556135323627683*xi[0]*xi[0] - 0.9737205583711748855990451*xi[0]*xi[1] + 6.2942286340599478208735085*xi[0]*xi[2], + -1.38526329025127924385202805*xi[1] + 3.63397459621556135323627683*xi[0]*xi[1] - 13.8634480157130028655322207*xi[1]*xi[1] + 10.189110867544647363269689*xi[1]*xi[2], + 4.75833024919770240792840122 - 6.2942286340599478208735085*xi[0] - 50.5044641670905487360811476*xi[1] + 48.1051177665153004576038195*xi[0]*xi[1] + 60.994845223857128437536995*xi[1]*xi[1] + 3.48333950160459518414319756*xi[2] - 10.9019237886466840597088305*xi[0]*xi[2] + 28.7006165897971806166634866*xi[1]*xi[2] - 8.2416697508022975920715988*xi[2]*xi[2] + }; + } + if (i == 19) { + return vec3{ + 1.12435565298214105469212439*xi[0] + 3.63397459621556135323627683*xi[0]*xi[0] - 43.4974226119285642187684976*xi[0]*xi[1] + 11.8756443470178589453078756*xi[0]*xi[2], + -2.24871130596428210938424878*xi[1] + 3.63397459621556135323627683*xi[0]*xi[1] + 17.4974226119285642187684976*xi[1]*xi[1] - 6.5551362713290860100334122*xi[1]*xi[2], + 1.53589838486224541294510732 - 6.2942286340599478208735085*xi[0] - 3.8948822334846995423961805*xi[1] + 48.1051177665153004576038195*xi[0]*xi[1] - 12.8897274573418279799331756*xi[1]*xi[1] + 1.12435565298214105469212439*xi[2] - 10.9019237886466840597088305*xi[0]*xi[2] + 8.5025773880714357812315024*xi[1]*xi[2] - 2.66025403784438646763723171*xi[2]*xi[2] + }; + } + if (i == 20) { + return vec3{ + -3.63397459621556135323627683*xi[0] + 3.6339745962155613532362768*xi[0]*xi[0] + 7.2679491924311227064725537*xi[0]*xi[1] + 3.6339745962155613532362768*xi[0]*xi[2], + -0.9737205583711748855990451*xi[1] - 44.471143170299739104367543*xi[0]*xi[1] + 7.2679491924311227064725537*xi[1]*xi[1] + 18.1698729810778067661813841*xi[1]*xi[2], + 6.2942286340599478208735085 - 54.399346400575248278477328*xi[0] + 48.1051177665153004576038195*xi[0]*xi[0] - 12.5884572681198956417470171*xi[1] + 96.210235533030600915207639*xi[0]*xi[1] + 4.60769515458673623883532195*xi[2] + 37.203193977868616397894989*xi[0]*xi[2] - 21.803847577293368119417661*xi[1]*xi[2] - 10.9019237886466840597088305*xi[2]*xi[2] + }; + } + if (i == 21) { + return vec3{ + 2.24871130596428210938424878*xi[0] - 17.4974226119285642187684976*xi[0]*xi[0] - 3.63397459621556135323627683*xi[0]*xi[1] + 6.5551362713290860100334122*xi[0]*xi[2], + -1.12435565298214105469212439*xi[1] + 43.4974226119285642187684976*xi[0]*xi[1] - 3.63397459621556135323627683*xi[1]*xi[1] - 11.8756443470178589453078756*xi[1]*xi[2], + -1.53589838486224541294510732 + 3.8948822334846995423961805*xi[0] + 12.8897274573418279799331756*xi[0]*xi[0] + 6.2942286340599478208735085*xi[1] - 48.1051177665153004576038195*xi[0]*xi[1] - 1.12435565298214105469212439*xi[2] - 8.5025773880714357812315024*xi[0]*xi[2] + 10.9019237886466840597088305*xi[1]*xi[2] + 2.66025403784438646763723171*xi[2]*xi[2] + }; + } + if (i == 22) { + return vec3{ + 3.0717967697244908258902146*xi[0] - 4.607695154586736238835322*xi[0]*xi[0] - 0.973720558371174885599045*xi[0]*xi[1] - 7.2679491924311227064725537*xi[0]*xi[2], + -42.3730669589464231640763732*xi[1] + 43.497422611928564218768498*xi[0]*xi[1] + 47.131397208144125572004774*xi[1]*xi[1] + 55.373066958946423164076373*xi[1]*xi[2], + -15.2487113059642821093842488 + 29.6743371481683555022625317*xi[0] - 12.8897274573418279799331756*xi[0]*xi[0] + 71.485226280623708138992843*xi[1] - 73.884572681198956417470171*xi[0]*xi[1] - 60.994845223857128437536995*xi[1]*xi[1] + 39.3012701892219323381861585*xi[2] - 34.2820323027550917410978537*xi[0]*xi[2] - 93.289073857917076258410504*xi[1]*xi[2] - 24.0525588832576502288019098*xi[2]*xi[2] + }; + } + if (i == 23) { + return vec3{ + -45.4448637286709139899665878*xi[0] + 51.739092362730861810840096*xi[0]*xi[0] + 44.471143170299739104367543*xi[0]*xi[1] + 62.641016151377545870548927*xi[0]*xi[2], + 45.4448637286709139899665878*xi[1] - 44.471143170299739104367543*xi[0]*xi[1] - 51.739092362730861810840096*xi[1]*xi[1] - 62.641016151377545870548927*xi[1]*xi[2], + 41.810889132455352636730311*xi[0] - 48.1051177665153004576038195*xi[0]*xi[0] - 41.810889132455352636730311*xi[1] + 48.1051177665153004576038195*xi[1]*xi[1] - 59.00704155516198451731265*xi[0]*xi[2] + 59.00704155516198451731265*xi[1]*xi[2] + }; + } + if (i == 24) { + return vec3{ + -3.0717967697244908258902146*xi[0] + 4.607695154586736238835322*xi[0]*xi[0] + 7.267949192431122706472554*xi[0]*xi[1] + 0.973720558371174885599045*xi[0]*xi[2], + 15.2487113059642821093842488 - 29.6743371481683555022625317*xi[0] + 12.8897274573418279799331756*xi[0]*xi[0] - 39.3012701892219323381861585*xi[1] + 34.282032302755091741097854*xi[0]*xi[1] + 24.05255888325765022880191*xi[1]*xi[1] - 71.485226280623708138992843*xi[2] + 73.884572681198956417470171*xi[0]*xi[2] + 93.289073857917076258410504*xi[1]*xi[2] + 60.994845223857128437536995*xi[2]*xi[2], + 42.3730669589464231640763732*xi[2] - 43.4974226119285642187684976*xi[0]*xi[2] - 55.373066958946423164076373*xi[1]*xi[2] - 47.1313972081441255720047744*xi[2]*xi[2] + }; + } + if (i == 25) { + return vec3{ + -42.3730669589464231640763732*xi[0] + 47.1313972081441255720047744*xi[0]*xi[0] + 55.373066958946423164076373*xi[0]*xi[1] + 43.4974226119285642187684976*xi[0]*xi[2], + -15.2487113059642821093842488 + 71.485226280623708138992843*xi[0] - 60.994845223857128437536995*xi[0]*xi[0] + 39.3012701892219323381861585*xi[1] - 93.289073857917076258410504*xi[0]*xi[1] - 24.0525588832576502288019098*xi[1]*xi[1] + 29.6743371481683555022625317*xi[2] - 73.884572681198956417470171*xi[0]*xi[2] - 34.2820323027550917410978537*xi[1]*xi[2] - 12.8897274573418279799331756*xi[2]*xi[2], + 3.0717967697244908258902146*xi[2] - 0.9737205583711748855990451*xi[0]*xi[2] - 7.2679491924311227064725537*xi[1]*xi[2] - 4.607695154586736238835322*xi[2]*xi[2] + }; + } + if (i == 26) { + return vec3{ + 3.63397459621556135323627683*xi[0] - 3.6339745962155613532362768*xi[0]*xi[0] - 3.6339745962155613532362768*xi[0]*xi[1] - 7.2679491924311227064725537*xi[0]*xi[2], + -6.2942286340599478208735085 + 54.399346400575248278477328*xi[0] - 48.1051177665153004576038195*xi[0]*xi[0] - 4.60769515458673623883532195*xi[1] - 37.203193977868616397894989*xi[0]*xi[1] + 10.9019237886466840597088305*xi[1]*xi[1] + 12.5884572681198956417470171*xi[2] - 96.210235533030600915207639*xi[0]*xi[2] + 21.803847577293368119417661*xi[1]*xi[2], + 0.9737205583711748855990451*xi[2] + 44.4711431702997391043675427*xi[0]*xi[2] - 18.1698729810778067661813841*xi[1]*xi[2] - 7.2679491924311227064725537*xi[2]*xi[2] + }; + } + if (i == 27) { + return vec3{ + -1.38526329025127924385202805*xi[0] - 13.8634480157130028655322207*xi[0]*xi[0] + 10.189110867544647363269689*xi[0]*xi[1] + 3.63397459621556135323627683*xi[0]*xi[2], + 4.75833024919770240792840122 - 50.5044641670905487360811476*xi[0] + 60.994845223857128437536995*xi[0]*xi[0] + 3.48333950160459518414319756*xi[1] + 28.7006165897971806166634866*xi[0]*xi[1] - 8.2416697508022975920715988*xi[1]*xi[1] - 6.2942286340599478208735085*xi[2] + 48.1051177665153004576038195*xi[0]*xi[2] - 10.9019237886466840597088305*xi[1]*xi[2], + -2.09807621135331594029116951*xi[2] - 0.9737205583711748855990451*xi[0]*xi[2] + 6.2942286340599478208735085*xi[1]*xi[2] + 3.63397459621556135323627683*xi[2]*xi[2] + }; + } + if (i == 28) { + return vec3{ + 2.09807621135331594029116951*xi[0] - 3.63397459621556135323627683*xi[0]*xi[0] - 6.2942286340599478208735085*xi[0]*xi[1] + 0.9737205583711748855990451*xi[0]*xi[2], + -4.75833024919770240792840122 + 6.2942286340599478208735085*xi[0] - 3.48333950160459518414319756*xi[1] + 10.9019237886466840597088305*xi[0]*xi[1] + 8.2416697508022975920715988*xi[1]*xi[1] + 50.5044641670905487360811476*xi[2] - 48.1051177665153004576038195*xi[0]*xi[2] - 28.7006165897971806166634866*xi[1]*xi[2] - 60.994845223857128437536995*xi[2]*xi[2], + 1.38526329025127924385202805*xi[2] - 3.63397459621556135323627683*xi[0]*xi[2] - 10.189110867544647363269689*xi[1]*xi[2] + 13.8634480157130028655322207*xi[2]*xi[2] + }; + } + if (i == 29) { + return vec3{ + -0.9737205583711748855990451*xi[0] + 7.2679491924311227064725537*xi[0]*xi[0] + 18.1698729810778067661813841*xi[0]*xi[1] - 44.4711431702997391043675427*xi[0]*xi[2], + 6.2942286340599478208735085 - 12.5884572681198956417470171*xi[0] + 4.60769515458673623883532195*xi[1] - 21.803847577293368119417661*xi[0]*xi[1] - 10.9019237886466840597088305*xi[1]*xi[1] - 54.399346400575248278477328*xi[2] + 96.210235533030600915207639*xi[0]*xi[2] + 37.203193977868616397894989*xi[1]*xi[2] + 48.1051177665153004576038195*xi[2]*xi[2], + -3.63397459621556135323627683*xi[2] + 7.2679491924311227064725537*xi[0]*xi[2] + 3.6339745962155613532362768*xi[1]*xi[2] + 3.6339745962155613532362768*xi[2]*xi[2] + }; + } + if (i == 30) { + return vec3{ + 8.803847577293368119417661*xi[0] - 24.05255888325765022880191*xi[0]*xi[0] - 6.5551362713290860100334122*xi[0]*xi[1] - 10.189110867544647363269689*xi[0]*xi[2], + 4.196152422706631880582339*xi[1] - 7.267949192431122706472554*xi[0]*xi[1] - 2.6602540378443864676372317*xi[1]*xi[1] - 6.2942286340599478208735085*xi[1]*xi[2], + -13*xi[2] + 55.373066958946423164076373*xi[0]*xi[2] + 11.8756443470178589453078756*xi[1]*xi[2] + 8.2416697508022975920715988*xi[2]*xi[2] + }; + } + if (i == 31) { + return vec3{ + -8.803847577293368119417661*xi[0] + 24.0525588832576502288019098*xi[0]*xi[0] + 10.189110867544647363269689*xi[0]*xi[1] + 6.5551362713290860100334122*xi[0]*xi[2], + 13*xi[1] - 55.373066958946423164076373*xi[0]*xi[1] - 8.2416697508022975920715988*xi[1]*xi[1] - 11.8756443470178589453078756*xi[1]*xi[2], + -4.196152422706631880582339*xi[2] + 7.2679491924311227064725537*xi[0]*xi[2] + 6.2942286340599478208735085*xi[1]*xi[2] + 2.66025403784438646763723171*xi[2]*xi[2] + }; + } + if (i == 32) { + return vec3{ + 17.196152422706631880582339*xi[0] - 10.9019237886466840597088305*xi[0]*xi[0] - 62.641016151377545870548927*xi[0]*xi[1] - 18.1698729810778067661813841*xi[0]*xi[2], + 3.6339745962155613532362768*xi[0]*xi[1] - 3.6339745962155613532362768*xi[1]*xi[2], + -17.196152422706631880582339*xi[2] + 18.1698729810778067661813841*xi[0]*xi[2] + 62.641016151377545870548927*xi[1]*xi[2] + 10.9019237886466840597088305*xi[2]*xi[2] + }; + } + if (i == 33) { + return vec3{ + -13*xi[0] + 8.2416697508022975920715988*xi[0]*xi[0] + 55.373066958946423164076373*xi[0]*xi[1] + 11.8756443470178589453078756*xi[0]*xi[2], + 8.803847577293368119417661*xi[1] - 10.189110867544647363269689*xi[0]*xi[1] - 24.0525588832576502288019098*xi[1]*xi[1] - 6.5551362713290860100334122*xi[1]*xi[2], + 4.196152422706631880582339*xi[2] - 6.2942286340599478208735085*xi[0]*xi[2] - 7.2679491924311227064725537*xi[1]*xi[2] - 2.66025403784438646763723171*xi[2]*xi[2] + }; + } + if (i == 34) { + return vec3{ + 13*xi[0] - 8.2416697508022975920715988*xi[0]*xi[0] - 11.8756443470178589453078756*xi[0]*xi[1] - 55.373066958946423164076373*xi[0]*xi[2], + -4.196152422706631880582339*xi[1] + 6.2942286340599478208735085*xi[0]*xi[1] + 2.6602540378443864676372317*xi[1]*xi[1] + 7.2679491924311227064725537*xi[1]*xi[2], + -8.803847577293368119417661*xi[2] + 10.189110867544647363269689*xi[0]*xi[2] + 6.5551362713290860100334122*xi[1]*xi[2] + 24.0525588832576502288019098*xi[2]*xi[2] + }; + } + if (i == 35) { + return vec3{ + -17.196152422706631880582339*xi[0] + 10.9019237886466840597088305*xi[0]*xi[0] + 18.1698729810778067661813841*xi[0]*xi[1] + 62.641016151377545870548927*xi[0]*xi[2], + 17.196152422706631880582339*xi[1] - 18.1698729810778067661813841*xi[0]*xi[1] - 10.9019237886466840597088305*xi[1]*xi[1] - 62.641016151377545870548927*xi[1]*xi[2], + -3.6339745962155613532362768*xi[0]*xi[2] + 3.6339745962155613532362768*xi[1]*xi[2] + }; + } + if (i == 36) { + return vec3{ + -1.53589838486224541294510732 - 1.12435565298214105469212439*xi[0] + 2.6602540378443864676372317*xi[0]*xi[0] + 3.8948822334846995423961805*xi[1] - 8.502577388071435781231502*xi[0]*xi[1] + 12.8897274573418279799331756*xi[1]*xi[1] + 6.2942286340599478208735085*xi[2] + 10.9019237886466840597088305*xi[0]*xi[2] - 48.1051177665153004576038195*xi[1]*xi[2], + 2.24871130596428210938424878*xi[1] + 6.5551362713290860100334122*xi[0]*xi[1] - 17.4974226119285642187684976*xi[1]*xi[1] - 3.63397459621556135323627683*xi[1]*xi[2], + -1.12435565298214105469212439*xi[2] - 11.8756443470178589453078756*xi[0]*xi[2] + 43.4974226119285642187684976*xi[1]*xi[2] - 3.63397459621556135323627683*xi[2]*xi[2] + }; + } + if (i == 37) { + return vec3{ + -4.75833024919770240792840122 - 3.48333950160459518414319756*xi[0] + 8.2416697508022975920715988*xi[0]*xi[0] + 50.5044641670905487360811476*xi[1] - 28.7006165897971806166634866*xi[0]*xi[1] - 60.994845223857128437536995*xi[1]*xi[1] + 6.2942286340599478208735085*xi[2] + 10.9019237886466840597088305*xi[0]*xi[2] - 48.1051177665153004576038195*xi[1]*xi[2], + 1.38526329025127924385202805*xi[1] - 10.189110867544647363269689*xi[0]*xi[1] + 13.8634480157130028655322207*xi[1]*xi[1] - 3.63397459621556135323627683*xi[1]*xi[2], + 2.09807621135331594029116951*xi[2] - 6.2942286340599478208735085*xi[0]*xi[2] + 0.9737205583711748855990451*xi[1]*xi[2] - 3.63397459621556135323627683*xi[2]*xi[2] + }; + } + if (i == 38) { + return vec3{ + 41.810889132455352636730311*xi[1] - 59.00704155516198451731265*xi[0]*xi[1] - 48.1051177665153004576038195*xi[1]*xi[1] - 41.810889132455352636730311*xi[2] + 59.00704155516198451731265*xi[0]*xi[2] + 48.1051177665153004576038195*xi[2]*xi[2], + -45.4448637286709139899665878*xi[1] + 62.641016151377545870548927*xi[0]*xi[1] + 51.739092362730861810840096*xi[1]*xi[1] + 44.471143170299739104367543*xi[1]*xi[2], + 45.4448637286709139899665878*xi[2] - 62.641016151377545870548927*xi[0]*xi[2] - 44.471143170299739104367543*xi[1]*xi[2] - 51.739092362730861810840096*xi[2]*xi[2] + }; + } + if (i == 39) { + return vec3{ + 15.2487113059642821093842488 - 39.3012701892219323381861585*xi[0] + 24.0525588832576502288019098*xi[0]*xi[0] - 71.485226280623708138992843*xi[1] + 93.289073857917076258410504*xi[0]*xi[1] + 60.994845223857128437536995*xi[1]*xi[1] - 29.6743371481683555022625317*xi[2] + 34.2820323027550917410978537*xi[0]*xi[2] + 73.884572681198956417470171*xi[1]*xi[2] + 12.8897274573418279799331756*xi[2]*xi[2], + 42.3730669589464231640763732*xi[1] - 55.373066958946423164076373*xi[0]*xi[1] - 47.1313972081441255720047744*xi[1]*xi[1] - 43.4974226119285642187684976*xi[1]*xi[2], + -3.0717967697244908258902146*xi[2] + 7.2679491924311227064725537*xi[0]*xi[2] + 0.9737205583711748855990451*xi[1]*xi[2] + 4.607695154586736238835322*xi[2]*xi[2] + }; + } + if (i == 40) { + return vec3{ + 1.53589838486224541294510732 + 1.12435565298214105469212439*xi[0] - 2.6602540378443864676372317*xi[0]*xi[0] - 6.2942286340599478208735085*xi[1] - 10.9019237886466840597088305*xi[0]*xi[1] - 3.8948822334846995423961805*xi[2] + 8.5025773880714357812315024*xi[0]*xi[2] + 48.1051177665153004576038195*xi[1]*xi[2] - 12.8897274573418279799331756*xi[2]*xi[2], + 1.12435565298214105469212439*xi[1] + 11.8756443470178589453078756*xi[0]*xi[1] + 3.63397459621556135323627683*xi[1]*xi[1] - 43.4974226119285642187684976*xi[1]*xi[2], + -2.24871130596428210938424878*xi[2] - 6.5551362713290860100334122*xi[0]*xi[2] + 3.63397459621556135323627683*xi[1]*xi[2] + 17.4974226119285642187684976*xi[2]*xi[2] + }; + } + if (i == 41) { + return vec3{ + -6.2942286340599478208735085 - 4.60769515458673623883532195*xi[0] + 10.9019237886466840597088305*xi[0]*xi[0] + 12.5884572681198956417470171*xi[1] + 21.803847577293368119417661*xi[0]*xi[1] + 54.399346400575248278477328*xi[2] - 37.203193977868616397894989*xi[0]*xi[2] - 96.210235533030600915207639*xi[1]*xi[2] - 48.1051177665153004576038195*xi[2]*xi[2], + 0.9737205583711748855990451*xi[1] - 18.1698729810778067661813841*xi[0]*xi[1] - 7.2679491924311227064725537*xi[1]*xi[1] + 44.4711431702997391043675427*xi[1]*xi[2], + 3.63397459621556135323627683*xi[2] - 3.6339745962155613532362768*xi[0]*xi[2] - 7.2679491924311227064725537*xi[1]*xi[2] - 3.6339745962155613532362768*xi[2]*xi[2] + }; + } + if (i == 42) { + return vec3{ + 0, + 64*xi[1] - 64*xi[0]*xi[1] - 64*xi[1]*xi[1] - 128*xi[1]*xi[2], + -64*xi[2] + 64*xi[0]*xi[2] + 128*xi[1]*xi[2] + 64*xi[2]*xi[2] + }; + } + if (i == 43) { + return vec3{ + -64*xi[0] + 64*xi[0]*xi[0] + 64*xi[0]*xi[1] + 128*xi[0]*xi[2], + 0, + 64*xi[2] - 128*xi[0]*xi[2] - 64*xi[1]*xi[2] - 64*xi[2]*xi[2] + }; + } + if (i == 44) { + return vec3{ + 64*xi[0] - 64*xi[0]*xi[0] - 128*xi[0]*xi[1] - 64*xi[0]*xi[2], + -64*xi[1] + 128*xi[0]*xi[1] + 64*xi[1]*xi[1] + 64*xi[1]*xi[2], + 0 + }; + } + } // if (p == 3) + + return {}; + } + + constexpr vec3 reoriented_shape_function_curl(vec3 xi, uint32_t i, int8_t transformation) const { + switch (transformation) { + case -1: return -shape_function_curl(xi, i); + case 0: return shape_function_curl(xi, i); + default: + // the way this element numbers its local dofs + // the first dof in that pair is always even + uint32_t ix = (i & 0xFFFFFFFE) + 0; + uint32_t iy = (i & 0xFFFFFFFE) + 1; + vec2 weights = face_transformation(transformation)[i % 2]; + return shape_function_curl(xi, ix) * weights[0] + shape_function_curl(xi, iy) * weights[1]; + } + } + + constexpr vec3 shape_function_derivative(vec3 xi, uint32_t i) const { + return shape_function_curl(xi, i); + } + + double shape_function_div(vec3 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + return 0.0; + } + if (p == 2) { + if (i == 0) { return -1.732050807568877293527446342 - 4.732050807568877293527446342*xi[0] + 1.732050807568877293527446342*xi[1] + 1.732050807568877293527446342*xi[2]; } + if (i == 1) { return 1.732050807568877293527446342 - 1.2679491924311227064725536585*xi[0] - 1.732050807568877293527446342*xi[1] - 1.732050807568877293527446342*xi[2]; } + if (i == 2) { return 0.6339745962155613532362768292*xi[0] - 2.366025403784438646763723171*xi[1]; } + if (i == 3) { return 2.366025403784438646763723171*xi[0] - 0.6339745962155613532362768292*xi[1]; } + if (i == 4) { return -1.732050807568877293527446342 + 1.732050807568877293527446342*xi[0] + 1.2679491924311227064725536585*xi[1] + 1.732050807568877293527446342*xi[2]; } + if (i == 5) { return 1.732050807568877293527446342 - 1.732050807568877293527446342*xi[0] + 4.732050807568877293527446342*xi[1] - 1.732050807568877293527446342*xi[2]; } + if (i == 6) { return -1.732050807568877293527446342 + 1.732050807568877293527446342*xi[0] + 1.732050807568877293527446342*xi[1] - 4.732050807568877293527446342*xi[2]; } + if (i == 7) { return 1.732050807568877293527446342 - 1.732050807568877293527446342*xi[0] - 1.732050807568877293527446342*xi[1] - 1.2679491924311227064725536585*xi[2]; } + if (i == 8) { return 0.6339745962155613532362768292*xi[0] - 2.366025403784438646763723171*xi[2]; } + if (i == 9) { return 2.366025403784438646763723171*xi[0] - 0.6339745962155613532362768292*xi[2]; } + if (i == 10) { return 0.6339745962155613532362768292*xi[1] - 2.366025403784438646763723171*xi[2]; } + if (i == 11) { return 2.366025403784438646763723171*xi[1] - 0.6339745962155613532362768292*xi[2]; } + if (i == 12) { return 6*xi[0] - 3*xi[1]; } + if (i == 13) { return -3*xi[0] - 3*xi[1]; } + if (i == 14) { return 6*xi[0] - 3*xi[2]; } + if (i == 15) { return -3*xi[0] + 6*xi[2]; } + if (i == 16) { return 0; } + if (i == 17) { return 0; } + if (i == 18) { return -3*xi[1] - 3*xi[2]; } + if (i == 19) { return -3*xi[1] + 6*xi[2]; } + } // if (p == 2) + if (p == 3) { + if (i == 0) { return -4.6243277820691389617264218 - 8.3223678689970410505146319*xi[0] + 21.4667582115526910866297217*xi[0]*xi[0] + 15.3577068878454845050412827*xi[1] + 23.3254021361589172685231189*xi[0]*xi[1] - 10.7333791057763455433148609*xi[1]*xi[1] + 15.3577068878454845050412827*xi[2] + 23.3254021361589172685231189*xi[0]*xi[2] - 21.4667582115526910866297217*xi[1]*xi[2] - 10.7333791057763455433148609*xi[2]*xi[2]; } + if (i == 1) { return 6.666666666666667 - 15.2732430892257989886650754*xi[0] - 40*xi[0]*xi[0]/3. - 40*xi[1]/3. + 25.0929723569031959546603017*xi[0]*xi[1] + 20*xi[1]*xi[1]/3. - 40*xi[2]/3. + 25.0929723569031959546603017*xi[0]*xi[2] + 40*xi[1]*xi[2]/3. + 20*xi[2]*xi[2]/3.; } + if (i == 2) { return -2.04233888459752770494024487 + 9.0597125733605946262346001*xi[0] - 8.1334248782193577532963884*xi[0]*xi[0] - 2.02437355451215117170794933*xi[1] - 6.2747809536131315714029913*xi[0]*xi[1] + 4.0667124391096788766481942*xi[1]*xi[1] - 2.02437355451215117170794933*xi[2] - 6.2747809536131315714029913*xi[0]*xi[2] + 8.1334248782193577532963884*xi[1]*xi[2] + 4.0667124391096788766481942*xi[2]*xi[2]; } + if (i == 3) { return -0.0165618601854139256815163943*xi[0] + 2.8867513459481288225457439*xi[0]*xi[0] + 6.1256131838926205072699555*xi[1] - 14.8000915448860244199630551*xi[0]*xi[1] - 2.8867513459481288225457439*xi[1]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2]; } + if (i == 4) { return -4.19757091807757909941129644*xi[0] + 11.8341924626904785937438341*xi[0]*xi[0] + 4.19757091807757909941129644*xi[1] - 11.8341924626904785937438341*xi[1]*xi[1] - 1.4245874315222387671726334*xi[0]*xi[2] + 1.4245874315222387671726334*xi[1]*xi[2]; } + if (i == 5) { return -6.1256131838926205072699555*xi[0] + 2.8867513459481288225457439*xi[0]*xi[0] + 0.0165618601854139256815163945*xi[1] + 14.8000915448860244199630551*xi[0]*xi[1] - 2.8867513459481288225457439*xi[1]*xi[1] - 2.75180789937663520346857598*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2]; } + if (i == 6) { return 2.04233888459752770494024487 + 2.02437355451215117170794934*xi[0] - 4.0667124391096788766481942*xi[0]*xi[0] - 9.0597125733605946262346001*xi[1] + 6.2747809536131315714029913*xi[0]*xi[1] + 8.1334248782193577532963884*xi[1]*xi[1] + 2.02437355451215117170794934*xi[2] - 8.1334248782193577532963884*xi[0]*xi[2] + 6.2747809536131315714029913*xi[1]*xi[2] - 4.0667124391096788766481942*xi[2]*xi[2]; } + if (i == 7) { return -6.666666666666667 + 40*xi[0]/3. - 20*xi[0]*xi[0]/3. + 15.2732430892257989886650754*xi[1] - 25.0929723569031959546603017*xi[0]*xi[1] + 40*xi[1]*xi[1]/3. + 40*xi[2]/3. - 40*xi[0]*xi[2]/3. - 25.0929723569031959546603017*xi[1]*xi[2] - 20*xi[2]*xi[2]/3.; } + if (i == 8) { return 4.6243277820691389617264218 - 15.3577068878454845050412827*xi[0] + 10.7333791057763455433148609*xi[0]*xi[0] + 8.3223678689970410505146319*xi[1] - 23.3254021361589172685231189*xi[0]*xi[1] - 21.4667582115526910866297217*xi[1]*xi[1] - 15.3577068878454845050412827*xi[2] + 21.4667582115526910866297217*xi[0]*xi[2] - 23.3254021361589172685231189*xi[1]*xi[2] + 10.7333791057763455433148609*xi[2]*xi[2]; } + if (i == 9) { return -4.6243277820691389617264218 + 15.3577068878454845050412827*xi[0] - 10.7333791057763455433148609*xi[0]*xi[0] + 15.3577068878454845050412827*xi[1] - 21.4667582115526910866297217*xi[0]*xi[1] - 10.7333791057763455433148609*xi[1]*xi[1] - 8.3223678689970410505146319*xi[2] + 23.3254021361589172685231189*xi[0]*xi[2] + 23.3254021361589172685231189*xi[1]*xi[2] + 21.4667582115526910866297217*xi[2]*xi[2]; } + if (i == 10) { return 6.666666666666667 - 40*xi[0]/3. + 20*xi[0]*xi[0]/3. - 40*xi[1]/3. + 40*xi[0]*xi[1]/3. + 20*xi[1]*xi[1]/3. - 15.2732430892257989886650754*xi[2] + 25.0929723569031959546603017*xi[0]*xi[2] + 25.0929723569031959546603017*xi[1]*xi[2] - 40*xi[2]*xi[2]/3.; } + if (i == 11) { return -2.04233888459752770494024487 - 2.02437355451215117170794933*xi[0] + 4.0667124391096788766481942*xi[0]*xi[0] - 2.02437355451215117170794933*xi[1] + 8.1334248782193577532963884*xi[0]*xi[1] + 4.0667124391096788766481942*xi[1]*xi[1] + 9.0597125733605946262346001*xi[2] - 6.2747809536131315714029913*xi[0]*xi[2] - 6.2747809536131315714029913*xi[1]*xi[2] - 8.1334248782193577532963884*xi[2]*xi[2]; } + if (i == 12) { return -0.0165618601854139256815163943*xi[0] + 2.8867513459481288225457439*xi[0]*xi[0] - 2.75180789937663520346857598*xi[0]*xi[1] + 6.1256131838926205072699555*xi[2] - 14.8000915448860244199630551*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2] - 2.8867513459481288225457439*xi[2]*xi[2]; } + if (i == 13) { return -4.19757091807757909941129644*xi[0] + 11.8341924626904785937438341*xi[0]*xi[0] - 1.4245874315222387671726334*xi[0]*xi[1] + 4.19757091807757909941129644*xi[2] + 1.4245874315222387671726334*xi[1]*xi[2] - 11.8341924626904785937438341*xi[2]*xi[2]; } + if (i == 14) { return -6.1256131838926205072699555*xi[0] + 2.8867513459481288225457439*xi[0]*xi[0] - 2.75180789937663520346857598*xi[0]*xi[1] + 0.0165618601854139256815163945*xi[2] + 14.8000915448860244199630551*xi[0]*xi[2] + 2.75180789937663520346857598*xi[1]*xi[2] - 2.8867513459481288225457439*xi[2]*xi[2]; } + if (i == 15) { return -0.0165618601854139256815163943*xi[1] - 2.75180789937663520346857598*xi[0]*xi[1] + 2.8867513459481288225457439*xi[1]*xi[1] + 6.1256131838926205072699555*xi[2] + 2.75180789937663520346857598*xi[0]*xi[2] - 14.8000915448860244199630551*xi[1]*xi[2] - 2.8867513459481288225457439*xi[2]*xi[2]; } + if (i == 16) { return -4.19757091807757909941129644*xi[1] - 1.4245874315222387671726334*xi[0]*xi[1] + 11.8341924626904785937438341*xi[1]*xi[1] + 4.19757091807757909941129644*xi[2] + 1.4245874315222387671726334*xi[0]*xi[2] - 11.8341924626904785937438341*xi[2]*xi[2]; } + if (i == 17) { return -6.1256131838926205072699555*xi[1] - 2.75180789937663520346857598*xi[0]*xi[1] + 2.8867513459481288225457439*xi[1]*xi[1] + 0.0165618601854139256815163945*xi[2] + 2.75180789937663520346857598*xi[0]*xi[2] + 14.8000915448860244199630551*xi[1]*xi[2] - 2.8867513459481288225457439*xi[2]*xi[2]; } + if (i == 18) { return -14.6865334794732115820381866*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0] + 2.09807621135331594029116951*xi[1] + 29.5237020535573893331694524*xi[0]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1] + 7.4185842870420888755656329*xi[0]*xi[2] + 3.63397459621556135323627683*xi[1]*xi[2]; } + if (i == 19) { return -11.4641016151377545870548927*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0] + 2.09807621135331594029116951*xi[1] - 1.8371685740841777511312659*xi[0]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1] + 13*xi[0]*xi[2] + 3.63397459621556135323627683*xi[1]*xi[2]; } + if (i == 20) { return -4.19615242270663188058233902*xi[0] + 24.0525588832576502288019098*xi[0]*xi[0] + 26.1506350946109661690930793*xi[1] - 27.6865334794732115820381866*xi[0]*xi[1] - 24.0525588832576502288019098*xi[1]*xi[1] - 7.2679491924311227064725537*xi[0]*xi[2] - 20.4185842870420888755656329*xi[1]*xi[2]; } + if (i == 21) { return 2.09807621135331594029116951*xi[0] - 12.0262794416288251144009549*xi[0]*xi[0] - 11.4641016151377545870548927*xi[1] - 1.8371685740841777511312659*xi[0]*xi[1] + 12.0262794416288251144009549*xi[1]*xi[1] + 3.63397459621556135323627683*xi[0]*xi[2] + 13*xi[1]*xi[2]; } + if (i == 22) { return 15.810889132455352636730311*xi[0] - 18.4711431702997391043675427*xi[0]*xi[0] - 17.9089653438086685770214805*xi[1] - 39.712812921102036696439141*xi[0]*xi[1] + 18.4711431702997391043675427*xi[1]*xi[1] - 23.0788383248864753432028646*xi[0]*xi[2] + 19.4448637286709139899665878*xi[1]*xi[2]; } + if (i == 23) { return 2.09807621135331594029116951*xi[0] + 2.09807621135331594029116951*xi[1] + 79.425625842204073392878283*xi[0]*xi[1] + 3.63397459621556135323627683*xi[0]*xi[2] + 3.63397459621556135323627683*xi[1]*xi[2]; } + if (i == 24) { return 15.810889132455352636730311*xi[0] - 18.4711431702997391043675427*xi[0]*xi[0] - 23.0788383248864753432028646*xi[0]*xi[1] - 17.9089653438086685770214805*xi[2] - 39.712812921102036696439141*xi[0]*xi[2] + 19.4448637286709139899665878*xi[1]*xi[2] + 18.4711431702997391043675427*xi[2]*xi[2]; } + if (i == 25) { return -17.9089653438086685770214805*xi[0] + 18.4711431702997391043675427*xi[0]*xi[0] + 19.4448637286709139899665878*xi[0]*xi[1] + 15.810889132455352636730311*xi[2] - 39.712812921102036696439141*xi[0]*xi[2] - 23.0788383248864753432028646*xi[1]*xi[2] - 18.4711431702997391043675427*xi[2]*xi[2]; } + if (i == 26) { return -4.19615242270663188058233902*xi[0] + 24.0525588832576502288019098*xi[0]*xi[0] - 7.2679491924311227064725537*xi[0]*xi[1] + 26.1506350946109661690930793*xi[2] - 27.6865334794732115820381866*xi[0]*xi[2] - 20.4185842870420888755656329*xi[1]*xi[2] - 24.0525588832576502288019098*xi[2]*xi[2]; } + if (i == 27) { return 2.09807621135331594029116951*xi[0] - 12.0262794416288251144009549*xi[0]*xi[0] + 3.63397459621556135323627683*xi[0]*xi[1] - 14.6865334794732115820381866*xi[2] + 29.5237020535573893331694524*xi[0]*xi[2] + 7.4185842870420888755656329*xi[1]*xi[2] + 12.0262794416288251144009549*xi[2]*xi[2]; } + if (i == 28) { return -14.6865334794732115820381866*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0] + 7.4185842870420888755656329*xi[0]*xi[1] + 2.09807621135331594029116951*xi[2] + 29.5237020535573893331694524*xi[0]*xi[2] + 3.63397459621556135323627683*xi[1]*xi[2] - 12.0262794416288251144009549*xi[2]*xi[2]; } + if (i == 29) { return 26.1506350946109661690930793*xi[0] - 24.0525588832576502288019098*xi[0]*xi[0] - 20.4185842870420888755656329*xi[0]*xi[1] - 4.19615242270663188058233902*xi[2] - 27.6865334794732115820381866*xi[0]*xi[2] - 7.2679491924311227064725537*xi[1]*xi[2] + 24.0525588832576502288019098*xi[2]*xi[2]; } + if (i == 30) { return -0.9737205583711748855990451*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[2] - 15.6602540378443864676372317*xi[1]*xi[2]; } + if (i == 31) { return 4.60769515458673623883532195*xi[0]*xi[1] - 0.97372055837117488559904512*xi[0]*xi[2] - 15.6602540378443864676372317*xi[1]*xi[2]; } + if (i == 32) { return -3.6339745962155613532362768*xi[0]*xi[1] + 31.3205080756887729352744634*xi[0]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]; } + if (i == 33) { return 4.60769515458673623883532195*xi[0]*xi[1] - 15.6602540378443864676372317*xi[0]*xi[2] - 0.97372055837117488559904512*xi[1]*xi[2]; } + if (i == 34) { return -15.6602540378443864676372317*xi[0]*xi[1] + 4.60769515458673623883532195*xi[0]*xi[2] - 0.97372055837117488559904512*xi[1]*xi[2]; } + if (i == 35) { return 31.3205080756887729352744634*xi[0]*xi[1] - 3.63397459621556135323627683*xi[0]*xi[2] - 3.63397459621556135323627683*xi[1]*xi[2]; } + if (i == 36) { return 2.09807621135331594029116951*xi[1] + 3.63397459621556135323627683*xi[0]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1] - 11.4641016151377545870548927*xi[2] + 13*xi[0]*xi[2] - 1.8371685740841777511312659*xi[1]*xi[2] + 12.0262794416288251144009549*xi[2]*xi[2]; } + if (i == 37) { return 2.09807621135331594029116951*xi[1] + 3.63397459621556135323627683*xi[0]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1] - 14.6865334794732115820381866*xi[2] + 7.4185842870420888755656329*xi[0]*xi[2] + 29.5237020535573893331694524*xi[1]*xi[2] + 12.0262794416288251144009549*xi[2]*xi[2]; } + if (i == 38) { return 2.09807621135331594029116951*xi[1] + 3.633974596215561353236277*xi[0]*xi[1] + 2.09807621135331594029116951*xi[2] + 3.63397459621556135323627683*xi[0]*xi[2] + 79.425625842204073392878283*xi[1]*xi[2]; } + if (i == 39) { return -17.9089653438086685770214805*xi[1] + 19.4448637286709139899665878*xi[0]*xi[1] + 18.4711431702997391043675427*xi[1]*xi[1] + 15.810889132455352636730311*xi[2] - 23.0788383248864753432028646*xi[0]*xi[2] - 39.712812921102036696439141*xi[1]*xi[2] - 18.4711431702997391043675427*xi[2]*xi[2]; } + if (i == 40) { return -11.4641016151377545870548927*xi[1] + 13*xi[0]*xi[1] + 12.0262794416288251144009549*xi[1]*xi[1] + 2.09807621135331594029116951*xi[2] + 3.63397459621556135323627683*xi[0]*xi[2] - 1.8371685740841777511312659*xi[1]*xi[2] - 12.0262794416288251144009549*xi[2]*xi[2]; } + if (i == 41) { return 26.1506350946109661690930793*xi[1] - 20.4185842870420888755656329*xi[0]*xi[1] - 24.0525588832576502288019098*xi[1]*xi[1] - 4.19615242270663188058233902*xi[2] - 7.2679491924311227064725537*xi[0]*xi[2] - 27.6865334794732115820381866*xi[1]*xi[2] + 24.0525588832576502288019098*xi[2]*xi[2]; } + if (i == 42) { return 32*xi[0]*xi[1] + 32*xi[0]*xi[2] - 32*xi[1]*xi[2]; } + if (i == 43) { return 32*xi[0]*xi[1] - 32*xi[0]*xi[2] + 32*xi[1]*xi[2]; } + if (i == 44) { return -32*xi[0]*xi[1] + 32*xi[0]*xi[2] + 32*xi[1]*xi[2]; } + } // if (p == 3) + + return {}; + } + + constexpr vec3 interpolate(vec3 xi, const double * values) const { + vec3 interpolated_value{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_value += values[i] * shape_function(xi, i); + } + return interpolated_value; + } + + constexpr vec3 curl(vec3 xi, const double * values) const { + vec3 interpolated_curl{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_curl += values[i] * shape_function_curl(xi, i); + } + return interpolated_curl; + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view) const { + return 0; + } + + nd::array< double, 3 > evaluate_shape_functions(nd::view xi) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + vec3 xi_i = vec3{xi(i, 0), xi(i, 1), xi(i, 2)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + vec3 phi_j = shape_function(xi_i, j); + shape_fns(i, j, 0) = phi_j[0]; + shape_fns(i, j, 1) = phi_j[1]; + shape_fns(i, j, 2) = phi_j[2]; + } + } + return shape_fns; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + value_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + for (uint32_t j = 0; j < dim; j++) { + sum[j] += shape_fns(q, i, j) * values_e(i); + } + } + values_q(q) = sum; + } + } + + nd::array< double, 3 > evaluate_shape_function_curls(nd::view xi) { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes(), 3}); + for (uint32_t i = 0; i < q; i++) { + vec3 xi_i = vec3{xi(i, 0), xi(i, 1), xi(i, 2)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + vec3 curl_phi_j = shape_function_curl(xi_i, j); + shape_fns(i, j, 0) = curl_phi_j[0]; + shape_fns(i, j, 1) = curl_phi_j[1]; + shape_fns(i, j, 2) = curl_phi_j[2]; + } + } + return shape_fns; + } + + void curl(nd::view values_q, nd::view values_e, nd::view shape_fn_curls, double * /*buffer*/) { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + derivative_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + for (uint32_t j = 0; j < dim; j++) { + sum[j] += shape_fn_curls(q, i, j) * values_e(i); + } + } + values_q(q) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_functions(nd::view xi, nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + vec3 xi_i = vec3{xi(i, 0), xi(i, 1), xi(i, 2)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + vec3 phi_j = shape_function(xi_i, j); + shape_fns(i, j, 0) = phi_j[0] * weights[i]; + shape_fns(i, j, 1) = phi_j[1] * weights[i]; + shape_fns(i, j, 2) = phi_j[2] * weights[i]; + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (uint32_t j = 0; j < dim; j++) { + sum += shape_fn(q, i, j) * source_q(q)[j]; + } + } + residual_e(i) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_function_curls(nd::view xi, nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + vec3 xi_i = vec3{xi(i, 0), xi(i, 1), xi(i, 2)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + vec3 dphi_j = shape_function_curl(xi_i, j); + shape_fns(i, j, 0) = dphi_j[0] * weights[i]; + shape_fns(i, j, 1) = dphi_j[1] * weights[i]; + shape_fns(i, j, 2) = dphi_j[2] * weights[i]; + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (uint32_t j = 0; j < dim; j++) { + sum += shape_fn(q, i, j) * flux_q(q)[j]; + } + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (int d = 0; d < dim; d++) { + sum += shape_fn_curl(q, i, d) * flux_q(q)[d]; + } + } + residual_e(i) = sum; + } + } + #endif + + uint32_t p; + +}; +// clang-format on + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/hcurl_triangle.hpp b/src/serac/numerics/refactor/elements/hcurl_triangle.hpp new file mode 100644 index 0000000000..70feba60cc --- /dev/null +++ b/src/serac/numerics/refactor/elements/hcurl_triangle.hpp @@ -0,0 +1,461 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +using namespace serac; + +// clang-format off +template <> +struct FiniteElement { + + using value_type = vec2; + using derivative_type = vec1; + + using source_type = vec2; + using flux_type = vec1; + + static constexpr int dim = 2; + + SERAC_HOST_DEVICE uint32_t num_nodes() const { return p * (p + 2); } + + #if 0 + // sam: we don't have a good way to get the orientation info from mfem into the cuda kernel + // so hcurl elements need to be handled slightly differently (e.g. the reorientation could happen in the + // "ElementRestriction" operators instead) + template < typename T > + SERAC_HOST_DEVICE void reorient(const TransformationType type, const Connection * tri, T * values) const { + + const Connection * edge = tri + Triangle::edge_offset; + + for (uint32_t e = 0; e < Triangle::num_edges; e++) { + if (edge[e].sign() == Sign::Negative) { + for (uint32_t i = 0; i < p; i++) { + values[p*e + i] *= -1; + } + } + } + + } + + SERAC_HOST_DEVICE void reorient(const TransformationType type, const Connection * tri, int8_t * transformation) { + + const Connection * edge = tri + Triangle::edge_offset; + + uint32_t count = 0; + for (uint32_t e = 0; e < Triangle::num_edges; e++) { + if (edge[e].sign() == Sign::Negative) { + for (uint32_t i = 0; i < p; i++) { + transformation[count++] = -1; + } + } else { + for (uint32_t i = 0; i < p; i++) { + transformation[count++] = 0; + } + } + } + + uint32_t nnodes = num_nodes(); + for (uint32_t k = count; k < nnodes; k++) { + transformation[k] = 0; + } + + } + #endif + + constexpr vec2 shape_function(vec2 xi, uint32_t i) const { + if (p == 1) { + if (i == 0) return {1.0 - xi[1], xi[0]}; + if (i == 1) return {-xi[1], xi[0]}; + if (i == 2) return {-xi[1], xi[0] - 1.0}; + } + + if (p == 2) { + if (i == 0) { + return vec2{ + 1.3660254037844386467637231708 - 1.732050807568877293527446342*xi[0] - 3.732050807568877293527446342*xi[1] + 1.732050807568877293527446342*xi[0]*xi[1] + 2.366025403784438646763723171*xi[1]*xi[1], + 1.3660254037844386467637231708*xi[0] - 1.732050807568877293527446342*xi[0]*xi[0] - 2.366025403784438646763723171*xi[0]*xi[1] + }; + } + if (i == 1) { + return vec2{ + -0.3660254037844386467637231708 + 1.732050807568877293527446342*xi[0] - 0.2679491924311227064725536585*xi[1] - 1.732050807568877293527446342*xi[0]*xi[1] + 0.6339745962155613532362768292*xi[1]*xi[1], + -0.3660254037844386467637231708*xi[0] + 1.732050807568877293527446342*xi[0]*xi[0] - 0.6339745962155613532362768292*xi[0]*xi[1] + }; + } + if (i == 2) { + return vec2{ + 1.*xi[1] - 2.366025403784438646763723171*xi[0]*xi[1] - 0.6339745962155613532362768292*xi[1]*xi[1], + -1.*xi[0] + 2.366025403784438646763723171*xi[0]*xi[0] + 0.6339745962155613532362768292*xi[0]*xi[1] + }; + } + if (i == 3) { + return vec2{ + 1.*xi[1] - 0.6339745962155613532362768292*xi[0]*xi[1] - 2.366025403784438646763723171*xi[1]*xi[1], + -1.*xi[0] + 0.6339745962155613532362768292*xi[0]*xi[0] + 2.366025403784438646763723171*xi[0]*xi[1] + }; + } + if (i == 4) { + return vec2{ + 0.3660254037844386467637231708*xi[1] + 0.6339745962155613532362768292*xi[0]*xi[1] - 1.732050807568877293527446342*xi[1]*xi[1], + 0.3660254037844386467637231708 + 0.2679491924311227064725536585*xi[0] - 0.6339745962155613532362768292*xi[0]*xi[0] - 1.732050807568877293527446342*xi[1] + 1.732050807568877293527446342*xi[0]*xi[1] + }; + } + if (i == 5) { + return vec2{ + -1.3660254037844386467637231708*xi[1] + 2.366025403784438646763723171*xi[0]*xi[1] + 1.732050807568877293527446342*xi[1]*xi[1], + -1.3660254037844386467637231708 + 3.732050807568877293527446342*xi[0] - 2.366025403784438646763723171*xi[0]*xi[0] + 1.732050807568877293527446342*xi[1] - 1.732050807568877293527446342*xi[0]*xi[1] + }; + } + if (i == 6) { + return vec2{ + 6.*xi[1] - 3.*xi[0]*xi[1] - 6.*xi[1]*xi[1], + -3.*xi[0] + 3.*xi[0]*xi[0] + 6.*xi[0]*xi[1] + }; + } + if (i == 7) { + return vec2{ + -3.*xi[1] + 6.*xi[0]*xi[1] + 3.*xi[1]*xi[1], + 6.*xi[0] - 6.*xi[0]*xi[0] - 3.*xi[0]*xi[1] + }; + } + } + + if (p == 3) { + if (i == 0) { + return vec2{ + 1.47883055770123614752987757 - 4.6243277820691389617264218*xi[0] + 3.33333333333333333333333333*xi[0]*xi[0] - 8.9733478255330900061205269*xi[1] + 15.3577068878454845050412827*xi[0]*xi[1] - 3.33333333333333333333333333*xi[0]*xi[0]*xi[1] + 14.3045824936940910415209517*xi[1]*xi[1] - 10.7333791057763455433148609*xi[0]*xi[1]*xi[1] - 6.8100652258622371829303024*xi[1]*xi[1]*xi[1], + 1.47883055770123614752987757*xi[0] - 4.6243277820691389617264218*xi[0]*xi[0] + 3.33333333333333333333333333*xi[0]*xi[0]*xi[0] - 7.4945172678318538585906493*xi[0]*xi[1] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[1] + 6.8100652258622371829303024*xi[0]*xi[1]*xi[1] + }; + } + if (i == 1) { + return vec2{ + -0.66666666666666666666666667 + 6.6666666666666666666666667*xi[0] - 6.6666666666666666666666667*xi[0]*xi[0] - 0.303288211279566160999204378*xi[1] - 13.3333333333333333333333333*xi[0]*xi[1] + 6.6666666666666666666666667*xi[0]*xi[0]*xi[1] + 3.55371777595813879120445478*xi[1]*xi[1] + 6.6666666666666666666666667*xi[0]*xi[1]*xi[1] - 2.58376289801190596353858374*xi[1]*xi[1]*xi[1], + -0.66666666666666666666666667*xi[0] + 6.6666666666666666666666667*xi[0]*xi[0] - 6.6666666666666666666666667*xi[0]*xi[0]*xi[0] - 0.96995487794623282766587104*xi[0]*xi[1] - 6.6666666666666666666666667*xi[0]*xi[0]*xi[1] + 2.58376289801190596353858374*xi[0]*xi[1]*xi[1] + }; + } + if (i == 2) { + return vec2{ + 0.1878361089654305191367891 - 2.04233888459752770494024487*xi[0] + 3.33333333333333333333333333*xi[0]*xi[0] + 1.00868684438153346064717759*xi[1] - 2.02437355451215117170794933*xi[0]*xi[1] - 3.33333333333333333333333333*xi[0]*xi[0]*xi[1] - 1.78650349992773900683519184*xi[1]*xi[1] + 4.0667124391096788766481942*xi[0]*xi[1]*xi[1] + 0.58998054658077502705122515*xi[1]*xi[1]*xi[1], + 0.1878361089654305191367891*xi[0] - 2.04233888459752770494024487*xi[0]*xi[0] + 3.33333333333333333333333333*xi[0]*xi[0]*xi[0] + 1.19652295334696397978396669*xi[0]*xi[1] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[1] - 0.58998054658077502705122515*xi[0]*xi[1]*xi[1] + }; + } + if (i == 3) { + return vec2{ + -0.79437851573161947186953064*xi[1] + 6.1256131838926205072699555*xi[0]*xi[1] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[1] + 0.0165618601854139256815163943*xi[1]*xi[1] - 2.8867513459481288225457439*xi[0]*xi[1]*xi[1] + 0.58998054658077502705122515*xi[1]*xi[1]*xi[1], + 0.79437851573161947186953064*xi[0] - 6.1256131838926205072699555*xi[0]*xi[0] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[0] - 0.0165618601854139256815163943*xi[0]*xi[1] + 2.8867513459481288225457439*xi[0]*xi[0]*xi[1] - 0.58998054658077502705122515*xi[0]*xi[1]*xi[1] + }; + } + if (i == 4) { + return vec2{ + -0.94714135339900646920604603*xi[1] + 4.19757091807757909941129644*xi[0]*xi[1] - 2.58376289801190596353858374*xi[0]*xi[0]*xi[1] + 4.19757091807757909941129644*xi[1]*xi[1] - 11.8341924626904785937438341*xi[0]*xi[1]*xi[1] - 2.58376289801190596353858374*xi[1]*xi[1]*xi[1], + 0.94714135339900646920604603*xi[0] - 4.19757091807757909941129644*xi[0]*xi[0] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[0] - 4.19757091807757909941129644*xi[0]*xi[1] + 11.8341924626904785937438341*xi[0]*xi[0]*xi[1] + 2.58376289801190596353858374*xi[0]*xi[1]*xi[1] + }; + } + if (i == 5) { + return vec2{ + -0.79437851573161947186953064*xi[1] + 0.0165618601854139256815163945*xi[0]*xi[1] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[1] + 6.1256131838926205072699555*xi[1]*xi[1] - 2.8867513459481288225457439*xi[0]*xi[1]*xi[1] - 6.8100652258622371829303024*xi[1]*xi[1]*xi[1], + 0.79437851573161947186953064*xi[0] - 0.0165618601854139256815163945*xi[0]*xi[0] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[0] - 6.1256131838926205072699555*xi[0]*xi[1] + 2.8867513459481288225457439*xi[0]*xi[0]*xi[1] + 6.8100652258622371829303024*xi[0]*xi[1]*xi[1] + }; + } + if (i == 6) { + return vec2{ + -0.1878361089654305191367891*xi[1] - 1.19652295334696397978396669*xi[0]*xi[1] + 0.58998054658077502705122515*xi[0]*xi[0]*xi[1] + 2.04233888459752770494024487*xi[1]*xi[1] + 4.0667124391096788766481942*xi[0]*xi[1]*xi[1] - 3.33333333333333333333333333*xi[1]*xi[1]*xi[1], + -0.1878361089654305191367891 - 1.00868684438153346064717759*xi[0] + 1.78650349992773900683519184*xi[0]*xi[0] - 0.58998054658077502705122515*xi[0]*xi[0]*xi[0] + 2.04233888459752770494024487*xi[1] + 2.02437355451215117170794934*xi[0]*xi[1] - 4.0667124391096788766481942*xi[0]*xi[0]*xi[1] - 3.33333333333333333333333333*xi[1]*xi[1] + 3.33333333333333333333333333*xi[0]*xi[1]*xi[1] + }; + } + if (i == 7) { + return vec2{ + 0.66666666666666666666666667*xi[1] + 0.96995487794623282766587105*xi[0]*xi[1] - 2.58376289801190596353858374*xi[0]*xi[0]*xi[1] - 6.6666666666666666666666667*xi[1]*xi[1] + 6.6666666666666666666666667*xi[0]*xi[1]*xi[1] + 6.6666666666666666666666667*xi[1]*xi[1]*xi[1], + 0.66666666666666666666666667 + 0.303288211279566160999204379*xi[0] - 3.55371777595813879120445479*xi[0]*xi[0] + 2.58376289801190596353858374*xi[0]*xi[0]*xi[0] - 6.6666666666666666666666667*xi[1] + 13.3333333333333333333333333*xi[0]*xi[1] - 6.6666666666666666666666667*xi[0]*xi[0]*xi[1] + 6.6666666666666666666666667*xi[1]*xi[1] - 6.6666666666666666666666667*xi[0]*xi[1]*xi[1] + }; + } + if (i == 8) { + return vec2{ + -1.47883055770123614752987757*xi[1] + 7.4945172678318538585906493*xi[0]*xi[1] - 6.8100652258622371829303024*xi[0]*xi[0]*xi[1] + 4.6243277820691389617264218*xi[1]*xi[1] - 10.7333791057763455433148609*xi[0]*xi[1]*xi[1] - 3.33333333333333333333333333*xi[1]*xi[1]*xi[1], + -1.47883055770123614752987757 + 8.9733478255330900061205269*xi[0] - 14.3045824936940910415209517*xi[0]*xi[0] + 6.8100652258622371829303024*xi[0]*xi[0]*xi[0] + 4.6243277820691389617264218*xi[1] - 15.3577068878454845050412827*xi[0]*xi[1] + 10.7333791057763455433148609*xi[0]*xi[0]*xi[1] - 3.33333333333333333333333333*xi[1]*xi[1] + 3.33333333333333333333333333*xi[0]*xi[1]*xi[1] + }; + } + if (i == 9) { + return vec2{ + 12.5884572681198956417470171*xi[1] - 17.9089653438086685770214805*xi[0]*xi[1] + 3.2224318643354569949832939*xi[0]*xi[0]*xi[1] - 27.8371685740841777511312659*xi[1]*xi[1] + 18.4711431702997391043675427*xi[0]*xi[1]*xi[1] + 15.2487113059642821093842488*xi[1]*xi[1]*xi[1], + -2.66025403784438646763723171*xi[0] + 5.8826859021798434626205256*xi[0]*xi[0] - 3.2224318643354569949832939*xi[0]*xi[0]*xi[0] + 15.810889132455352636730311*xi[0]*xi[1] - 18.4711431702997391043675427*xi[0]*xi[0]*xi[1] - 15.2487113059642821093842488*xi[0]*xi[1]*xi[1] + }; + } + if (i == 10) { + return vec2{ + -2.66025403784438646763723171*xi[1] + 15.810889132455352636730311*xi[0]*xi[1] - 15.2487113059642821093842488*xi[0]*xi[0]*xi[1] + 5.8826859021798434626205256*xi[1]*xi[1] - 18.4711431702997391043675427*xi[0]*xi[1]*xi[1] - 3.2224318643354569949832939*xi[1]*xi[1]*xi[1], + 12.5884572681198956417470171*xi[0] - 27.8371685740841777511312659*xi[0]*xi[0] + 15.2487113059642821093842488*xi[0]*xi[0]*xi[0] - 17.9089653438086685770214805*xi[0]*xi[1] + 18.4711431702997391043675427*xi[0]*xi[0]*xi[1] + 3.2224318643354569949832939*xi[0]*xi[1]*xi[1] + }; + } + if (i == 11) { + return vec2{ + -4.19615242270663188058233902*xi[1] + 26.1506350946109661690930793*xi[0]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + 4.19615242270663188058233902*xi[1]*xi[1] - 24.0525588832576502288019098*xi[0]*xi[1]*xi[1], + 2.09807621135331594029116951*xi[0] - 14.1243556529821410546921244*xi[0]*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[0] - 4.19615242270663188058233902*xi[0]*xi[1] + 24.0525588832576502288019098*xi[0]*xi[0]*xi[1] + }; + } + if (i == 12) { + return vec2{ + 2.09807621135331594029116951*xi[1] - 14.6865334794732115820381866*xi[0]*xi[1] + 15.2487113059642821093842488*xi[0]*xi[0]*xi[1] - 2.09807621135331594029116951*xi[1]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[1]*xi[1], + -2.66025403784438646763723171*xi[0] + 17.9089653438086685770214805*xi[0]*xi[0] - 15.2487113059642821093842488*xi[0]*xi[0]*xi[0] + 2.09807621135331594029116951*xi[0]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + }; + } + if (i == 13) { + return vec2{ + -2.66025403784438646763723171*xi[1] + 2.09807621135331594029116951*xi[0]*xi[1] + 17.9089653438086685770214805*xi[1]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[1]*xi[1] - 15.2487113059642821093842488*xi[1]*xi[1]*xi[1], + 2.09807621135331594029116951*xi[0] - 2.09807621135331594029116951*xi[0]*xi[0] - 14.6865334794732115820381866*xi[0]*xi[1] + 12.0262794416288251144009549*xi[0]*xi[0]*xi[1] + 15.2487113059642821093842488*xi[0]*xi[1]*xi[1] + }; + } + if (i == 14) { + return vec2{ + 2.09807621135331594029116951*xi[1] - 4.19615242270663188058233902*xi[0]*xi[1] - 14.1243556529821410546921244*xi[1]*xi[1] + 24.0525588832576502288019098*xi[0]*xi[1]*xi[1] + 12.0262794416288251144009549*xi[1]*xi[1]*xi[1], + -4.19615242270663188058233902*xi[0] + 4.19615242270663188058233902*xi[0]*xi[0] + 26.1506350946109661690930793*xi[0]*xi[1] - 24.0525588832576502288019098*xi[0]*xi[0]*xi[1] - 12.0262794416288251144009549*xi[0]*xi[1]*xi[1] + }; + } + } + + return {}; + } + + constexpr vec2 reoriented_shape_function(vec2 xi, uint32_t i, int8_t transformation) const { + if (transformation == -1) { + return -shape_function(xi, i); + } else { + return shape_function(xi, i); + } + } + + vec1 shape_function_curl(vec2 xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + return 2.0; + } + if (p == 2) { + if (i == 0) { return 5.098076211353315940291169512 - 5.196152422706631880582339025*xi[0] - 7.098076211353315940291169512*xi[1]; } + if (i == 1) { return -0.0980762113533159402911695123 + 5.196152422706631880582339025*xi[0] - 1.901923788646684059708830488*xi[1]; } + if (i == 2) { return -2. + 7.098076211353315940291169512*xi[0] + 1.901923788646684059708830488*xi[1]; } + if (i == 3) { return -2. + 1.901923788646684059708830488*xi[0] + 7.098076211353315940291169512*xi[1]; } + if (i == 4) { return -0.0980762113533159402911695123 - 1.901923788646684059708830488*xi[0] + 5.196152422706631880582339025*xi[1]; } + if (i == 5) { return 5.098076211353315940291169512 - 7.098076211353315940291169512*xi[0] - 5.196152422706631880582339025*xi[1]; } + if (i == 6) { return -9. + 9.*xi[0] + 18.*xi[1]; } + if (i == 7) { return 9. - 18.*xi[0] - 9.*xi[1]; } + } + if (p == 3) { + if (i == 0) { return 10.4521783832343261536504044 - 24.6063624519837624284941263*xi[0] + 13.3333333333333333333333333*xi[0]*xi[0] - 36.1036822552200359416325527*xi[1] + 42.9335164231053821732594435*xi[0]*xi[1] + 27.2402609034489487317212095*xi[1]*xi[1]; } + if (i == 1) { return -0.36337845538710050566746229 + 26.6666666666666666666666667*xi[0] - 26.6666666666666666666666667*xi[0]*xi[0] - 8.0773904298625104100747806*xi[1] - 26.6666666666666666666666667*xi[0]*xi[1] + 10.335051592047623854154335*xi[1]*xi[1]; } + if (i == 2) { return -0.82085073541610294151038849 - 2.0603042146829042381725404*xi[0] + 13.3333333333333333333333333*xi[0]*xi[0] + 4.76952995320244199345435038*xi[1] - 16.2668497564387155065927768*xi[0]*xi[1] - 2.3599221863231001082049006*xi[1]*xi[1]; } + if (i == 3) { return 1.58875703146323894373906129 - 18.3768395516778615218098664*xi[0] + 27.2402609034489487317212095*xi[0]*xi[0] - 0.049685580556241777044549183*xi[1] + 11.5470053837925152901829756*xi[0]*xi[1] - 2.3599221863231001082049006*xi[1]*xi[1]; } + if (i == 4) { return 1.89428270679801293841209206 - 12.5927127542327372982338893*xi[0] + 10.335051592047623854154335*xi[0]*xi[0] - 12.5927127542327372982338893*xi[1] + 47.3367698507619143749753366*xi[0]*xi[1] + 10.335051592047623854154335*xi[1]*xi[1]; } + if (i == 5) { return 1.58875703146323894373906129 - 0.0496855805562417770445491834*xi[0] - 2.3599221863231001082049006*xi[0]*xi[0] - 18.3768395516778615218098664*xi[1] + 11.5470053837925152901829756*xi[0]*xi[1] + 27.2402609034489487317212095*xi[1]*xi[1]; } + if (i == 6) { return -0.82085073541610294151038849 + 4.76952995320244199345435038*xi[0] - 2.3599221863231001082049006*xi[0]*xi[0] - 2.0603042146829042381725404*xi[1] - 16.2668497564387155065927768*xi[0]*xi[1] + 13.3333333333333333333333333*xi[1]*xi[1]; } + if (i == 7) { return -0.36337845538710050566746229 - 8.0773904298625104100747806*xi[0] + 10.335051592047623854154335*xi[0]*xi[0] + 26.6666666666666666666666667*xi[1] - 26.6666666666666666666666667*xi[0]*xi[1] - 26.6666666666666666666666667*xi[1]*xi[1]; } + if (i == 8) { return 10.4521783832343261536504044 - 36.1036822552200359416325527*xi[0] + 27.2402609034489487317212095*xi[0]*xi[0] - 24.6063624519837624284941263*xi[1] + 42.9335164231053821732594435*xi[0]*xi[1] + 13.3333333333333333333333333*xi[1]*xi[1]; } + if (i == 9) { return -15.2487113059642821093842488 + 29.6743371481683555022625317*xi[0] - 12.8897274573418279799331756*xi[0]*xi[0] + 71.485226280623708138992843*xi[1] - 73.884572681198956417470171*xi[0]*xi[1] - 60.994845223857128437536995*xi[1]*xi[1]; } + if (i == 10) { return 15.2487113059642821093842488 - 71.485226280623708138992843*xi[0] + 60.994845223857128437536995*xi[0]*xi[0] - 29.6743371481683555022625317*xi[1] + 73.884572681198956417470171*xi[0]*xi[1] + 12.8897274573418279799331756*xi[1]*xi[1]; } + if (i == 11) { return 6.2942286340599478208735085 - 54.399346400575248278477328*xi[0] + 48.1051177665153004576038195*xi[0]*xi[0] - 12.5884572681198956417470171*xi[1] + 96.210235533030600915207639*xi[0]*xi[1]; } + if (i == 12) { return -4.75833024919770240792840122 + 50.5044641670905487360811476*xi[0] - 60.994845223857128437536995*xi[0]*xi[0] + 6.2942286340599478208735085*xi[1] - 48.1051177665153004576038195*xi[0]*xi[1]; } + if (i == 13) { return 4.75833024919770240792840122 - 6.2942286340599478208735085*xi[0] - 50.5044641670905487360811476*xi[1] + 48.1051177665153004576038195*xi[0]*xi[1] + 60.994845223857128437536995*xi[1]*xi[1]; } + if (i == 14) { return -6.2942286340599478208735085 + 12.5884572681198956417470171*xi[0] + 54.399346400575248278477328*xi[1] - 96.210235533030600915207639*xi[0]*xi[1] - 48.1051177665153004576038195*xi[1]*xi[1]; } + } + + return {}; + } + + vec1 reoriented_shape_function_curl(vec2 xi, uint32_t i, int8_t transformation) const { + if (transformation == -1) { + return -shape_function_curl(xi, i); + } else { + return shape_function_curl(xi, i); + } + } + + vec1 shape_function_derivative(vec2 xi, uint32_t i) const { + return shape_function_curl(xi, i); + } + + vec1 shape_function_div(const double * xi, uint32_t i) const { + // expressions generated symbolically by mathematica + if (p == 1) { + return 0.0; + } + if (p == 2) { + if (i == 0) { return -1.732050807568877293527446342 - 2.366025403784438646763723171*xi[0] + 1.732050807568877293527446342*xi[1]; } + if (i == 1) { return 1.732050807568877293527446342 - 0.6339745962155613532362768292*xi[0] - 1.732050807568877293527446342*xi[1]; } + if (i == 2) { return 0.6339745962155613532362768292*xi[0] - 2.366025403784438646763723171*xi[1]; } + if (i == 3) { return 2.366025403784438646763723171*xi[0] - 0.6339745962155613532362768292*xi[1]; } + if (i == 4) { return -1.732050807568877293527446342 + 1.732050807568877293527446342*xi[0] + 0.6339745962155613532362768292*xi[1]; } + if (i == 5) { return 1.732050807568877293527446342 - 1.732050807568877293527446342*xi[0] + 2.366025403784438646763723171*xi[1]; } + if (i == 6) { return 6.*xi[0] - 3.*xi[1]; } + if (i == 7) { return -3.*xi[0] + 6.*xi[1]; } + } + if (p == 3) { + if (i == 0) { return -4.6243277820691389617264218 - 0.8278506011651871919239826*xi[0] + 10.7333791057763455433148609*xi[0]*xi[0] + 15.3577068878454845050412827*xi[1] + 6.9534637850578076991939381*xi[0]*xi[1] - 10.7333791057763455433148609*xi[1]*xi[1]; } + if (i == 1) { return 6.6666666666666666666666667 - 14.3032882112795661609992044*xi[0] - 6.6666666666666666666666667*xi[0]*xi[0] - 13.3333333333333333333333333*xi[1] + 18.5008591293571452604105008*xi[0]*xi[1] + 6.6666666666666666666666667*xi[1]*xi[1]; } + if (i == 2) { return -2.04233888459752770494024487 + 7.8631896200136306464506334*xi[0] - 4.0667124391096788766481942*xi[0]*xi[0] - 2.02437355451215117170794933*xi[1] - 7.846627759828216720769117*xi[0]*xi[1] + 4.0667124391096788766481942*xi[1]*xi[1]; } + if (i == 3) { return -0.0165618601854139256815163943*xi[0] + 2.8867513459481288225457439*xi[0]*xi[0] + 6.1256131838926205072699555*xi[1] - 14.8000915448860244199630551*xi[0]*xi[1] - 2.8867513459481288225457439*xi[1]*xi[1]; } + if (i == 4) { return -4.19757091807757909941129644*xi[0] + 11.8341924626904785937438341*xi[0]*xi[0] + 4.19757091807757909941129644*xi[1] + 0.e-25*xi[0]*xi[1] - 11.8341924626904785937438341*xi[1]*xi[1]; } + if (i == 5) { return -6.1256131838926205072699555*xi[0] + 2.8867513459481288225457439*xi[0]*xi[0] + 0.0165618601854139256815163945*xi[1] + 14.8000915448860244199630551*xi[0]*xi[1] - 2.8867513459481288225457439*xi[1]*xi[1]; } + if (i == 6) { return 2.04233888459752770494024487 + 2.02437355451215117170794934*xi[0] - 4.0667124391096788766481942*xi[0]*xi[0] - 7.8631896200136306464506334*xi[1] + 7.846627759828216720769117*xi[0]*xi[1] + 4.0667124391096788766481942*xi[1]*xi[1]; } + if (i == 7) { return -6.6666666666666666666666667 + 13.3333333333333333333333333*xi[0] - 6.6666666666666666666666667*xi[0]*xi[0] + 14.3032882112795661609992044*xi[1] - 18.5008591293571452604105008*xi[0]*xi[1] + 6.6666666666666666666666667*xi[1]*xi[1]; } + if (i == 8) { return 4.6243277820691389617264218 - 15.3577068878454845050412827*xi[0] + 10.7333791057763455433148609*xi[0]*xi[0] + 0.8278506011651871919239826*xi[1] - 6.9534637850578076991939381*xi[0]*xi[1] - 10.7333791057763455433148609*xi[1]*xi[1]; } + if (i == 9) { return 15.810889132455352636730311*xi[0] - 18.4711431702997391043675427*xi[0]*xi[0] - 17.9089653438086685770214805*xi[1] - 24.0525588832576502288019098*xi[0]*xi[1] + 18.4711431702997391043675427*xi[1]*xi[1]; } + if (i == 10) { return -17.9089653438086685770214805*xi[0] + 18.4711431702997391043675427*xi[0]*xi[0] + 15.810889132455352636730311*xi[1] - 24.0525588832576502288019098*xi[0]*xi[1] - 18.4711431702997391043675427*xi[1]*xi[1]; } + if (i == 11) { return -4.19615242270663188058233902*xi[0] + 24.0525588832576502288019098*xi[0]*xi[0] + 26.1506350946109661690930793*xi[1] - 24.0525588832576502288019098*xi[0]*xi[1] - 24.0525588832576502288019098*xi[1]*xi[1]; } + if (i == 12) { return 2.09807621135331594029116951*xi[0] - 12.0262794416288251144009549*xi[0]*xi[0] - 14.6865334794732115820381866*xi[1] + 30.4974226119285642187684976*xi[0]*xi[1] + 12.0262794416288251144009549*xi[1]*xi[1]; } + if (i == 13) { return -14.6865334794732115820381866*xi[0] + 12.0262794416288251144009549*xi[0]*xi[0] + 2.09807621135331594029116951*xi[1] + 30.4974226119285642187684976*xi[0]*xi[1] - 12.0262794416288251144009549*xi[1]*xi[1]; } + if (i == 14) { return 26.1506350946109661690930793*xi[0] - 24.0525588832576502288019098*xi[0]*xi[0] - 4.19615242270663188058233902*xi[1] - 24.0525588832576502288019098*xi[0]*xi[1] + 24.0525588832576502288019098*xi[1]*xi[1]; } + } + + return {}; + } + + vec2 interpolate(vec2 xi, const double * values) const { + vec2 interpolated_value{}; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_value += values[i] * shape_function(xi, i); + } + return interpolated_value; + } + + vec1 curl(vec2 xi, const double * values) const { + vec1 interpolated_curl = 0.0; + for (uint32_t i = 0; i < num_nodes(); i++) { + interpolated_curl += values[i] * shape_function_curl(xi, i); + } + return interpolated_curl; + } + + SERAC_HOST_DEVICE uint32_t batch_interpolation_scratch_space(nd::view) const { + return 0; + } + + nd::array< double, 3 > evaluate_shape_functions(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + vec2 xi_i = vec2{xi(i, 0), xi(i, 1)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + vec2 phi_j = shape_function(xi_i, j); + shape_fns(i, j, 0) = phi_j[0]; + shape_fns(i, j, 1) = phi_j[1]; + } + } + return shape_fns; + } + + void interpolate(nd::view values_q, nd::view values_e, nd::view shape_fns, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + value_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + for (uint32_t j = 0; j < dim; j++) { + sum[j] += shape_fns(q, i, j) * values_e(i); + } + } + values_q(q) = sum; + } + } + + nd::array< double, 2 > evaluate_shape_function_curls(nd::view xi) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + vec2 xi_i = vec2{xi(i, 0), xi(i, 1)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + shape_fns(i, j) = shape_function_curl(xi_i, j); + } + } + return shape_fns; + } + + void curl(nd::view values_q, nd::view values_e, nd::view shape_fn_curls, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = values_q.shape[0]; + + for (uint32_t q = 0; q < nqpts; q++) { + derivative_type sum{}; + for (uint32_t i = 0; i < nnodes; i++) { + sum[0] += shape_fn_curls(q, i) * values_e(i); + } + values_q(q) = sum; + } + } + + nd::array< double, 3 > evaluate_weighted_shape_functions(nd::view xi, nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes(), dim}); + for (uint32_t i = 0; i < q; i++) { + vec2 xi_i = vec2{xi(i, 0), xi(i, 1)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + vec2 phi_j = shape_function(xi_i, j); + shape_fns(i, j, 0) = phi_j[0] * weights[i]; + shape_fns(i, j, 1) = phi_j[1] * weights[i]; + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_source(nd::view residual_e, nd::view source_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = source_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + for (uint32_t j = 0; j < dim; j++) { + sum += shape_fn(q, i, j) * source_q(q)[j]; + } + } + residual_e(i) = sum; + } + } + + nd::array< double, 2 > evaluate_weighted_shape_function_curls(nd::view xi, nd::view weights) const { + uint32_t q = xi.shape[0]; + nd::array shape_fns({q, num_nodes()}); + for (uint32_t i = 0; i < q; i++) { + vec2 xi_i = vec2{xi(i, 0), xi(i, 1)}; + for (uint32_t j = 0; j < num_nodes(); j++) { + shape_fns(i, j) = shape_function_curl(xi_i, j) * weights[i]; + } + } + return shape_fns; + } + + SERAC_HOST_DEVICE void integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (uint32_t i = 0; i < nnodes; i++) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + + #ifdef __CUDACC__ + __device__ void cuda_integrate_flux(nd::view residual_e, nd::view flux_q, nd::view shape_fn_curl, double * /*buffer*/) const { + uint32_t nnodes = num_nodes(); + uint32_t nqpts = flux_q.shape[0]; + + for (int i = threadIdx.x; i < nnodes; i += blockDim.x) { + double sum = 0.0; + for (uint32_t q = 0; q < nqpts; q++) { + sum += shape_fn_curl(q, i) * flux_q(q); + } + residual_e(i) = sum; + } + } + #endif + + uint32_t p; + +}; +// clang-format on + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/hcurl_vertex.hpp b/src/serac/numerics/refactor/elements/hcurl_vertex.hpp new file mode 100644 index 0000000000..1a7d6c2a28 --- /dev/null +++ b/src/serac/numerics/refactor/elements/hcurl_vertex.hpp @@ -0,0 +1,14 @@ +#pragma once + + + +namespace refactor { + +template <> +struct FiniteElement < mfem::Geometry::POINT, Family::HCURL >{ + SERAC_HOST_DEVICE uint32_t num_nodes() const { return 0; } + + uint32_t p; +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/elements/tensor_contractions.hpp b/src/serac/numerics/refactor/elements/tensor_contractions.hpp new file mode 100644 index 0000000000..5edcd8f5fa --- /dev/null +++ b/src/serac/numerics/refactor/elements/tensor_contractions.hpp @@ -0,0 +1,174 @@ +#pragma once + +#include +#include "serac/numerics/refactor/containers/ndarray.hpp" + +inline void contract(const nd::view & A, nd::view & B, nd::view C, bool accumulate = false) { + // A1(qx, iz, iy) = B(qx, ix) * in(iz, iy, ix) + // A2(qy, qx, iz) = B(qy, iy) * A1(qx, iz, iy) + // out(qz, qy, qx) = B(qz, iz) * A2(qy, qx, iz) + uint32_t n0 = C.shape[0]; + uint32_t n1 = C.shape[1]; + uint32_t n2 = C.shape[2]; + uint32_t m = A.shape[2]; + for (uint32_t i0 = 0; i0 < n0; i0++) { + for (uint32_t i1 = 0; i1 < n1; i1++) { + for (uint32_t i2 = 0; i2 < n2; i2++) { + double sum = (accumulate) ? C(i0, i1, i2) : 0.0; + for (uint32_t j = 0; j < m; j++) { + sum += B(i0, j) * A(i1, i2, j); + } + C(i0, i1, i2) = sum; + } + } + } +} + +/// C(qx, iy) {=,+=} sum_{ix} A(qx, ix) * B(iy, ix) +inline void _contract(nd::view C, const nd::view & A, const nd::view & B, bool accumulate = false) { + uint32_t n0 = C.shape[0]; + uint32_t n1 = C.shape[1]; + uint32_t m = A.shape[1]; + assert(A.shape[0] == C.shape[0]); + assert(B.shape[0] == C.shape[1]); + assert(A.shape[1] == B.shape[1]); + for (uint32_t i0 = 0; i0 < n0; i0++) { + for (uint32_t i1 = 0; i1 < n1; i1++) { + double sum = (accumulate) ? C(i0, i1) : 0.0; + for (uint32_t j = 0; j < m; j++) { + sum += A(i0, j) * B(i1, j); + } + C(i0, i1) = sum; + } + } +} + +template < int i > +void contract(const nd::view & A, nd::view & B, nd::view C, bool accumulate = false) { + uint32_t n0 = C.shape[0]; + uint32_t n1 = C.shape[1]; + uint32_t m = A.shape[i]; + assert(C.shape[1] == B.shape[0]); + assert(A.shape[i] == B.shape[1]); + assert(A.shape[1-i] == C.shape[0]); + for (uint32_t i0 = 0; i0 < n0; i0++) { + for (uint32_t i1 = 0; i1 < n1; i1++) { + double sum = (accumulate) ? C(i0, i1) : 0.0; + for (uint32_t j = 0; j < m; j++) { + if constexpr (i == 0) { sum += A(j, i0) * B(i1, j); } + if constexpr (i == 1) { sum += A(i0, j) * B(i1, j); } + } + C(i0, i1) = sum; + } + } +} + +inline void contract(const nd::view & A, nd::view & B, const nd::view C, bool accumulate = false) { + uint32_t n = C.shape[0]; + uint32_t m = A.shape[0]; + for (uint32_t i = 0; i < n; i++) { + double sum = (accumulate) ? C(i) : 0.0; + for (uint32_t j = 0; j < m; j++) { + sum += A(j) * B(i, j); + } + C(i) = sum; + } +} + +#ifdef __CUDACC__ +struct threadid { + int x; + int y; + int z; + int stride; +}; + +__device__ __forceinline__ void cuda_contract(threadid tid, const nd::view & A, const nd::view & B, nd::view & C, bool accumulate = false) { + uint32_t n0 = C.shape[0]; + uint32_t n1 = C.shape[1]; + uint32_t n2 = C.shape[2]; + uint32_t m = A.shape[2]; + + for (uint32_t i0 = tid.z; i0 < n0; i0 += tid.stride) { + for (uint32_t i1 = tid.y; i1 < n1; i1 += tid.stride) { + for (uint32_t i2 = tid.x; i2 < n2; i2 += tid.stride) { + double sum = (accumulate) ? C(i0, i1, i2) : 0.0; + for (int j = 0; j < m; j++) { + sum += B(i0, j) * A(i1, i2, j); + } + C(i0, i1, i2) = sum; + } + } + } + __syncthreads(); +} + +template < int i > +__device__ __forceinline__ void cuda_contract(threadid tid, const nd::view & A, const nd::view & B, nd::view C, bool accumulate = false) { + uint32_t n0 = C.shape[0]; + uint32_t n1 = C.shape[1]; + uint32_t m = A.shape[i]; + for (uint32_t i0 = tid.y; i0 < n0; i0 += tid.stride) { + for (uint32_t i1 = tid.x; i1 < n1; i1 += tid.stride) { + double sum = (accumulate) ? C(i0, i1) : 0.0; + for (int j = 0; j < m; j++) { + if constexpr (i == 0) { sum += A(j, i0) * B(i1, j); } + if constexpr (i == 1) { sum += A(i0, j) * B(i1, j); } + } + C(i0, i1) = sum; + } + } + __syncthreads(); +} + +///// C(qx, iy) {=,+=} sum_{ix} A(qx, ix) * B(iy, ix) +//inline void _contract(nd::view C, const nd::view & A, const nd::view & B, bool accumulate = false) { +// uint32_t n0 = C.shape[0]; +// uint32_t n1 = C.shape[1]; +// uint32_t m = A.shape[1]; +// assert(A.shape[0] == C.shape[0]); +// assert(B.shape[0] == C.shape[1]); +// assert(A.shape[1] == B.shape[1]); +// for (uint32_t i0 = 0; i0 < n0; i0++) { +// for (uint32_t i1 = 0; i1 < n1; i1++) { +// double sum = (accumulate) ? C(i0, i1) : 0.0; +// for (int j = 0; j < m; j++) { +// sum += A(i0, j) * B(i1, j); +// } +// C(i0, i1) = sum; +// } +// } +//} +// +//template < int i > +//void contract(const nd::view & A, nd::view & B, nd::view C, bool accumulate = false) { +// uint32_t n0 = C.shape[0]; +// uint32_t n1 = C.shape[1]; +// uint32_t m = A.shape[i]; +// assert(C.shape[1] == B.shape[0]); +// assert(A.shape[i] == B.shape[1]); +// assert(A.shape[1-i] == C.shape[0]); +// for (uint32_t i0 = 0; i0 < n0; i0++) { +// for (uint32_t i1 = 0; i1 < n1; i1++) { +// double sum = (accumulate) ? C(i0, i1) : 0.0; +// for (int j = 0; j < m; j++) { +// if constexpr (i == 0) { sum += A(j, i0) * B(i1, j); } +// if constexpr (i == 1) { sum += A(i0, j) * B(i1, j); } +// } +// C(i0, i1) = sum; +// } +// } +//} +// +//inline void contract(const nd::view & A, nd::view & B, const nd::view C, bool accumulate = false) { +// uint32_t n = C.shape[0]; +// uint32_t m = A.shape[0]; +// for (uint32_t i = 0; i < n; i++) { +// double sum = (accumulate) ? C(i) : 0.0; +// for (int j = 0; j < m; j++) { +// sum += A(j) * B(i, j); +// } +// C(i) = sum; +// } +//} +#endif diff --git a/src/serac/numerics/refactor/evaluate.cpp b/src/serac/numerics/refactor/evaluate.cpp new file mode 100644 index 0000000000..5c6bf12008 --- /dev/null +++ b/src/serac/numerics/refactor/evaluate.cpp @@ -0,0 +1,183 @@ +#if 1 +#include "evaluate.hpp" + +#include "common.hpp" + +namespace refactor { + +namespace impl { + +template < mfem::Geometry::Type geom, Family family, DerivedQuantity op > +void batched_interpolate(nd::view u_q, + const double * u, + uint32_t u_degree, + uint32_t u_components, + const std::vector & elements, + const nd::view xi) { + + uint32_t num_elements = uint32_t(elements.size()); + if (num_elements == 0) return; + + FiniteElement< geom, family > u_el{u_degree}; + + using output_t = typename std::conditional< + op == DerivedQuantity::VALUE, + typename FiniteElement< geom, family >::source_type, + typename FiniteElement< geom, family >::flux_type + >::type; + + nd::view output_q(reinterpret_cast(&u_q[0]), {u_q.shape[0], u_q.shape[1]}); + + uint32_t qpts_per_element = impl::qpe(xi.shape[0]); + + uint32_t u_nodes_per_element = u_el.num_nodes(); + uint32_t u_dofs_per_element = u_nodes_per_element * u_components; + auto u_shape_fns = [&](){ + if constexpr(op == DerivedQuantity::VALUE) { + return u_el.evaluate_shape_functions(xi); + } + + if constexpr(op == DerivedQuantity::DERIVATIVE && family == Family::HCURL) { + return u_el.evaluate_shape_function_curls(xi); + } + + if constexpr(op == DerivedQuantity::DERIVATIVE && is_scalar_valued(family)) { + return u_el.evaluate_shape_function_gradients(xi); + } + }(); + + // for each element with this geometry + nd::array u_ids({u_nodes_per_element}); + nd::array u_e({u_nodes_per_element}); + nd::array< double > u_scratch({u_el.batch_interpolation_scratch_space(xi)}); + + for (uint32_t i = 0; i < num_elements; i++) { + + nd::array u_xi_q({qpts_per_element}); + for (uint32_t c = 0; c < u_components; c++) { + + for (uint32_t j = 0; j < u_nodes_per_element; j++) { + u_e(j) = u[i * u_dofs_per_element + c * u_nodes_per_element + j]; + } + + //if constexpr (is_vector_valued(family)) { + // u_el.reorient(TransformationType::PhysicalToParent, &connectivity(elements(i), 0), u_e.data()); + //} + + // carry out the appropriate kind of interpolation + // for the requested family and differential operator + if constexpr (op == DerivedQuantity::VALUE) { + u_el.interpolate(u_xi_q, u_e, u_shape_fns, u_scratch.data()); + } + + if constexpr (op == DerivedQuantity::DERIVATIVE && is_scalar_valued(family)) { + u_el.gradient(u_xi_q, u_e, u_shape_fns, u_scratch.data()); + } + + if constexpr (op == DerivedQuantity::DERIVATIVE && family == Family::HCURL) { + u_el.curl(u_xi_q, u_e, u_shape_fns, u_scratch.data()); + } + + for (uint32_t q = 0; q < qpts_per_element; q++) { + output_q(i*qpts_per_element+q, c) = u_xi_q[q]; + } + + } + + } + +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +template < Family family, DerivedQuantity op > +void evaluate(nd::array & output, const Field & u_T, Domain & domain, const MeshQuadratureRule & qrule) { + + uint32_t gdim = static_cast(domain.dim_); + + auto qranges = ranges(qrule.num_qpts(domain)); + + uint32_t u_degree = get_degree(u_T); + uint32_t u_components = get_num_components(u_T); + mfem::FiniteElementSpace * u_fes = get_FES(u_T); + const mfem::Operator * P = u_fes->GetProlongationMatrix(); + + static mfem::Vector u_L; + u_L.SetSize(P->Height(), mfem::Device::GetMemoryType()); + P->Mult(u_T, u_L); + + // we just use this as a key to create/fetch the appropriate restriction operator + serac::FunctionSpace space{get_family(u_T), int(get_degree(u_T)), int(u_components)}; + + // insert_restriction is idempotent, so only the first call will do anything expensive + domain.insert_restriction(u_fes, space); + + const serac::BlockElementRestriction& G = domain.get_restriction(space); + + static mfem::Vector u_E_buffer; // persistent storage buffer to be used by u_E below + u_E_buffer.SetSize(int(G.ESize())); + mfem::BlockVector u_E(u_E_buffer, G.bOffsets()); + + G.Gather(u_L, u_E); + + foreach_geometry([&](auto geom){ + const std::vector & elements = domain.get(geom); + if (gdim == dimension(geom) && elements.size() > 0) { + nd::view xi = qrule[geom].points; + impl::batched_interpolate(output(qranges[geom]), u_E.GetBlock(geom).ReadWrite(), u_degree, u_components, elements, xi); + } + }); + +} + +} // namespace impl + +nd::array evaluate(const FieldOp && input, Domain & domain, const MeshQuadratureRule & qrule) { + + Family f = get_family(input.field); + + uint32_t gdim = geometry_dimension(domain); + uint32_t num_components = get_num_components(input.field); + stack::array output_dimensions{ + total(qrule.num_qpts(domain)), + num_components, + qshape(f, input.op, gdim) + }; + + nd::array u_q(output_dimensions); + + foreach_constexpr< Family::H1, Family::HCURL >([&](auto family) { + if (family == f) { + if (input.op == DerivedQuantity::VALUE) { + impl::evaluate(u_q, input.field, domain, qrule); + } + if (input.op == DerivedQuantity::DERIVATIVE) { + impl::evaluate(u_q, input.field, domain, qrule); + } + } + }); + + return u_q; + +} + +FieldOp grad(const Field & f) { + SLIC_ERROR_IF(!is_scalar_valued(get_family(f)), "grad(Field) only supports scalar-valued function spaces"); + return {DerivedQuantity::DERIVATIVE, f}; +} + +FieldOp curl(const Field & f) { + SLIC_ERROR_IF(get_family(f) != Family::HCURL, "curl(Field) only supports Family::Hcurl"); + return {DerivedQuantity::DERIVATIVE, f}; +} + +FieldOp div(const Field & f) { + SLIC_ERROR_IF(get_family(f) != Family::HDIV, "div(Field) only supports Family::Hdiv"); + return {DerivedQuantity::DERIVATIVE, f}; +} + + +} // namespace refactor +#endif diff --git a/src/serac/numerics/refactor/evaluate.hpp b/src/serac/numerics/refactor/evaluate.hpp new file mode 100644 index 0000000000..ee37d50e82 --- /dev/null +++ b/src/serac/numerics/refactor/evaluate.hpp @@ -0,0 +1,44 @@ +#pragma once + +#include "serac/numerics/functional/family.hpp" +#include "serac/numerics/refactor/containers/ndarray.hpp" +#include "serac/numerics/refactor/finite_element.hpp" +#include "serac/physics/state/finite_element_state.hpp" +#include "serac/physics/state/finite_element_dual.hpp" + +namespace refactor { + +using Field = serac::FiniteElementState; + +inline bool is_value(DerivedQuantity op) { + return op == DerivedQuantity::VALUE; +} + +inline bool is_derivative(DerivedQuantity op) { + return op == DerivedQuantity::DERIVATIVE; +} + +struct FieldOp { + const DerivedQuantity op; + const Field & field; + + FieldOp(const Field & f) : op(DerivedQuantity::VALUE), field(f){}; + FieldOp(const DerivedQuantity & o, const Field & f) : op(o), field(f){}; +}; + +//////////////////////////////////////////////////////////////////////////////// + +FieldOp grad(const Field & f); +FieldOp curl(const Field & f); +FieldOp div(const Field & f); + +//////////////////////////////////////////////////////////////////////////////// + +double dot(const Residual & r, const Field & u); +double dot(const Field & u, const Residual & r); + +//////////////////////////////////////////////////////////////////////////////// + +nd::array evaluate(const FieldOp && input, Domain & domain, const MeshQuadratureRule &); + +} diff --git a/src/serac/numerics/refactor/finite_element.hpp b/src/serac/numerics/refactor/finite_element.hpp new file mode 100644 index 0000000000..0d35c5a390 --- /dev/null +++ b/src/serac/numerics/refactor/finite_element.hpp @@ -0,0 +1,94 @@ +#pragma once + +#include "serac/numerics/functional/family.hpp" +#include "serac/numerics/functional/tensor.hpp" +#include "serac/numerics/refactor/geometry.hpp" +#include "serac/numerics/refactor/quadrature.hpp" +#include "serac/numerics/refactor/containers/ndarray.hpp" + +namespace refactor { + +using serac::Family; + +enum class Modifier { NONE, DIAGONAL, SYM }; +enum class DerivedQuantity { VALUE, DERIVATIVE }; + +SERAC_HOST_DEVICE constexpr bool is_scalar_valued(Family f) { + return (f == Family::H1) || (f == Family::L2); +} + +SERAC_HOST_DEVICE constexpr bool is_vector_valued(Family f) { + return (f == Family::HCURL) || (f == Family::HDIV); +} + +enum class TransformationType { + PhysicalToParent, + TransposePhysicalToParent, +}; + +template < mfem::Geometry::Type g, Family f > +struct FiniteElement; + +template < mfem::Geometry::Type geom, Family family > +auto shape_function_derivatives(FiniteElement< geom, family > element, + const nd::view xi) { + if constexpr (family == Family::H1) { + return element.evaluate_shape_function_gradients(xi); + } + + if constexpr (family == Family::HCURL) { + return element.evaluate_shape_function_curls(xi); + } +} + +template < mfem::Geometry::Type geom, Family family > +auto weighted_shape_function_derivatives(FiniteElement< geom, family > element, + const nd::view xi, + const nd::view weights) { + if constexpr (family == Family::H1) { + return element.evaluate_weighted_shape_function_gradients(xi, weights); + } + + if constexpr (family == Family::HCURL) { + return element.evaluate_weighted_shape_function_curls(xi, weights); + } +} + +SERAC_HOST_DEVICE constexpr serac::mat2 face_transformation(int8_t id) { + constexpr serac::mat2 matrices[5] = { + {{{0, 1}, {1, 0}}}, + {{{-1, 0}, {-1, 1}}}, + {{{1, -1}, {0, -1}}}, + {{{-1, -1}, {0, 1}}}, + {{{1, 0}, {-1, -1}}} + }; + + return matrices[id-1]; +} + +// sam: these orientations are for refactor's face orientation convention +SERAC_HOST_DEVICE constexpr int8_t face_transformation_id(TransformationType type, int orientation) { + if (type == TransformationType::PhysicalToParent) { + constexpr int8_t LUT[3] = {1, 2, 3}; + return LUT[orientation]; + } else { + constexpr int8_t LUT[3] = {1, 4, 5}; + return LUT[orientation]; + } +} + +} + +#include "serac/numerics/refactor/elements/h1_vertex.hpp" +#include "serac/numerics/refactor/elements/h1_edge.hpp" +#include "serac/numerics/refactor/elements/h1_triangle.hpp" +#include "serac/numerics/refactor/elements/h1_quadrilateral.hpp" +#include "serac/numerics/refactor/elements/h1_tetrahedron.hpp" +#include "serac/numerics/refactor/elements/h1_hexahedron.hpp" + +#include "serac/numerics/refactor/elements/hcurl_vertex.hpp" +#include "serac/numerics/refactor/elements/hcurl_edge.hpp" +#include "serac/numerics/refactor/elements/hcurl_triangle.hpp" +#include "serac/numerics/refactor/elements/hcurl_quadrilateral.hpp" +#include "serac/numerics/refactor/elements/hcurl_tetrahedron.hpp" +#include "serac/numerics/refactor/elements/hcurl_hexahedron.hpp" diff --git a/src/serac/numerics/refactor/forall.hpp b/src/serac/numerics/refactor/forall.hpp new file mode 100644 index 0000000000..1f47089fb7 --- /dev/null +++ b/src/serac/numerics/refactor/forall.hpp @@ -0,0 +1,288 @@ + +#pragma once + +#include + +#include "serac/numerics/functional/tensor.hpp" +#include "serac/numerics/refactor/containers/ndarray.hpp" + +namespace refactor { + +template < typename ... T > +struct type_list{}; + +template < typename T > +struct FunctionSignature; + +template < typename ret_t, typename ... arg_t > +struct FunctionSignature< ret_t (*)(arg_t ...) > { + using return_type = ret_t; + using argument_types = type_list< arg_t ... >; +}; + +template < typename obj_t, typename ret_t, typename ... arg_t > +struct FunctionSignature< ret_t (obj_t::*)(arg_t ...) const > { + using return_type = ret_t; + using argument_types = type_list< arg_t ... >; +}; + +using serac::vec; +using serac::mat; + +template < typename T > +auto make_ndarray(uint32_t length, T) { + return nd::array({length}); +} + +auto make_ndarray(uint32_t length, double) { + return nd::array({length, 1}); +} + +template < int n > +auto make_ndarray(uint32_t length, vec) { + return nd::array({length, uint32_t(n)}); +} + +template < int m, int n > +auto make_ndarray(uint32_t length, mat) { + return nd::array({length, uint32_t(m), uint32_t(n)}); +} + +template < int m, int n, int p, int q > +auto make_ndarray(uint32_t length, mat >) { + return nd::array({length, m, n, p, q}); +} + +template < typename T > +static constexpr bool is_vec(T) { return false; } + +template < typename T, uint32_t n > +static constexpr bool is_vec(vec) { return true; } + +template < typename T > +static constexpr bool is_mat(T) { return false; } + +template < typename T, uint32_t m, int n > +static constexpr bool is_mat(mat) { return true; } + +template < typename T, uint32_t n, uint32_t rank > +auto load_vec(const nd::array< T, rank > & arr, int i, vec) { + vec output; + for (uint32_t j = 0; j < n; j++) { + if constexpr (rank == 2) { + output[j] = arr(i,j); + } + if constexpr (rank == 3) { + output[j] = arr(i,0,j); + } + } + return output; +} + +template < typename T, uint32_t m, uint32_t n > +auto load_mat(const nd::array< T, 3 > & arr, int i, mat) { + mat output; + for (uint32_t j = 0; j < m; j++) { + for (uint32_t k = 0; k < n; k++) { + output(j,k) = arr(i,j,k); + } + } + return output; +} + +template < typename T, typename arr_type, uint32_t rank > +auto load(const nd::array< arr_type, rank > & arr, int i) { + if constexpr (std::is_same::value || + std::is_same::value) { + static_assert(rank == 1 || rank == 2 || rank == 3); + if constexpr (rank == 1) { return arr(i); } + if constexpr (rank == 2) { return arr(i,0); } + if constexpr (rank == 3) { return arr(i,0,0); } + } + + if constexpr (is_vec(T{})) { + static_assert(rank == 2 || rank == 3); + return load_vec(arr, i, T{}); + } + + if constexpr (is_mat(T{})) { + static_assert(rank == 3); + return load_mat(arr, i, T{}); + } +} + +template < typename T, int n, uint32_t rank > +void save_vec(nd::array< T, rank > & arr, int i, const vec & value) { + for (uint32_t j = 0; j < n; j++) { + if constexpr (rank == 2) { + arr(i,j) = value[j]; + } + if constexpr (rank == 3) { + arr(i,0,j) = value[j]; + } + } +} + +template < typename T, int m, int n > +void save_mat(nd::array< T, 3 > & arr, uint32_t i, const mat & value) { + for (uint32_t j = 0; j < m; j++) { + for (uint32_t k = 0; k < n; k++) { + arr(i,j,k) = value(j,k); + } + } +} + +template < typename T, typename arr_type, uint32_t rank > +auto save(nd::array< arr_type, rank > & arr, uint32_t i, const T & value) { + if constexpr (std::is_same::value || + std::is_same::value) { + if constexpr (rank == 1) arr(i) = value; + if constexpr (rank == 2) arr(i, 0) = value; + } + + if constexpr (is_vec(T{})) { + static_assert(rank == 2 || rank == 3); + save_vec(arr, i, value); + } + + if constexpr (is_mat(T{})) { + static_assert(rank == 3); + save_mat(arr, i, value); + } +} + +namespace impl { + +template < typename T, typename return_type, typename ... parameter_types > +auto forall(uint32_t n, const T & f, return_type * output, const parameter_types * ... args) { + for (uint32_t i = 0; i < n; i++) { + output[i] = f(args[i] ... ); + } +} + +template < typename output_type, typename ... input_types, typename callable, typename ... arg_types > +auto forall(output_type, type_list< input_types ... >, callable func, const arg_types & ... args) { + + uint32_t leading_dimensions[] = {args.shape[0] ...}; + uint32_t n = leading_dimensions[0]; + auto output = make_ndarray(n, output_type{}); + + { + impl::forall( + n, + func, + reinterpret_cast< output_type * >(output.data()), + reinterpret_cast< const input_types * >(args.data()) ... + ); + } + + return output; +} + +} + +template < typename return_type, typename ... parameter_types, typename ... arg_types > +auto forall(std::function< return_type(const parameter_types & ...) > f, const arg_types & ... args) { + + uint32_t leading_dimensions[] = {args.shape[0] ...}; + uint32_t n = leading_dimensions[0]; + auto output = make_ndarray(n, return_type{}); + + impl::forall( + n, + f, + reinterpret_cast< return_type * >(output.data()), + reinterpret_cast< const parameter_types * >(args.data()) ... + ); + + return output; +} + +template < typename return_type, typename ... parameter_types, typename ... arg_types > +auto forall(return_type (*f)(const parameter_types & ...), const arg_types & ... args) { + + uint32_t leading_dimensions[] = {args.shape[0] ...}; + uint32_t n = leading_dimensions[0]; + auto output = make_ndarray(n, return_type{}); + + impl::forall( + n, + f, + reinterpret_cast< return_type * >(output.data()), + reinterpret_cast< const parameter_types * >(args.data()) ... + ); + + return output; +} + +template < typename callable, typename ... arg_types > +auto forall(callable func, const arg_types & ... args) { + + using signature = FunctionSignature< decltype(&callable::operator()) >; + + return impl::forall( + typename signature::return_type{}, + typename signature::argument_types{}, + func, + args ... + ); + +} + +#ifdef __CUDACC__ + +template < typename functor, typename return_type, typename ... input_types > +__global__ void forall_kernel( + uint32_t n, + functor f, + return_type * output, + const input_types * ... inputs) { + int tid = threadIdx.x + blockIdx.x * blockDim.x; + if (tid < n) { + output[tid] = f(inputs[tid] ...); + } +} + +namespace impl { + +template < typename output_type, typename ... input_types, typename callable, typename ... arg_types > +auto cuda_forall(output_type, type_list< input_types ... >, callable func, const arg_types & ... args) { + + uint32_t leading_dimensions[] = {args.shape[0] ...}; + int n = leading_dimensions[0]; + auto output = make_ndarray(n, output_type{}); + + { + MTR_SCOPE("cuda_forall", "apply functor kernel"); + int blocksize = 128; + int gridsize = (n + blocksize - 1) / blocksize; + forall_kernel<<< gridsize, blocksize >>>( + n, + func, + reinterpret_cast< output_type * >(output.data()), + reinterpret_cast< const input_types * >(args.data()) ... + ); + cudaDeviceSynchronize(); + } + + return output; +} + +} + +template < typename callable, typename ... arg_types > +auto cuda_forall(callable func, const arg_types & ... args) { + + using signature = FunctionSignature< decltype(&callable::operator()) >; + + return impl::cuda_forall( + typename signature::return_type{}, + typename signature::argument_types{}, + func, + args ... + ); + +} +#endif + +} // namespace refactor diff --git a/src/serac/numerics/refactor/geometry.hpp b/src/serac/numerics/refactor/geometry.hpp new file mode 100644 index 0000000000..8b541e740f --- /dev/null +++ b/src/serac/numerics/refactor/geometry.hpp @@ -0,0 +1,304 @@ +#pragma once + +#include +#include + +#include "serac/infrastructure/accelerator.hpp" +#include "serac/numerics/refactor/containers/ndarray.hpp" + +#include "mfem.hpp" + +namespace refactor { + +namespace impl { + template < mfem::Geometry::Type g > + struct constexpr_geometry{ + constexpr operator mfem::Geometry::Type() { return g; } + }; +} + +template < typename T > +void foreach_geometry(T && function) { + function(impl::constexpr_geometry< mfem::Geometry::SEGMENT >{}); + function(impl::constexpr_geometry< mfem::Geometry::TRIANGLE >{}); + function(impl::constexpr_geometry< mfem::Geometry::SQUARE >{}); + function(impl::constexpr_geometry< mfem::Geometry::TETRAHEDRON >{}); + function(impl::constexpr_geometry< mfem::Geometry::CUBE >{}); +} + +inline const char * to_string(mfem::Geometry::Type g) { + switch (g) { + case mfem::Geometry::POINT: return "Geometry_Vertex"; + case mfem::Geometry::SEGMENT: return "Geometry_Edge"; + case mfem::Geometry::TRIANGLE: return "Geometry_Triangle"; + case mfem::Geometry::SQUARE: return "Geometry_Quadrilateral"; + case mfem::Geometry::TETRAHEDRON: return "Geometry_Tetrahedron"; + case mfem::Geometry::CUBE: return "Geometry_Hexahedron"; + default: return ""; + } + return ""; +} + +constexpr mfem::Geometry::Type all_geometries[6] = { + mfem::Geometry::POINT, + mfem::Geometry::SEGMENT, + mfem::Geometry::TRIANGLE, + mfem::Geometry::SQUARE, + mfem::Geometry::TETRAHEDRON, + mfem::Geometry::CUBE +}; + +constexpr nd::range geometries_by_dim[4] = { + {all_geometries+0, all_geometries+1}, + {all_geometries+1, all_geometries+2}, + {all_geometries+2, all_geometries+4}, + {all_geometries+4, all_geometries+6} +}; + +//constexpr uint32_t dimension(mfem::Geometry::Type g) { +SERAC_HOST_DEVICE constexpr uint32_t dimension(mfem::Geometry::Type g) { + switch (g) { + case mfem::Geometry::POINT: return 0; + case mfem::Geometry::SEGMENT: return 1; + case mfem::Geometry::TRIANGLE: return 2; + case mfem::Geometry::SQUARE: return 2; + case mfem::Geometry::TETRAHEDRON: return 3; + case mfem::Geometry::CUBE: return 3; + default: return 1u<<30; + } +} + +template < typename T > +struct GeometryData { + T vert; + T edge; + T tri; + T quad; + T tet; + T hex; + + T & operator[](mfem::Geometry::Type g) { + switch (g) { + case mfem::Geometry::POINT: return vert; + case mfem::Geometry::SEGMENT: return edge; + case mfem::Geometry::TRIANGLE: return tri; + case mfem::Geometry::SQUARE: return quad; + case mfem::Geometry::TETRAHEDRON: return tet; + case mfem::Geometry::CUBE: return hex; + default: return vert; // (hopefully) unreachable code, to silence compiler warnings + } + } + + const T & operator[](mfem::Geometry::Type g) const { + switch (g) { + case mfem::Geometry::POINT: return vert; + case mfem::Geometry::SEGMENT: return edge; + case mfem::Geometry::TRIANGLE: return tri; + case mfem::Geometry::SQUARE: return quad; + case mfem::Geometry::TETRAHEDRON: return tet; + case mfem::Geometry::CUBE: return hex; + default: return vert; // (hopefully) unreachable code, to silence compiler warnings + } + } + +}; + +struct GeometryInfo : public GeometryData { + static GeometryInfo from_array(uint32_t * data) { + return GeometryInfo { data[0], data[1], data[2], data[3], data[4], data[5] }; + } +}; + +inline void operator+=(GeometryInfo & a, const GeometryInfo & b) { + a.vert += b.vert; + a.edge += b.edge; + a.tri += b.tri; + a.quad += b.quad; + a.tet += b.tet; + a.hex += b.hex; +}; + +inline GeometryInfo operator*(GeometryInfo a, GeometryInfo b) { + return GeometryInfo{ + a.vert * b.vert, + a.edge * b.edge, + a.tri * b.tri, + a.quad * b.quad, + a.tet * b.tet, + a.hex * b.hex + }; +}; + +inline GeometryInfo operator*(GeometryInfo a, uint32_t scale) { + return GeometryInfo{ + a.vert * scale, + a.edge * scale, + a.tri * scale, + a.quad * scale, + a.tet * scale, + a.hex * scale + }; +}; + +inline GeometryData< nd::range > ranges(GeometryInfo a) { + GeometryData< nd::range > output; + + uint32_t total = 0; + output.vert = nd::range{total, total + a.vert}; total += a.vert; + output.edge = nd::range{total, total + a.edge}; total += a.edge; + output.tri = nd::range{total, total + a.tri}; total += a.tri; + output.quad = nd::range{total, total + a.quad}; total += a.quad; + output.tet = nd::range{total, total + a.tet}; total += a.tet; + output.hex = nd::range{total, total + a.hex}; total += a.hex; + + return output; +}; + +inline uint32_t total(GeometryInfo input){ + return input.vert + input.edge + input.tri + input.quad + input.tet + input.hex; +}; + +inline GeometryInfo scan(const GeometryInfo & input){ + GeometryInfo output; + output.vert = 0; + output.edge = output.vert + input.vert; + output.tri = output.edge + input.edge; + output.quad = output.tri + input.tri; + output.tet = output.quad + input.quad; + output.hex = output.tet + input.tet; + return output; +}; + +template < uint32_t n > +std::array< uint32_t, n + 1 > scan(const uint32_t (&input)[n]){ + std::array< uint32_t, n + 1 > output{}; + for (uint32_t i = 0; i < n; i++) { + output[i+1] = output[i] + input[i]; + } + return output; +}; + + + +template < mfem::Geometry::Type g > +struct GeometryType; + +template <> +struct GeometryType< mfem::Geometry::POINT > { + static constexpr mfem::Geometry::Type geometry = mfem::Geometry::POINT; + static constexpr int offset = 0; + static constexpr int dim = 0; +}; +using Vertex = GeometryType< mfem::Geometry::POINT >; + +template <> +struct GeometryType< mfem::Geometry::SEGMENT > { + static constexpr mfem::Geometry::Type geometry = mfem::Geometry::SEGMENT; + static constexpr int offset = 1; + + static constexpr int dim = 1; + static constexpr int num_vertices = 2; + + static constexpr int cell_offset = num_vertices; +}; +using Edge = GeometryType< mfem::Geometry::SEGMENT >; + +template <> +struct GeometryType< mfem::Geometry::TRIANGLE > { + static constexpr mfem::Geometry::Type geometry = mfem::Geometry::TRIANGLE; + static constexpr int offset = 2; + + static constexpr int dim = 2; + static constexpr int num_vertices = 3; + static constexpr int num_edges = 3; + + static constexpr int edge_offset = num_vertices; + static constexpr int cell_offset = num_vertices + num_edges; + + static constexpr int local_edge_ids[3][2] = {{0, 1},{1, 2},{2, 0}}; + + SERAC_HOST_DEVICE static constexpr uint32_t number(uint32_t n) { return (n * (n + 1)) / 2; }; +}; +using Triangle = GeometryType< mfem::Geometry::TRIANGLE >; + +template <> +struct GeometryType< mfem::Geometry::SQUARE > { + static constexpr mfem::Geometry::Type geometry = mfem::Geometry::SQUARE; + static constexpr int offset = 3; + + static constexpr int dim = 2; + static constexpr int num_vertices = 4; + static constexpr int num_edges = 4; + + static constexpr int edge_offset = num_vertices; + static constexpr int cell_offset = edge_offset + num_edges; + + static constexpr int local_edge_ids[4][4] = {{0, 1},{1, 2},{2, 3},{3,0}}; +}; +using Quadrilateral = GeometryType< mfem::Geometry::SQUARE >; + +template <> +struct GeometryType< mfem::Geometry::TETRAHEDRON > { + static constexpr mfem::Geometry::Type geometry = mfem::Geometry::TETRAHEDRON; + static constexpr int offset = 4; + + static constexpr int dim = 3; + static constexpr int num_vertices = 4; + static constexpr int num_edges = 6; + static constexpr int num_triangles = 4; + static constexpr int num_quadrilaterals = 0; + + static constexpr int edge_offset = num_vertices; + static constexpr int tri_offset = edge_offset + num_edges; + static constexpr int quad_offset = tri_offset + num_triangles; + static constexpr int cell_offset = quad_offset + num_quadrilaterals; + + static constexpr double vertices[4][3] = {{0,0,0}, {1,0,0}, {0,1,0}, {0,0,1}}; + static constexpr int local_edge_ids[6][2] = {{0, 1}, {1, 2}, {2, 0}, {0, 3}, {1, 3}, {2, 3}}; + static constexpr int local_triangle_ids[4][3] = {{2, 1, 0}, {0, 1, 3}, {1, 2, 3}, {2, 0, 3}}; + + SERAC_HOST_DEVICE static constexpr uint32_t number(uint32_t n) { return (n * (n + 1) * (n + 2)) / 6; } +}; +using Tetrahedron = GeometryType< mfem::Geometry::TETRAHEDRON >; + +template <> +struct GeometryType< mfem::Geometry::CUBE > { + static constexpr mfem::Geometry::Type geometry = mfem::Geometry::CUBE; + static constexpr int offset = 5; + + static constexpr int dim = 3; + static constexpr int num_vertices = 8; + static constexpr int num_edges = 12; + static constexpr int num_triangles = 0; + static constexpr int num_quadrilaterals = 6; + + static constexpr int edge_offset = num_vertices; + static constexpr int tri_offset = edge_offset + num_edges; + static constexpr int quad_offset = tri_offset + num_triangles; + static constexpr int cell_offset = quad_offset + num_quadrilaterals; + + // mathematica code for visualizing these edge/quad numberings + /* + localEdgeIds = 1 + {{0, 1},{1, 2},{3, 2},{0, 3},{0, 4},{1, 5},{2, 6},{3, 7},{4, 5},{5, 6},{7, 6},{4, 7}}; + localQuadIds = 1 + {{1, 0, 3, 2}, {0, 1, 5, 4}, {1, 2, 6, 5}, {2, 3, 7, 6}, {3, 0, 4, 7}, {4, 5, 6, 7}}; + vertices = {{-1, -1, -1}, {1, -1, -1}, {1, 1, -1}, {-1, 1, -1}, {-1, -1, 1}, {1, -1, 1}, {1, 1, 1}, {-1, 1, 1}}; + Graphics3D[{ + Thickness[0.01], JoinForm["Round"], Black, PointSize[0.03], + Point /@ vertices, Table[Text[Style[i - 1, Large], 1.2 vertices[[i]]], {i, 1, 8}], + Red, Arrow[( { {0.9, 0.1}, {0.1, 0.9} } ) . vertices[[#]]] & /@ localEdgeIds, + Table[Text[Style[i - 1, Large], 1.3 Mean[vertices[[localEdgeIds[[i]]]]]], {i, 1, 12}], + Blue, Arrow[( { + {0.7, 0.1, 0.1, 0.1}, + {0.1, 0.7, 0.1, 0.1}, + {0.1, 0.1, 0.7, 0.1}, + {0.1, 0.1, 0.1, 0.7} + } ) . vertices[[#]]] & /@ localQuadIds, + Table[Text[Style[i - 1, Large], Mean[vertices[[localQuadIds[[i]]]]]], {i, 1, 6}] + }, Boxed -> False] + */ + static constexpr int local_edge_ids[12][2] = {{0, 1},{1, 2},{3, 2},{0, 3},{0, 4},{1, 5},{2, 6},{3, 7},{4, 5},{5, 6},{7, 6},{4, 7}}; + static constexpr int local_quadrilateral_ids[6][4] = {{1, 0, 3, 2},{0, 1, 5, 4},{1, 2, 6, 5},{2, 3, 7, 6},{3, 0, 4, 7},{4, 5, 6, 7}}; +}; +using Hexahedron = GeometryType< mfem::Geometry::CUBE >; + +} diff --git a/src/serac/numerics/refactor/get_nodal_coordinates.cpp b/src/serac/numerics/refactor/get_nodal_coordinates.cpp new file mode 100644 index 0000000000..6123eea459 --- /dev/null +++ b/src/serac/numerics/refactor/get_nodal_coordinates.cpp @@ -0,0 +1,89 @@ +#if 0 +#include "serac/numerics/refactor/finite_element.hpp" + +namespace refactor { + +nd::array< double, 2 > get_nodal_coordinates(const Field & f) { + + uint32_t num_nodes = get_num_nodes(f); + uint32_t spatial_dimension = static_cast(f.mesh().SpaceDimension()); + + mfem::ParGridFunction pgf = f.gridFunction(); + + nd::array nodal_coords({num_nodes, spatial_dimension}); + + if (refactor::is_scalar_valued(get_family(f))) { + + for (uint32_t j = 0; j < spatial_dimension; j++) { + + // it seems there is no direct way to get the nodal coordinates + // for an mfem::GridFunction, so instead we proceed by asking pgf + // to evaluate the identity function at each of its nodes + mfem::FunctionCoefficient identity_function( + static_cast(spatial_dimension), + [&](const mfem::Vector& x) { + output = x[j]; + } + ); + + pgf.ProjectCoefficient(identity_function); + + // then, we extract the nodal coordinates from the gridfunction + for (uint32_t i = 0; i < num_nodes; i++) { + //nodal_coords(i, j) = pgf[static_cast(i * spatial_dimension + j)]; + nodal_coords(i, j) = pgf[static_cast(j * num_nodes + i)]; + } + + } + + return nodal_coords; + + } else { + + // with vector-valued fields, the workaround is weirder: + // if we evaluate the function f(x, y, z) = {x, 0, 0}, that will + // reveal the x-coordinate of the node times the length of the nodal direction + // + // so, to get just the coordinates, we need to compute the directions + // as well, so we can later divide through by their magnitudes. + + nd::array nodal_directions = get_nodal_directions(f); + + nd::array magnitudes({num_nodes}); + for (uint32_t i = 0; i < num_nodes; i++) { + double sum = 0.0; + for (uint32_t d = 0; d < spatial_dimension; d++) { + sum += nodal_directions(i, d) * nodal_directions(i, d); + } + magnitudes[i] = sqrt(sum); + } + + nd::array nodal_coords({num_nodes, spatial_dimension}); + + for (uint32_t d = 0; d < spatial_dimension; d++) { + + mfem::VectorFunctionCoefficient directional_identity_function( + static_cast(spatial_dimension), + [&](const mfem::Vector& x, mfem::Vector & output) { + output = 0.0; + output[static_cast(d)] = x[static_cast(d)]; + } + ); + + pgf.ProjectCoefficient(directional_identity_function); + + for (uint32_t i = 0; i < num_nodes; i++) { + nodal_coords(i, d) = pgf[static_cast(i * spatial_dimension + d)]; + } + + } + + return nodal_coords; + + + } + +} + +} +#endif diff --git a/src/serac/numerics/refactor/get_nodal_directions.cpp b/src/serac/numerics/refactor/get_nodal_directions.cpp new file mode 100644 index 0000000000..c619461499 --- /dev/null +++ b/src/serac/numerics/refactor/get_nodal_directions.cpp @@ -0,0 +1,43 @@ +#if 0 +#include "serac/numerics/refactor/finite_element.hpp" + +namespace refactor { + +nd::array< double, 2 > get_nodal_directions(const Field & f) { + + if (refactor::is_scalar_valued(get_family(f))) { + SLIC_ERROR("invalid function space for get_nodal_directions"); + } + + uint32_t num_nodes = get_num_nodes(f); + uint32_t spatial_dimension = static_cast(f.mesh().SpaceDimension()); + + mfem::ParGridFunction pgf = f.gridFunction(); + + // it seems there is no direct way to get the nodal directions + // for a mfem::GridFunction, so instead we proceed by asking pgf + // to evaluate the identity function at each of its nodes + mfem::VectorFunctionCoefficient identity_function( + static_cast(spatial_dimension), + [&](const mfem::Vector& x, mfem::Vector & output) { + output = x; + } + ); + + pgf.ProjectCoefficient(identity_function); + + // then, we extract the nodal coordinates from the gridfunction + nd::array nodal_coords({num_nodes, spatial_dimension}); + + for (uint32_t i = 0; i < num_nodes; i++) { + for (uint32_t j = 0; j < spatial_dimension; j++) { + nodal_coords(i, j) = pgf[static_cast(i * spatial_dimension + j)]; + } + } + + return nodal_coords; + +} + +} +#endif diff --git a/src/serac/numerics/refactor/integrate.hpp b/src/serac/numerics/refactor/integrate.hpp new file mode 100644 index 0000000000..b3d8804fd8 --- /dev/null +++ b/src/serac/numerics/refactor/integrate.hpp @@ -0,0 +1,309 @@ +#pragma once + +#include + +#include "serac/numerics/functional/family.hpp" +#include "serac/numerics/refactor/type_traits.hpp" +#include "serac/numerics/refactor/finite_element.hpp" +#include "serac/physics/state/finite_element_state.hpp" +#include "serac/physics/state/finite_element_dual.hpp" + +//#include "misc/for_constexpr.hpp" + +namespace refactor { + +struct BasisFunctionOp { + const Modifier mod; + const DerivedQuantity op; + const BasisFunction function; + + BasisFunctionOp(const BasisFunction & f) : mod(Modifier::NONE), op(DerivedQuantity::VALUE), function(f){}; + BasisFunctionOp(const DerivedQuantity & o, const BasisFunction & f) : mod(Modifier::NONE), op(o), function(f){}; + BasisFunctionOp(const Modifier & m, const DerivedQuantity & o, const BasisFunction & f) : mod(m), op(o), function(f){}; +}; + +BasisFunctionOp grad(const BasisFunction & phi); +BasisFunctionOp curl(const BasisFunction & phi); +BasisFunctionOp div(const BasisFunction & phi); + +// for integrating sparse matrices (e.g. mass, stiffness) +template < typename T1, typename T2, typename T3 > +struct WeightedIntegrand { + const T1 test; + const T2 & qdata; + const T3 trial; +}; + +// for integrating residual vectors +template < typename T1, typename T2 > +struct WeightedIntegrand< T1, T2, void > { + const T1 test; + const T2 & qdata; +}; + +inline BasisFunctionOp grad(const BasisFunction & f) { + SLIC_ERROR_IF(!is_scalar_valued(f.space.family), "grad(BasisFunction) only supports scalar-valued function spaces"); + return {DerivedQuantity::DERIVATIVE, f}; +} + +inline BasisFunctionOp curl(const BasisFunction & f) { + SLIC_ERROR_IF(f.space.family != Family::HCURL, "curl(BasisFunction) only supports Family::Hcurl"); + return {DerivedQuantity::DERIVATIVE, f}; +} + +inline BasisFunctionOp div(const BasisFunction & f) { + SLIC_ERROR_IF(f.space.family != Family::HDIV, "div(BasisFunction) only supports Family::Hdiv"); + return {DerivedQuantity::DERIVATIVE, f}; +} + +template < typename T > +struct DiagonalOnly : public T {}; + +template < typename T > +DiagonalOnly(T) -> DiagonalOnly; + +template < typename T, uint32_t n > +auto operator*(const nd::array & data, const BasisFunction & phi) { + return WeightedIntegrand< BasisFunctionOp, nd::array, void >{phi, data}; +} + +template < typename T, uint32_t n > +auto operator*(const nd::array & data, const BasisFunctionOp & dphi) { + return WeightedIntegrand< BasisFunctionOp, nd::array, void >{dphi, data}; +} + +template < typename T, uint32_t n > +auto dot(const nd::array & data, const BasisFunctionOp & dphi) { + return WeightedIntegrand< BasisFunctionOp, nd::array, void >{dphi, data}; +} + +template < typename T, uint32_t n > +auto diagonal(WeightedIntegrand< BasisFunctionOp, nd::array, BasisFunctionOp > integrand) { + SERAC_ASSERT( + integrand.test.function == integrand.trial.function, + "diag(...) requires same test and trial space" + ); + + return DiagonalOnly{integrand}; +} + +//////////////////////////////////////////////////////////////////////////////// + +template < typename T, uint32_t n > +auto dot(BasisFunctionOp psi, const nd::array & data, BasisFunctionOp phi) { + return WeightedIntegrand< BasisFunctionOp, nd::array, BasisFunctionOp >{phi, data, psi}; +} + +namespace impl { + +template < typename T > +struct is_a_weighted_integrand { + static constexpr bool value = false; +}; + +template < typename T1, typename T2, typename T3 > +struct is_a_weighted_integrand < WeightedIntegrand< T1, T2, T3 > >{ + static constexpr bool value = true; +}; + +template < typename T1, typename T2, typename T3 > +struct is_a_weighted_integrand < DiagonalOnly< WeightedIntegrand< T1, T2, T3 > > >{ + static constexpr bool value = true; +}; + +template < typename return_type, typename T > +uint32_t dimension_of_first_argument(return_type (* /*integrand*/)(T)) { + return dimension(T{}); +} + +template < typename return_type, typename T > +uint32_t dimension_of_first_argument(std::function< return_type(T) > /*integrand*/) { + return dimension(T{}); +} + +//////////////////////////////////////////////////////////////////////////////// + +#if 0 +template < typename T > +T integrate_ndarray(const nd::array< T > & integrand, const Domain& domain); + +//////////////////////////////////////////////////////////////////////////////// + +template < typename return_type > +return_type integrate_function_pointer(return_type (*f)(vec2), const Domain& domain, const DomainType & type); + +template < typename return_type > +return_type integrate_function_pointer(return_type (*f)(vec3), const Domain& domain, const DomainType & type); + +//////////////////////////////////////////////////////////////////////////////// + +template < typename return_type > +return_type integrate_stdfunction(std::function< return_type(vec2) > integrand, const Domain& domain, const DomainType & type); + +template < typename return_type > +return_type integrate_stdfunction(std::function< return_type(vec3) > integrand, const Domain& domain, const DomainType & type); +#endif + +//////////////////////////////////////////////////////////////////////////////// + +template < serac::Family family > +void integrate_residual(Residual & r, BasisFunctionOp b, const nd::view f, Domain & domain); + +template < uint32_t n > +Residual integrate_weighted_integrand( + const WeightedIntegrand< BasisFunctionOp, nd::array, void > & integrand, + Domain & domain) { + + DerivedQuantity op = integrand.test.op; + BasisFunction phi = integrand.test.function; + Family test_family = phi.space.family; + uint32_t p = phi.space.degree; + uint32_t components = phi.space.components; + uint32_t gdim = geometry_dimension(domain); + + Residual r(domain.mesh_, test_family, p, components); + + const nd::array & qdata = integrand.qdata; + + stack::array shape3D{qdata.shape[0], components, qshape(test_family, op, gdim)}; + + refactor_ASSERT(compatible_shapes(qdata.shape, shape3D), "incompatible array shapes"); + + nd::view q3D{qdata.data(), shape3D}; + foreach_constexpr< serac::Family::H1, serac::Family::Hcurl >([&](auto family) { + if (family == test_family) { + integrate_residual< family >(r, integrand.test, q3D, domain, type); + } + }); + + return r; +} + +//////////////////////////////////////////////////////////////////////////////// + +#if 0 +template +std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunctionOp phi, const nd::view f, BasisFunctionOp psi, const Domain &domain); + +template < uint32_t n > +std::function< void(refactor::sparse_matrix&) > integrate_weighted_integrand( + const WeightedIntegrand< BasisFunctionOp, nd::array, BasisFunctionOp > & integrand, + const Domain & domain) { + + BasisFunctionOp phi = integrand.test; + BasisFunctionOp psi = integrand.trial; + const nd::array & qdata = integrand.qdata; + + DerivedQuantity test_op = phi.op; + DerivedQuantity trial_op = psi.op; + FunctionSpace test_space = phi.function.space; + FunctionSpace trial_space = psi.function.space; + uint32_t test_components = phi.function.space.components; + uint32_t trial_components = psi.function.space.components; + uint32_t sdim = domain.mesh.spatial_dimension; + uint32_t gdim = domain.mesh.geometry_dimension; + + stack::array shape5D = { + qdata.shape[0], + phi.function.space.components, qshape(test_space.family, test_op, gdim), + psi.function.space.components, qshape(trial_space.family, trial_op, gdim) + }; + + SLIC_ASSER_MSH(compatible_shapes(qdata.shape, shape5D), "incompatible array shapes"); + + std::function< void(refactor::sparse_matrix&) > output; + + nd::view q5D{qdata.data(), shape5D}; + foreach_constexpr< serac::Family::H1, serac::Family::Hcurl >([&](auto test_family) { + foreach_constexpr< serac::Family::H1, serac::Family::Hcurl >([&](auto trial_family) { + if (test_family == test_space.family && trial_family == trial_space.family) { + output = integrate_sparse_matrix< test_family, trial_family >(phi, q5D, psi, domain, type); + } + }); + }); + + return output; + +} + +//////////////////////////////////////////////////////////////////////////////// + +template +void integrate_sparse_matrix_diagonal(Residual & r, BasisFunctionOp phi, const nd::view f, BasisFunctionOp psi, const Domain &domain); + +template < uint32_t n > +nd::array integrate_weighted_integrand( + const DiagonalOnly < WeightedIntegrand< BasisFunctionOp, nd::array, BasisFunctionOp > > & integrand, + const Domain & domain) { + + BasisFunctionOp phi = integrand.test; + BasisFunctionOp psi = integrand.trial; + const nd::array & qdata = integrand.qdata; + + SLIC_ASSERT_MSG(phi.function.space == psi.function.space, "must have matching test and trial spaces for diag(...)"); + + DerivedQuantity test_op = phi.op; + DerivedQuantity trial_op = psi.op; + Family test_family = phi.function.space.family; + Family trial_family = psi.function.space.family; + uint32_t test_components = phi.function.space.components; + uint32_t trial_components = psi.function.space.components; + uint32_t sdim = domain.mesh.spatial_dimension; + uint32_t gdim = domain.mesh.geometry_dimension; + + stack::array shape5D = { + qdata.shape[0], + phi.function.space.components, qshape(test_family, test_op, gdim), + psi.function.space.components, qshape(trial_family, trial_op, gdim) + }; + + SLIC_ASSERT_MSG(compatible_shapes(qdata.shape, shape5D), "incompatible array shapes"); + + Residual output(phi.function.space, domain.mesh); + + nd::view q5D{qdata.data(), shape5D}; + foreach_constexpr< Family::H1, Family::Hcurl >([&](auto family) { + if (family == test_family) { + integrate_sparse_matrix_diagonal< family >(output, phi, q5D, psi, domain, type); + } + }); + + return output.data; + +} +#endif + +} // namespace impl + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +template < typename integrand_t > +auto integrate(const integrand_t & integrand, Domain & domain) { + + //if constexpr (is_a_1D_ndarray::value) { + // return impl::integrate_ndarray(integrand, d.domain, d.type); + //} + + //if constexpr (is_a_function_pointer::value) { + // uint32_t sdim = impl::dimension_of_first_argument(integrand); + // SLIC_ASSERT_MSG(d.domain.mesh.X.data.shape[1] != sdim, "integration function has invalid signature"); + // return impl::integrate_function_pointer(integrand, d.domain, d.type); + //} + + //if constexpr (is_a_stdfunction::value) { + // uint32_t sdim = impl::dimension_of_first_argument(integrand); + // SLIC_ASSERT_MSG(d.domain.mesh.X.data.shape[1] != sdim, "integration function has invalid signature"); + // return impl::integrate_stdfunction(integrand, d.domain, d.type); + //} + + if constexpr (impl::is_a_weighted_integrand::value) { + return impl::integrate_weighted_integrand(integrand, domain); + } + + static_assert(always_true::value, "error: unsupported integrand type"); + +} + +} \ No newline at end of file diff --git a/src/serac/numerics/refactor/integrate_diag.cpp b/src/serac/numerics/refactor/integrate_diag.cpp new file mode 100644 index 0000000000..89abacc99a --- /dev/null +++ b/src/serac/numerics/refactor/integrate_diag.cpp @@ -0,0 +1,267 @@ +#if 0 +#include "common.hpp" + +namespace refactor { + +namespace impl { + +template < mfem::Geometry::Type geom, Family family, DerivedQuantity test_op, DerivedQuantity trial_op> +void batched_integrate_diag(nd::view D, + nd::view qdata, + const FunctionSpace space, + const Field & X, + const DomainType type, + const nd::view elements, + const nd::view xi, + const nd::view weights, + nd::array & D_e_buffer) { + + constexpr uint32_t gdim = dimension(geom); + constexpr uint32_t test_qshape = qshape(family, test_op, gdim); + constexpr uint32_t trial_qshape = qshape(family, trial_op, gdim); + + using test_qtype = vec; + using trial_qtype = vec; + using mat_t = mat; + + using test_Atype = decltype(piola_transformation(mat{})); + using trial_Atype = decltype(weighted_piola_transformation(mat{})); + + FiniteElement< geom, Family::H1 > X_el{get_degree(X)}; + FiniteElement< geom, family > el{space.degree}; + + uint32_t num_nodes = D.shape[0]; + uint32_t num_elements = elements.size(); + uint32_t num_components = space.components; + uint32_t nodes_per_element = el.num_nodes(); + uint32_t qpts_per_element = impl::qpe(xi.shape[0]); + + uint32_t X_components = get_num_components(X); + uint32_t X_nodes_per_element = X_el.num_nodes(); + + auto X_shape_fn_grads = X_el.evaluate_shape_function_gradients(xi); + + // When do we need to calculate dX/dxi? + // + // ❌ : don't need to ✅ : need to + // +---------------------+------+-------+------+----+ + // | | H1 | Hcurl | Hdiv | DG | + // +---------------------+------+-------+------+----+ + // | isoparametric value | ❌ | ❌ | ❌ | ❌ | + // +---------------------+------+-------+------+----+ + // | isoparametric deriv | ❌ | ❌ | ❌ | ❌ | + // +---------------------+------+-------+------+----+ + // | spatial value | ✅ | ✅ | ✅ | ✅ | + // +---------------------+------+-------+------+----+ + // | spatial deriv | ✅ | ✅ | ✅ | ✅ | + // +---------------------+------+-------+------+----+ + const bool need_to_compute_dX_dxi = (type == DomainType::SPATIAL); + + stack::array D_e_shape = {num_elements * nodes_per_element, num_components}; + + if (D_e_buffer.sz < nd::product(D_e_shape)) { + D_e_buffer.resize(nd::product(D_e_shape)); + } + + nd::view D_e(D_e_buffer.data(), D_e_shape); + + // for each element of this mfem::Geometry::Type in the domain + for (uint32_t e = 0; e < num_elements; e++) { + + nd::array testA_q; + nd::array trialA_q; + + if (need_to_compute_dX_dxi) { + nd::array, 2> dX_dxi_q({X_components, qpts_per_element}); + nd::array X_ids({X_nodes_per_element}); + nd::array X_e({X_nodes_per_element}); + nd::array X_scratch({X_el.batch_interpolation_scratch_space(xi)}); + + + for (uint32_t c = 0; c < X_components; c++) { + for (uint32_t j = 0; j < X_nodes_per_element; j++) { + X_e(j) = X.data(X_ids(j), c); + } + X_el.gradient(dX_dxi_q(c), X_e, X_shape_fn_grads, X_scratch.data()); + } + + testA_q.resize({qpts_per_element}); + trialA_q.resize({qpts_per_element}); + for (uint32_t q = 0; q < qpts_per_element; q++) { + mat dX_dxi; + for (uint32_t c = 0; c < gdim; c++) { + dX_dxi[c] = dX_dxi_q(c, q); + } + testA_q[q] = piola_transformation(dX_dxi); + trialA_q[q] = weighted_piola_transformation(dX_dxi); + } + } + + nd::array< int8_t > transformation({nodes_per_element}); + if constexpr (is_vector_valued(family)) { + el.reorient(TransformationType::TransposePhysicalToParent, &connectivity(elements(e), 0), transformation.data()); + } + + uint32_t qoffset = e * qpts_per_element; + + for (uint32_t i = 0; i < num_components; i++) { + for (uint32_t I = 0; I < nodes_per_element; I++) { + + double sum = 0.0; + + for (uint32_t q = 0; q < qpts_per_element; q++) { + uint32_t qid = qoffset + q; + + auto xi_q = quadrature_point(q, xi); + double wt = integration_weight(q, weights); + + mat_t C{}; + for (uint32_t k = 0; k < test_qshape; k++) { + for (uint32_t m = 0; m < trial_qshape; m++) { + C(k, m) = qdata(qid, i, k, i, m); + } + } + + test_qtype phi_I; + if constexpr (is_scalar_valued(family) && test_op == DerivedQuantity::VALUE) { + phi_I = el.shape_function(xi_q, I); + } + + if constexpr (is_scalar_valued(family) && test_op == DerivedQuantity::DERIVATIVE) { + phi_I = el.shape_function_gradient(xi_q, I); + } + + if constexpr (family == Family::HCURL && test_op == DerivedQuantity::VALUE) { + phi_I = el.reoriented_shape_function(xi_q, I, transformation[I]); + } + + if constexpr (family == Family::HCURL && test_op == DerivedQuantity::DERIVATIVE) { + phi_I = el.reoriented_shape_function_curl(xi_q, I, transformation[I]); + } + + trial_qtype psi_I; + if constexpr (is_scalar_valued(family) && trial_op == DerivedQuantity::VALUE) { + psi_I = el.shape_function(xi_q, I); + } + + if constexpr (is_scalar_valued(family) && trial_op == DerivedQuantity::DERIVATIVE) { + psi_I = el.shape_function_gradient(xi_q, I); + } + + if constexpr (family == Family::HCURL && trial_op == DerivedQuantity::VALUE) { + psi_I = el.reoriented_shape_function(xi_q, I, transformation[I]); + } + + if constexpr (family == Family::HCURL && trial_op == DerivedQuantity::DERIVATIVE) { + psi_I = el.reoriented_shape_function_curl(xi_q, I, transformation[I]); + } + + if (need_to_compute_dX_dxi) { + phi_I = serac::dot(phi_I, testA_q[q]); + psi_I = serac::dot(psi_I, trialA_q[q]); + } + + sum += serac::dot(serac::dot(phi_I, C), psi_I) * wt; + + } + + D_e(e * nodes_per_element + I, i) = sum; + + } + + } + + } + +} + +template +nd::array integrate_sparse_matrix_diagonal(BasisFunction test, const nd::array & qdata, BasisFunction trial, const Domain &domain, const DomainType type) { + + auto phi = test.space; + auto psi = trial.space; + + SLIC_ASSERT_MSG(phi == psi, "must have matching test and trial spaces for diag(...)"); + + uint32_t test_components = phi.components; + uint32_t trial_components = psi.components; + uint32_t sdim = spatial_dimension(domain); + uint32_t gdim = geometry_dimension(domain); + + stack::array shape5D = { + qdata.shape[0], + phi.components, qshape(phi.family, test_op, gdim), + psi.components, qshape(psi.family, trial_op, gdim) + }; + + SLIC_ASSERT_MSG(compatible_shapes(qdata.shape, shape5D), "incompatible array shapes"); + + nd::view q5D{qdata.data(), shape5D}; + + Residual output(phi, domain.mesh); + + static nd::array< double > D_e_buffer; + + uint32_t qoffset = 0; + foreach_geometry([&](auto geom){ + nd::view elements = domain.active_elements[geom]; + if (gdim == dimension(geom) && elements.size() > 0) { + nd::view connectivity = domain.mesh[geom]; + nd::view xi = domain.rule[geom].points; + nd::view weights = domain.rule[geom].weights; + + stack::array< uint32_t, 5 > qdata_shape{domain.num_qpts[geom], shape5D[1], shape5D[2], shape5D[3], shape5D[4]}; + nd::view geom_qdata{&q5D(qoffset, 0, 0, 0, 0), qdata_shape}; + + const Domain::AssemblyLUT & table = domain.get(geom, phi.family, phi.degree); + + foreach_constexpr< Family::H1, Family::HCURL >([&](auto family) { + if (family == phi.family) { + batched_integrate_diag( + output.data, + geom_qdata, psi, + output.offsets, domain.mesh.X, type, + connectivity, elements, + xi, weights, + table, D_e_buffer + ); + } + }); + + qoffset += domain.num_qpts[geom]; + } + }); + + return output.data; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template nd::array integrate_sparse_matrix_diagonal(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +} // namespace impl + +} // namespace refactor +#endif diff --git a/src/serac/numerics/refactor/integrate_residual.cpp b/src/serac/numerics/refactor/integrate_residual.cpp new file mode 100644 index 0000000000..685125c7ce --- /dev/null +++ b/src/serac/numerics/refactor/integrate_residual.cpp @@ -0,0 +1,152 @@ +#include "serac/numerics/refactor/integrate.hpp" + +#include "serac/numerics/refactor/common.hpp" + +namespace refactor { + +namespace impl { + +template < mfem::Geometry::Type geom, Family family, DerivedQuantity op > +void batched_integrate_residual(Residual & r, + const Field & X, + const DomainType type, + nd::view f_q, + const nd::view elements, + const nd::view xi, + const nd::view weights, + nd::array & element_residual_buffer) { + + uint32_t num_elements = elements.size(); + if (num_elements == 0) return; + + FiniteElement< geom, family > r_el{get_degree(r)}; + + using input_t = typename std::conditional< + op == DerivedQuantity::VALUE, + typename FiniteElement< geom, family >::source_type, + typename FiniteElement< geom, family >::flux_type + >::type; + + nd::view input_q(reinterpret_cast(&f_q[0]), {f_q.shape[0], f_q.shape[1]}); + + uint32_t qpts_per_element = impl::qpe(xi.shape[0]); + + uint32_t r_components = get_num_components(r); + uint32_t r_nodes_per_element = r_el.num_nodes(); + auto r_shape_fns = [&](){ + if constexpr(op == DerivedQuantity::VALUE) { + return r_el.evaluate_weighted_shape_functions(xi, weights); + } + + if constexpr(op == DerivedQuantity::DERIVATIVE && family == Family::HCURL) { + return r_el.evaluate_weighted_shape_function_curls(xi, weights); + } + + if constexpr(op == DerivedQuantity::DERIVATIVE && is_scalar_valued(family)) { + return r_el.evaluate_weighted_shape_function_gradients(xi, weights); + } + }(); + + stack::array element_residual_shape = {num_elements * r_nodes_per_element, r_components}; + + if (element_residual_buffer.sz < nd::product(element_residual_shape)) { + element_residual_buffer.resize(nd::product(element_residual_shape)); + } + + nd::view element_residuals(element_residual_buffer.data(), element_residual_shape); + + // for each element with this geometry + for (uint32_t i = 0; i < num_elements; i++) { + + nd::array r_ids({r_nodes_per_element}); + nd::array r_e({r_nodes_per_element}); + nd::array< double > r_scratch({r_el.batch_interpolation_scratch_space(xi)}); + + nd::array input_xi_q({qpts_per_element}); + for (uint32_t c = 0; c < r_components; c++) { + + for (uint32_t q = 0; q < qpts_per_element; q++) { + input_xi_q(q) = input_q(i*qpts_per_element+q, c); + } + + if constexpr (op == DerivedQuantity::VALUE) { + r_el.integrate_source(r_e, input_xi_q, r_shape_fns, r_scratch.data()); + } + + if constexpr (op == DerivedQuantity::DERIVATIVE) { + r_el.integrate_flux(r_e, input_xi_q, r_shape_fns, r_scratch.data()); + } + + //if constexpr (is_vector_valued(family)) { + // r_el.reorient(TransformationType::TransposePhysicalToParent, &connectivity(elements(i), 0), r_e.data()); + //} + + for (uint32_t j = 0; j < r_nodes_per_element; j++) { + element_residuals(i * r_nodes_per_element + j, c) = r_e(j); + } + + } + + } + +} + +template < DerivedQuantity op, uint32_t n > +void integrate_residual(Residual & r, BasisFunction phi, const nd::array & f_q, Domain & domain, const MeshQuadratureRule & qrule) { + + r = 0.0; + + uint32_t gdim = geometry_dimension(domain); + + stack::array input_dimensions{ + f_q.shape[0], + phi.space.components, + qshape(get_family(r), op, gdim) + }; + + GeometryInfo num_qpts = qrule.num_qpts(domain); + + SLIC_ASSERT_MSG(compatible_shapes(f_q.shape, input_dimensions), "incompatible array shapes"); + SLIC_ASSERT_MSG(input_dimensions[0] == total(num_qpts), "wrong number of quadrature points"); + + static nd::array< double > element_residual_buffer; + + nd::view f3D{f_q.data(), input_dimensions}; + uint32_t offset = 0; + foreach_geometry([&](auto geom){ + const std::vector & elements = domain.get(geom); + if (gdim == dimension(geom) && elements.size() > 0) { + nd::view xi = qrule[geom].points; + nd::view weights = qrule[geom].weights; + + nd::view integrand_geom = {&f3D(offset, 0, 0), {num_qpts[geom], f3D.shape[1], f3D.shape[2]}}; + + if (phi.space.family == Family::H1) { + batched_integrate_residual(r, integrand_geom, elements, xi, weights, element_residual_buffer); + } + + if (phi.space.family == Family::HCURL) { + batched_integrate_residual(r, integrand_geom, elements, xi, weights, element_residual_buffer); + } + } + + offset += num_qpts[geom]; + }); + +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +template void integrate_residual(Residual&, BasisFunction, const nd::array &, const Domain &, const DomainType); +template void integrate_residual(Residual&, BasisFunction, const nd::array &, const Domain &, const DomainType); +template void integrate_residual(Residual&, BasisFunction, const nd::array &, const Domain &, const DomainType); + +template void integrate_residual(Residual&, BasisFunction, const nd::array &, const Domain &, const DomainType); +template void integrate_residual(Residual&, BasisFunction, const nd::array &, const Domain &, const DomainType); +template void integrate_residual(Residual&, BasisFunction, const nd::array &, const Domain &, const DomainType); + +} // namespace impl + +} // namespace refactor diff --git a/src/serac/numerics/refactor/integrate_spmat.cpp b/src/serac/numerics/refactor/integrate_spmat.cpp new file mode 100644 index 0000000000..e5317a1755 --- /dev/null +++ b/src/serac/numerics/refactor/integrate_spmat.cpp @@ -0,0 +1,319 @@ +#if 0 +#include "common.hpp" + +namespace refactor { + +namespace impl { + +template < mfem::Geometry::Type geom, Family test_family, DerivedQuantity test_op, Family trial_family, DerivedQuantity trial_op> +void batched_integrate_spmat(nd::view values, + nd::view row_ptr, + nd::view col_ind, + nd::view qdata, + FunctionSpace trial_space, + FunctionSpace test_space, + GeometryInfo trial_offsets, + GeometryInfo test_offsets, + const Field & X, + const DomainType type, + nd::view connectivity, + const nd::view elements, + const nd::view xi, + const nd::view weights) { + + constexpr uint32_t gdim = dimension(geom); + constexpr uint32_t test_qshape = qshape(test_family, test_op, gdim); + constexpr uint32_t trial_qshape = qshape(trial_family, trial_op, gdim); + + using test_qtype = vec; + using trial_qtype = vec; + using mat_t = mat; + + using test_Atype = decltype(piola_transformation(mat{})); + using trial_Atype = decltype(weighted_piola_transformation(mat{})); + + FiniteElement< geom, Family::H1 > X_el{get_degree(X)}; + FiniteElement< geom, test_family > test_el{test_space.degree}; + FiniteElement< geom, trial_family > trial_el{trial_space.degree}; + + uint32_t num_elements = elements.size(); + uint32_t test_components = test_space.components; + uint32_t trial_components = trial_space.components; + uint32_t test_nodes_per_element = test_el.num_nodes(); + uint32_t trial_nodes_per_element = trial_el.num_nodes(); + uint32_t qpts_per_element = impl::qpe(xi.shape[0]); + + // precalculate test functions for the provided quadrature rule + auto psi_wt = [&](){ + if constexpr(trial_op == DerivedQuantity::VALUE) { + return trial_el.evaluate_weighted_shape_functions(xi, weights); + } + + if constexpr(trial_op == DerivedQuantity::DERIVATIVE && trial_family == Family::HCURL) { + return trial_el.evaluate_weighted_shape_function_curls(xi, weights); + } + + if constexpr(trial_op == DerivedQuantity::DERIVATIVE && is_scalar_valued(trial_family)) { + return trial_el.evaluate_weighted_shape_function_gradients(xi, weights); + } + }(); + + uint32_t X_components = get_num_components(X); + uint32_t X_nodes_per_element = X_el.num_nodes(); + + auto X_shape_fn_grads = X_el.evaluate_shape_function_gradients(xi); + + nd::array testA_q; + nd::array trialA_q; + nd::array, 2> dX_dxi_q; + nd::array X_ids; + nd::array X_e; + nd::array X_scratch; + + // When do we need to calculate dX/dxi? + // + // ❌ : don't need to ✅ : need to + // +---------------------+------+-------+------+----+ + // | | H1 | Hcurl | Hdiv | DG | + // +---------------------+------+-------+------+----+ + // | isoparametric value | ❌ | ❌ | ❌ | ❌ | + // +---------------------+------+-------+------+----+ + // | isoparametric deriv | ❌ | ❌ | ❌ | ❌ | + // +---------------------+------+-------+------+----+ + // | spatial value | ✅ | ✅ | ✅ | ✅ | + // +---------------------+------+-------+------+----+ + // | spatial deriv | ✅ | ✅ | ✅ | ✅ | + // +---------------------+------+-------+------+----+ + const bool need_to_compute_dX_dxi = (type == DomainType::SPATIAL); + + if (need_to_compute_dX_dxi) { + testA_q.resize({qpts_per_element}); + trialA_q.resize({qpts_per_element}); + dX_dxi_q.resize({X_components, qpts_per_element}); + X_ids.resize(X_nodes_per_element); + X_e.resize(X_nodes_per_element); + X_scratch.resize({X_el.batch_interpolation_scratch_space(xi)}); + } + + // for each element of this mfem::Geometry::Type in the domain + for (uint32_t e = 0; e < num_elements; e++) { + + if (need_to_compute_dX_dxi) { + + // figure out which nodal values belong to this element + X_el.indices(X.offsets, connectivity(elements(e)).data(), X_ids.data()); + + for (uint32_t c = 0; c < X_components; c++) { + for (uint32_t j = 0; j < X_nodes_per_element; j++) { + X_e(j) = X.data(X_ids(j), c); + } + X_el.gradient(dX_dxi_q(c), X_e, X_shape_fn_grads, X_scratch.data()); + } + + for (uint32_t q = 0; q < qpts_per_element; q++) { + mat dX_dxi; + for (uint32_t c = 0; c < gdim; c++) { + dX_dxi[c] = dX_dxi_q(c, q); + } + testA_q[q] = piola_transformation(dX_dxi); + trialA_q[q] = weighted_piola_transformation(dX_dxi); + } + } + + nd::array< double > trial_scratch({trial_el.batch_interpolation_scratch_space(xi)}); + + nd::array< trial_qtype > hat_f({qpts_per_element}); + + nd::array test_ids({test_nodes_per_element}); + test_el.indices(test_offsets, connectivity(elements(e)).data(), test_ids.data()); + + nd::array trial_ids({trial_nodes_per_element}); + trial_el.indices(trial_offsets, connectivity(elements(e)).data(), trial_ids.data()); + + nd::array< int8_t > transformation({test_nodes_per_element}); + if constexpr (is_vector_valued(test_family)) { + test_el.reorient(TransformationType::TransposePhysicalToParent, &connectivity(elements(e), 0), transformation.data()); + } + + uint32_t qoffset = e * qpts_per_element; + + for (uint32_t i = 0; i < test_components; i++) { + for (uint32_t j = 0; j < trial_components; j++) { + for (uint32_t I = 0; I < test_nodes_per_element; I++) { + uint32_t row_id = test_ids[I] * test_components + i; + + for (uint32_t q = 0; q < qpts_per_element; q++) { + uint32_t qid = qoffset + q; + + auto xi_q = quadrature_point(q, xi); + + mat_t C{}; + for (uint32_t k = 0; k < test_qshape; k++) { + for (uint32_t m = 0; m < trial_qshape; m++) { + C(k, m) = qdata(qid, i, k, j, m); + } + } + + test_qtype phi_I; + + if constexpr (is_scalar_valued(test_family) && test_op == DerivedQuantity::VALUE) { + phi_I = test_el.shape_function(xi_q, I); + } + + if constexpr (is_scalar_valued(test_family) && test_op == DerivedQuantity::DERIVATIVE) { + phi_I = test_el.shape_function_gradient(xi_q, I); + } + + if constexpr (test_family == Family::HCURL && test_op == DerivedQuantity::VALUE) { + phi_I = test_el.reoriented_shape_function(xi_q, I, transformation[I]); + } + + if constexpr (test_family == Family::HCURL && test_op == DerivedQuantity::DERIVATIVE) { + phi_I = test_el.reoriented_shape_function_curl(xi_q, I, transformation[I]); + } + + if (need_to_compute_dX_dxi) { + phi_I = serac::dot(phi_I, testA_q[q]); + } + + hat_f[q] = serac::dot(phi_I, C); + + if (need_to_compute_dX_dxi) { + hat_f[q] = serac::dot(trialA_q[q], hat_f[q]); + } + + } + + nd::array r_e({trial_el.num_nodes()}); + + if constexpr (trial_op == DerivedQuantity::VALUE) { + trial_el.integrate_source(r_e, hat_f, psi_wt, trial_scratch.data()); + } + + if constexpr (trial_op == DerivedQuantity::DERIVATIVE) { + trial_el.integrate_flux(r_e, hat_f, psi_wt, trial_scratch.data()); + } + + if constexpr (is_vector_valued(trial_family)) { + trial_el.reorient(TransformationType::TransposePhysicalToParent, &connectivity(elements(e), 0), r_e.data()); + } + + int row_start = row_ptr[row_id]; + int row_end = row_ptr[row_id+1]; + for (uint32_t J = 0; J < trial_nodes_per_element; J++) { + int col_id = static_cast(trial_ids[J] * trial_components + j); + + // find the position of the nonzero entry of this row with the right column + int position = std::lower_bound(&col_ind[row_start], &col_ind[row_end], col_id) - &col_ind[0]; + + values[position] += r_e(J); + } + } + } + } + + } + +} + +template +std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction test, const nd::array & qdata, BasisFunction trial, const Domain &domain, const DomainType type) { + + return [&, type, test, trial](refactor::sparse_matrix & A) { + + auto phi = test.space; + auto psi = trial.space; + + uint32_t test_components = phi.components; + uint32_t trial_components = psi.components; + uint32_t sdim = spatial_dimension(domain); + uint32_t gdim = geometry_dimension(domain); + + stack::array shape5D = { + qdata.shape[0], + phi.components, qshape(phi.family, test_op, gdim), + psi.components, qshape(psi.family, trial_op, gdim) + }; + + SLIC_ASSERT_MSG(compatible_shapes(qdata.shape, shape5D), "incompatible array shapes"); + + nd::view q5D{qdata.data(), shape5D}; + + GeometryInfo counts = domain.mesh.geometry_counts(); + GeometryInfo test_offsets = scan(interior_nodes_per_geom(phi) * counts); + GeometryInfo trial_offsets = scan(interior_nodes_per_geom(psi) * counts); + auto nrows = total(interior_dofs_per_geom(phi) * counts); + auto ncols = total(interior_dofs_per_geom(psi) * counts); + + if (A.nnz == 0) { + A = blank_sparse_matrix(test, trial, domain); + } else { + zero(A.values); + } + + uint32_t qoffset = 0; + foreach_geometry([&](auto geom){ + nd::view elements = domain.active_elements[geom]; + if (gdim == dimension(geom) && elements.size() > 0) { + nd::view connectivity = domain.mesh[geom]; + nd::view xi = domain.rule[geom].points; + nd::view weights = domain.rule[geom].weights; + + if constexpr (geom != mfem::Geometry::POINT) { + stack::array< uint32_t, 5 > qdata_shape{domain.num_qpts[geom], shape5D[1], shape5D[2], shape5D[3], shape5D[4]}; + nd::view geom_qdata{&q5D(qoffset, 0, 0, 0, 0), qdata_shape}; + + foreach_constexpr< Family::H1, Family::HCURL >([&](auto test_family) { + foreach_constexpr< Family::H1, Family::HCURL >([&](auto trial_family) { + if (test_family == phi.family && trial_family == psi.family) { + batched_integrate_spmat( + A.values, A.row_ptr, A.col_ind, + geom_qdata, psi, phi, + trial_offsets, test_offsets, domain.mesh.X, type, + connectivity, elements, + xi, weights + ); + } + }); + }); + + qoffset += domain.num_qpts[geom]; + } + } + }); + + return A; + + }; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); +template std::function< void(refactor::sparse_matrix&) > integrate_sparse_matrix(BasisFunction, const nd::array &, BasisFunction, const Domain &, const DomainType); + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// + +} // namespace impl + +} // namespace refactor +#endif diff --git a/src/serac/numerics/refactor/interpolation.cpp b/src/serac/numerics/refactor/interpolation.cpp new file mode 100644 index 0000000000..c1f5fdf605 --- /dev/null +++ b/src/serac/numerics/refactor/interpolation.cpp @@ -0,0 +1,599 @@ +#include + +namespace refactor { + +void GaussLegendreNodes(uint32_t n, double * output) { + + // clang-format off + switch (n) { + case 1: + output[0] = 0.5; + break; + case 2: + output[0] = 0.2113248654051871; + output[1] = 0.7886751345948129; + break; + case 3: + output[0] = 0.1127016653792583; + output[1] = 0.500000000000000; + output[2] = 0.887298334620742; + break; + case 4: + output[0] = 0.0694318442029737; + output[1] = 0.330009478207572 ; + output[2] = 0.669990521792428 ; + output[3] = 0.930568155797026 ; + break; + case 5: + output[0] = 0.04691007703066800; + output[1] = 0.2307653449471585 ; + output[2] = 0.5000000000000000 ; + output[3] = 0.7692346550528415 ; + output[4] = 0.9530899229693320 ; + break; + case 6: + output[0] = 0.03376524289842399; + output[1] = 0.1693953067668677 ; + output[2] = 0.3806904069584015 ; + output[3] = 0.6193095930415985 ; + output[4] = 0.8306046932331323 ; + output[5] = 0.9662347571015760 ; + break; + } + // clang-format on + +} + +void GaussLegendreInterpolation(double x, uint32_t n, double * output) { + + if (n == 1) { + output[0] = 1; + } + + if (n == 2) { + output[0] = 1.3660254037844386467637231708 - 1.732050807568877293527446342*x; + output[1] = -0.3660254037844386467637231708 + 1.7320508075688772935274463415*x; + } + + if (n == 3) { + output[0] = 1.4788305577012361475298776 + x*(-4.624327782069138961726422 + 3.3333333333333333333333333*x); + output[1] = -0.666666666666666666666666667 + (6.66666666666666666666666667 - 6.666666666666666666666666667*x)*x; + output[2] = 0.1878361089654305191367891 + x*(-2.0423388845975277049402449 + 3.3333333333333333333333333*x); + } + + if (n == 4) { + output[0] = 1.526788125457266786984328 + x*(-8.54602360787219876597302 + (14.32585835417188815296662 - 7.42054006803894610520064*x)*x); + output[1] = -0.8136324494869272605619 + x*(13.8071669256895770661587 + x*(-31.3882223634460602120582 + 18.7954494075550608112617*x)); + output[2] = 0.400761520311650404800281777 + x*(-7.41707042146263907582738061 + (24.9981258592191222217269164 - 18.79544940755506081126171563*x)*x); + output[3] = -0.11391719628198993122271197 + x*(2.1559271036452607756417044 + x*(-7.935761849944950162635307 + 7.420540068038946105200642*x)); + } + + if (n == 5) { + output[0] = 1.551408049094313012813028 + x*(-13.47028450119487106120462 + x*(38.6444990553441957009803 + x*(-44.9889850558789977671881 + 18.33972111443117301508323*x))); + output[1] = -0.8931583920000717373262 + x*(22.924333555723729737768 + x*(-88.22281082816288605026 + (117.8634151266470135556 - 51.939721114431173015083*x)*x)); + output[2] = 0.5333333333333333333333 + x*(-14.933333333333333333333 + x*(82.13333333333333333333 + x*(-134.4 + 67.2*x))); + output[3] = -0.26794165222338750930410993 + x*(7.6899271783856937562943889 + x*(-46.270892134808883473969833 + (89.895469331077678504736602 - 51.9397211144311730150832251*x)*x)); + output[4] = 0.07635866179581290048392539 + x*(-2.210642899581219099524808 + x*(13.71587057429424048991553 + x*(-28.36989940184569429314485 + 18.33972111443117301508323*x))); + } + + if (n == 6) { + output[0] = 1.565673200151071933093717 + x*(-19.38889969575614186464859 + x*(83.3561716652066047719407 + x*(-161.6334485633571811708389 + (144.8933610434784341266087 - 48.8475703740520537090491*x)*x))); + output[1] = -0.94046284317634892902 + x*(33.94755689005745838881 + x*(-194.5900409203250530156 + x*(431.2442105751191477314 + x*(-416.6718961318097255735 + 147.20243244417318935282*x)))); + output[2] = 0.616930055430488708617 + x*(-24.29050650593736015819 + x*(195.3041651669510511719 + x*(-523.416260790836176187 + (568.4164873451100029584 - 217.0100429728326202484*x)*x))); + output[3] = -0.37922770211461375461734918 + x*(15.315224028266875783526055 + x*(-134.54612286322366212220967 + x*(419.85074113872236683695564 + x*(-516.63372751905309828340431 + 217.010042972832620248366597*x)))); + output[4] = 0.1918000140386679548202 + x*(-7.82468446839184002159 + x*(71.1355384559059302654 + x*(-236.5809504896121389654 + (319.3402660890562211905 - 147.2024324441731893528*x)*x))); + output[5] = -0.05471272432926591289350948 + x*(2.241309751761007872094777 + x*(-20.65971150451487107141517 + x*(70.5357081299639817548955 + x*(-99.344490826781834418637 + 48.84757037405205370904914*x)))); + } + +} + +void GaussLegendreInterpolationDerivative01(double x, uint32_t n, double * output) { + + if (n == 1) { + output[0] = 0.0; + } + + if (n == 2) { + output[0] = -1.7320508075688772935274463415; + output[1] = 1.7320508075688772935274463415; + } + + if (n == 3) { + output[0] = -4.6243277820691389617264218 + 6.6666666666666666666666667*x; + output[1] = 6.66666666666666666666666667 - 13.3333333333333333333333333*x; + output[2] = -2.04233888459752770494024487 + 6.6666666666666666666666667*x; + } + + if (n == 4) { + output[0] = -8.546023607872198765973 + (28.6517167083437763059332 - 22.2616202041168383156019*x)*x; + output[1] = 13.80716692568958 + x*(-62.7764447268921 + 56.3863482226652*x); + output[2] = -7.417070421462639075827381 + (49.99625171843824444345383 - 56.38634822266518243378515*x)*x; + output[3] = 2.155927103645260775641704 + x*(-15.87152369988990032527061 + 22.26162020411683831560193*x); + } + + if (n == 5) { + output[0] = -13.4702845011948710612046 + x*(77.288998110688391401961 + x*(-134.966955167636993301564 + 73.358884457724692060333*x)); + output[1] = 22.92433355572373 + x*(-176.4456216563258 + (353.590245379941 - 207.7588844577247*x)*x); + output[2] = -14.93333333333333 + x*(164.2666666666667 + x*(-403.2 + 268.8*x)); + output[3] = 7.689927178385693756294389 + x*(-92.54178426961776694793967 + (269.6864079932330355142098 - 207.7588844577246920603329*x)*x); + output[4] = -2.21064289958121909952481 + x*(27.4317411485884809798311 + x*(-85.1096982055370828794345 + 73.3588844577246920603329*x)); + } + + if (n == 6) { + output[0] = -19.3888996957561418646486 + x*(166.712343330413209543881 + x*(-484.90034569007154351252 + (579.57344417391373650643 - 244.23785187026026854525*x)*x)); + output[1] = 33.94755689005746 + x*(-389.18008184065 + x*(1293.732631725357 + x*(-1666.687584527239 + 736.012162220866*x))); + output[2] = -24.29050650593736 + x*(390.6083303339021 + x*(-1570.248782372509 + (2273.66594938044 - 1085.050214864163*x)*x)); + output[3] = 15.31522402826687578352605 + x*(-269.0922457264473242444193 + x*(1259.552223416167100510867 + x*(-2066.534910076212393133617 + 1085.050214864163101241833*x))); + output[4] = -7.82468446839184 + x*(142.2710769118119 + x*(-709.742851468836 + (1277.361064356225 - 736.012162220866*x)*x)); + output[5] = 2.24130975176100787209478 + x*(-41.3194230090297421428303 + x*(211.607124389891945264686 + x*(-397.377963307127337674548 + 244.237851870260268545246*x))); + } + +} + +void GaussLobattoNodes(uint32_t n, double * output) { + if (n == 1) { + output[0] = 0.5; + return; + } + if (n == 2) { + output[0] = 0.0; + output[1] = 1.0; + return; + } + if (n == 3) { + output[0] = 0.0; + output[1] = 0.5; + output[2] = 1.0; + return; + } + if (n == 4) { + output[0] = 0.0; + output[1] = 0.2763932022500210; + output[2] = 0.7236067977499790; + output[3] = 1.0; + return; + } +} + +void GaussLobattoInterpolation(double x, uint32_t n, double * output) { + if (n == 1) { + output[0] = 1.0; + return; + } + if (n == 2) { + output[0] = 1.0 - x; + output[1] = x; + return; + } + if (n == 3) { + output[0] = (-1.0 + x) * (-1.0 + 2.0 * x); + output[1] = -4.0 * (-1.0 + x) * x; + output[2] = x * (-1.0 + 2.0 * x); + return; + } + if (n == 4) { + constexpr double sqrt5 = 2.23606797749978981; + output[0] = -(-1.0 + x) * (1.0 + 5.0 * (-1.0 + x) * x); + output[1] = -0.5 * sqrt5 * (5.0 + sqrt5 - 10.0 * x) * (-1.0 + x) * x; + output[2] = -0.5 * sqrt5 * (-1.0 + x) * x * (-5.0 + sqrt5 + 10.0 * x); + output[3] = x * (1.0 + 5.0 * (-1.0 + x) * x); + return; + } + + std::cout << "error: invalid polynomial order in GaussLobattoInterpolation" << std::endl; +} + +void GaussLobattoInterpolationDerivative(double x, uint32_t n, double * output) { + if (n == 1) { + output[0] = 0.0; + return; + } + if (n == 2) { + output[0] = -1.0; + output[1] = 1.0; + return; + } + if (n == 3) { + output[0] = -3.0 + 4.0 * x; + output[1] = 4.0 - 8.0 * x; + output[2] = -1.0 + 4.0 * x; + return; + } + if (n == 4) { + constexpr double sqrt5 = 2.23606797749978981; + output[0] = -6.0 + 5.0 * (4.0 - 3.0 * x) * x; + output[1] = 2.5 * (1.0 + sqrt5 + 2.0 * x * (-1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * x)); + output[2] = -2.5 * (-1.0 + sqrt5 + 2.0 * x * (1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * x)); + output[3] = 1.0 + 5.0 * x * (-2.0 + 3.0 * x); + return; + } + + std::cout << "error: invalid polynomial order in GaussLobattoInterpolationDerivative" << std::endl; +} + +#if 1 +constexpr double GaussLobattoInterpolation(double x, uint32_t n, uint32_t i) { + if (n == 1) { return 1.0; } + if (n == 2) { return (i == 0) ? 1.0 - x : x; } + if (n == 3) { + if (i == 0) return (-1.0 + x) * (-1.0 + 2.0 * x); + if (i == 1) return -4.0 * (-1.0 + x) * x; + if (i == 2) return x * (-1.0 + 2.0 * x); + } + if (n == 4) { + constexpr double sqrt5 = 2.23606797749978981; + if (i == 0) return -(-1.0 + x) * (1.0 + 5.0 * (-1.0 + x) * x); + if (i == 1) return -0.5 * sqrt5 * (5.0 + sqrt5 - 10.0 * x) * (-1.0 + x) * x; + if (i == 2) return -0.5 * sqrt5 * (-1.0 + x) * x * (-5.0 + sqrt5 + 10.0 * x); + if (i == 3) return x * (1.0 + 5.0 * (-1.0 + x) * x); + } + return -1.0; +} + +constexpr double GaussLobattoInterpolationDerivative(double x, uint32_t n, uint32_t i) { + if (n == 1) { return 0.0; } + if (n == 2) { return (i == 0) ? -1.0 : 1.0; } + if (n == 3) { + if (i == 0) return -3.0 + 4.0 * x; + if (i == 1) return 4.0 - 8.0 * x; + if (i == 2) return -1.0 + 4.0 * x; + } + if (n == 4) { + constexpr double sqrt5 = 2.23606797749978981; + if (i == 0) return -6.0 + 5.0 * (4.0 - 3.0 * x) * x; + if (i == 1) return 2.5 * (1.0 + sqrt5 + 2.0 * x * (-1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * x)); + if (i == 2) return -2.5 * (-1.0 + sqrt5 + 2.0 * x * (1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * x)); + if (i == 3) return 1.0 + 5.0 * x * (-2.0 + 3.0 * x); + } + return -1.0; +} +#endif + +void GaussLobattoInterpolationTriangle(const double * xi, uint32_t p, double * output) { + if (p == 0) { + output[0] = 1.0; + return; + } + if (p == 1) { + output[0] = 1.0 - xi[0] - xi[1]; + output[1] = xi[0]; + output[2] = xi[1]; + return; + } + if (p == 2) { + output[0] = (-1+xi[0]+xi[1])*(-1+2*xi[0]+2*xi[1]); + output[1] = -4*xi[0]*(-1+xi[0]+xi[1]); + output[2] = xi[0]*(-1+2*xi[0]); + output[3] = -4*xi[1]*(-1+xi[0]+xi[1]); + output[4] = 4*xi[0]*xi[1]; + output[5] = xi[1]*(-1+2*xi[1]); + return; + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + output[0] = -((-1+xi[0]+xi[1])*(1+5*xi[0]*xi[0]+5*(-1+xi[1])*xi[1]+xi[0]*(-5+11*xi[1]))); + output[1] = (5*xi[0]*(-1+xi[0]+xi[1])*(-1-sqrt5+2*sqrt5*xi[0]+(3+sqrt5)*xi[1]))/2.0; + output[2] = (-5*xi[0]*(-1+xi[0]+xi[1])*(1-sqrt5+2*sqrt5*xi[0]+(-3+sqrt5)*xi[1]))/2.0; + output[3] = xi[0]*(1+5*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]-xi[0]*(5+xi[1])); + output[4] = (5*xi[1]*(-1+xi[0]+xi[1])*(-1-sqrt5+(3+sqrt5)*xi[0]+2*sqrt5*xi[1]))/2.0; + output[5] = -27*xi[0]*xi[1]*(-1+xi[0]+xi[1]); + output[6] = (5*xi[0]*xi[1]*(-2+(3+sqrt5)*xi[0]-(-3+sqrt5)*xi[1]))/2.; + output[7] = (5*xi[1]*(-1+xi[0]+xi[1])*(5-3*sqrt5+2*(-5+2*sqrt5)*xi[0]+5*(-1+sqrt5)*xi[1]))/(-5+sqrt5); + output[8] = (-5*xi[0]*xi[1]*(2+(-3+sqrt5)*xi[0]-(3+sqrt5)*xi[1]))/2.; + output[9] = xi[1]*(1+xi[0]-xi[0]*xi[0]-xi[0]*xi[1]+5*(-1+xi[1])*xi[1]); + return; + } +} + +void GaussLobattoInterpolationDerivativeTriangle(const double * xi, uint32_t p, double * output) { + if (p == 0) { + output[0] = 0.0; + output[1] = 0.0; + return; + } + if (p == 1) { + output[0] = -1; + output[1] = -1; + output[2] = 1; + output[3] = 0; + output[4] = 0; + output[5] = 1; + return; + } + if (p == 2) { + output[ 0] = -3+4*xi[0]+4*xi[1]; + output[ 1] = -3+4*xi[0]+4*xi[1]; + output[ 2] = -4*(-1+2*xi[0]+xi[1]); + output[ 3] = -4*xi[0]; + output[ 4] = -1+4*xi[0]; + output[ 5] = 0; + output[ 6] = -4*xi[1]; + output[ 7] = -4*(-1+xi[0]+2*xi[1]); + output[ 8] = 4*xi[1]; + output[ 9] = 4*xi[0]; + output[10] = 0; + output[11] = -1+4*xi[1]; + return; + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + output[ 0] = -6-15*xi[0]*xi[0]+4*xi[0]*(5-8*xi[1])+(21-16*xi[1])*xi[1]; + output[ 1] = -6-16*xi[0]*xi[0]+xi[0]*(21-32*xi[1])+5*(4-3*xi[1])*xi[1]; + output[ 2] = (5*(6*sqrt5*xi[0]*xi[0]+xi[0]*(-2-6*sqrt5+6*(1+sqrt5)*xi[1])+(-1+xi[1])*(-1-sqrt5+(3+sqrt5)*xi[1])))/2.; + output[ 3] = (5*xi[0]*(-2*(2+sqrt5)+3*(1+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]))/2.; + output[ 4] = (-5*(6*sqrt5*xi[0]*xi[0]+(-1+xi[1])*(1-sqrt5+(-3+sqrt5)*xi[1])+xi[0]*(2-6*sqrt5+6*(-1+sqrt5)*xi[1])))/2.; + output[ 5] = (-5*xi[0]*(4-2*sqrt5+3*(-1+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]))/2.; + output[ 6] = 1+15*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]-2*xi[0]*(5+xi[1]); + output[ 7] = -(xi[0]*(-1+xi[0]+2*xi[1])); + output[ 8] = (5*xi[1]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+3*(1+sqrt5)*xi[1]))/2.; + output[ 9] = (5*(1+sqrt5-2*(2+sqrt5)*xi[0]+(3+sqrt5)*xi[0]*xi[0]+6*(1+sqrt5)*xi[0]*xi[1]+2*xi[1]*(-1-3*sqrt5+3*sqrt5*xi[1])))/2.; + output[10] = -27*xi[1]*(-1+2*xi[0]+xi[1]); + output[11] = -27*xi[0]*(-1+xi[0]+2*xi[1]); + output[12] = (-5*xi[1]*(2-2*(3+sqrt5)*xi[0]+(-3+sqrt5)*xi[1]))/2.; + output[13] = (5*xi[0]*(-2+(3+sqrt5)*xi[0]-2*(-3+sqrt5)*xi[1]))/2.; + output[14] = (-5*xi[1]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[1]))/2.; + output[15] = (-5*(-1+sqrt5+(-3+sqrt5)*xi[0]*xi[0]+2*xi[1]*(1-3*sqrt5+3*sqrt5*xi[1])+xi[0]*(4-2*sqrt5+6*(-1+sqrt5)*xi[1])))/2.; + output[16] = (5*xi[1]*(-2-2*(-3+sqrt5)*xi[0]+(3+sqrt5)*xi[1]))/2.; + output[17] = (-5*xi[0]*(2+(-3+sqrt5)*xi[0]-2*(3+sqrt5)*xi[1]))/2.; + output[18] = -(xi[1]*(-1+2*xi[0]+xi[1])); + output[19] = 1+xi[0]-xi[0]*xi[0]-2*(5+xi[0])*xi[1]+15*xi[1]*xi[1]; + return; + } +} + +void GaussLobattoInterpolationQuadrilateral(const double * xi, uint32_t n, double * output) { + double * N[2] = {new double[n], new double[n]}; + + GaussLobattoInterpolation(xi[0], n, N[0]); + GaussLobattoInterpolation(xi[1], n, N[1]); + + for (uint32_t j = 0; j < n; j++) { + for (uint32_t i = 0; i < n; i++) { + output[j * n + i] = N[0][i] * N[0][j]; + } + } + + delete N[0]; + delete N[1]; +} + +void GaussLobattoInterpolationDerivativeQuadrilateral(const double * xi, uint32_t n, double * output) { + double * N[2] = {new double[n], new double[n]}; + double * dN[2] = {new double[n], new double[n]}; + + GaussLobattoInterpolation(xi[0], n, N[0]); + GaussLobattoInterpolation(xi[1], n, N[1]); + + GaussLobattoInterpolation(xi[0], n, dN[0]); + GaussLobattoInterpolation(xi[1], n, dN[1]); + + for (uint32_t j = 0; j < n; j++) { + for (uint32_t i = 0; i < n; i++) { + output[2 * (j * n + i) + 0] = dN[0][i] * N[0][j]; + output[2 * (j * n + i) + 1] = N[0][i] * dN[0][j]; + } + } + + delete N[0]; + delete N[1]; + delete dN[0]; + delete dN[1]; +} + +void GaussLobattoInterpolationTetrahedron(const double * xi, uint32_t p, double * output) { + if (p == 0) { + output[0] = 1.0; + return; + } + if (p == 1) { + output[0] = 1-xi[0]-xi[1]-xi[2]; + output[1] = xi[0]; + output[2] = xi[1]; + output[3] = xi[2]; + return; + } + if (p == 2) { + output[0] = (-1+xi[0]+xi[1]+xi[2])*(-1+2*xi[0]+2*xi[1]+2*xi[2]); + output[1] = -4*xi[0]*(-1+xi[0]+xi[1]+xi[2]); + output[2] = xi[0]*(-1+2*xi[0]); + output[3] = -4*xi[1]*(-1+xi[0]+xi[1]+xi[2]); + output[4] = 4*xi[0]*xi[1]; + output[5] = xi[1]*(-1+2*xi[1]); + output[6] = -4*xi[2]*(-1+xi[0]+xi[1]+xi[2]); + output[7] = 4*xi[0]*xi[2]; + output[8] = 4*xi[1]*xi[2]; + output[9] = xi[2]*(-1+2*xi[2]); + return; + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + output[ 0] = -((-1+xi[0]+xi[1]+xi[2])*(1+5*xi[0]*xi[0]+5*xi[1]*xi[1]+5*(-1+xi[2])*xi[2]+xi[1]*(-5+11*xi[2])+xi[0]*(-5+11*xi[1]+11*xi[2]))); + output[ 1] = (5*xi[0]*(-1+xi[0]+xi[1]+xi[2])*(-1-sqrt5+2*sqrt5*xi[0]+(3+sqrt5)*xi[1]+(3+sqrt5)*xi[2]))/2.; + output[ 2] = (-5*xi[0]*(-1+xi[0]+xi[1]+xi[2])*(1-sqrt5+2*sqrt5*xi[0]+(-3+sqrt5)*xi[1]+(-3+sqrt5)*xi[2]))/2.; + output[ 3] = xi[0]*(1+5*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]+xi[2]-xi[1]*xi[2]-xi[2]*xi[2]-xi[0]*(5+xi[1]+xi[2])); + output[ 4] = (5*xi[1]*(-1+xi[0]+xi[1]+xi[2])*(-1-sqrt5+(3+sqrt5)*xi[0]+2*sqrt5*xi[1]+(3+sqrt5)*xi[2]))/2.; + output[ 5] = -27*xi[0]*xi[1]*(-1+xi[0]+xi[1]+xi[2]); + output[ 6] = (5*xi[0]*xi[1]*(-2+(3+sqrt5)*xi[0]-(-3+sqrt5)*xi[1]))/2.; + output[ 7] = (-5*xi[1]*(-1+xi[0]+xi[1]+xi[2])*(1-sqrt5+(-3+sqrt5)*xi[0]+2*sqrt5*xi[1]+(-3+sqrt5)*xi[2]))/2.; + output[ 8] = (-5*xi[0]*xi[1]*(2+(-3+sqrt5)*xi[0]-(3+sqrt5)*xi[1]))/2.; + output[ 9] = xi[1]*(1-xi[0]*xi[0]+5*xi[1]*xi[1]+xi[2]-xi[2]*xi[2]-xi[1]*(5+xi[2])-xi[0]*(-1+xi[1]+xi[2])); + output[10] = (5*xi[2]*(-1+xi[0]+xi[1]+xi[2])*(-439204-196418*sqrt5+(710647+317811*sqrt5)*xi[0]+(710647+317811*sqrt5)*xi[1]+606965*xi[2]+271443*sqrt5*xi[2]))/(271443+121393*sqrt5); + output[11] = -27*xi[0]*xi[2]*(-1+xi[0]+xi[1]+xi[2]); + output[12] = (5*xi[0]*xi[2]*(-5-3*sqrt5+(15+7*sqrt5)*xi[0]+2*sqrt5*xi[2]))/(5+3*sqrt5); + output[13] = -27*xi[1]*xi[2]*(-1+xi[0]+xi[1]+xi[2]); + output[14] = 27*xi[0]*xi[1]*xi[2]; + output[15] = (5*xi[1]*xi[2]*(-5-3*sqrt5+(15+7*sqrt5)*xi[1]+2*sqrt5*xi[2]))/(5+3*sqrt5); + output[16] = (5*xi[2]*(-1+xi[0]+xi[1]+xi[2])*(88555+39603*sqrt5+(54730+24476*sqrt5)*xi[0]+(54730+24476*sqrt5)*xi[1]-5*(64079+28657*sqrt5)*xi[2]))/(143285+64079*sqrt5); + output[17] = (-5*xi[0]*xi[2]*(2+(-3+sqrt5)*xi[0]-(3+sqrt5)*xi[2]))/2.; + output[18] = (-5*xi[1]*xi[2]*(2+(-3+sqrt5)*xi[1]-(3+sqrt5)*xi[2]))/2.; + output[19] = -(xi[2]*(-1+xi[0]*xi[0]+xi[1]*xi[1]+xi[1]*(-1+xi[2])-5*(-1+xi[2])*xi[2]+xi[0]*(-1+xi[1]+xi[2]))); + return; + } +} + +void GaussLobattoInterpolationDerivativeTetrahedron(const double * xi, uint32_t p, double * output) { + if (p == 0) { + output[0] = 0.0; + output[1] = 0.0; + output[2] = 0.0; + return; + } + if (p == 1) { + output[ 0] = -1; + output[ 1] = -1; + output[ 2] = -1; + output[ 3] = 1; + output[ 4] = 0; + output[ 5] = 0; + output[ 6] = 0; + output[ 7] = 1; + output[ 8] = 0; + output[ 9] = 0; + output[10] = 0; + output[11] = 1; + return; + } + if (p == 2) { + output[ 0] = -3+4*xi[0]+4*xi[1]+4*xi[2]; + output[ 1] = -3+4*xi[0]+4*xi[1]+4*xi[2]; + output[ 2] = -3+4*xi[0]+4*xi[1]+4*xi[2]; + output[ 3] = -4*(-1+2*xi[0]+xi[1]+xi[2]); + output[ 4] = -4*xi[0]; + output[ 5] = -4*xi[0]; + output[ 6] = -1+4*xi[0]; + output[ 7] = 0; + output[ 8] = 0; + output[ 9] = -4*xi[1]; + output[10] = -4*(-1+xi[0]+2*xi[1]+xi[2]); + output[11] = -4*xi[1]; + output[12] = 4*xi[1]; + output[13] = 4*xi[0]; + output[14] = 0; + output[15] = 0; + output[16] = -1+4*xi[1]; + output[17] = 0; + output[18] = -4*xi[2]; + output[19] = -4*xi[2]; + output[20] = -4*(-1+xi[0]+xi[1]+2*xi[2]); + output[21] = 4*xi[2]; + output[22] = 0; + output[23] = 4*xi[0]; + output[24] = 0; + output[25] = 4*xi[2]; + output[26] = 4*xi[1]; + output[27] = 0; + output[28] = 0; + output[29] = -1+4*xi[2]; + return; + } + if (p == 3) { + double sqrt5 = 2.23606797749978981; + output[ 0] = -6-15*xi[0]*xi[0]-16*xi[1]*xi[1]+xi[1]*(21-33*xi[2])+(21-16*xi[2])*xi[2]-4*xi[0]*(-5+8*xi[1]+8*xi[2]); + output[ 1] = -6-16*xi[0]*xi[0]+20*xi[1]+xi[0]*(21-32*xi[1]-33*xi[2])+21*xi[2]-(3*xi[1]+4*xi[2])*(5*xi[1]+4*xi[2]); + output[ 2] = -6-16*xi[0]*xi[0]+21*xi[1]+xi[0]*(21-33*xi[1]-32*xi[2])+20*xi[2]-(4*xi[1]+3*xi[2])*(4*xi[1]+5*xi[2]); + output[ 3] = (5*(6*sqrt5*xi[0]*xi[0]+xi[0]*(-2-6*sqrt5+6*(1+sqrt5)*xi[1]+6*(1+sqrt5)*xi[2])+(-1+xi[1]+xi[2])*(-1-sqrt5+(3+sqrt5)*xi[1]+(3+sqrt5)*xi[2])))/2.; + output[ 4] = (5*xi[0]*(-4-2*sqrt5+3*(1+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2.; + output[ 5] = (5*xi[0]*(-4-2*sqrt5+3*(1+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2.; + output[ 6] = -15*sqrt5*xi[0]*xi[0]-(5*(-1+xi[1]+xi[2])*(1-sqrt5+(-3+sqrt5)*xi[1]+(-3+sqrt5)*xi[2]))/2.-5*xi[0]*(1-3*sqrt5+3*(-1+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2]); + output[ 7] = (-5*xi[0]*(4-2*sqrt5+3*(-1+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2.; + output[ 8] = (-5*xi[0]*(4-2*sqrt5+3*(-1+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2.; + output[ 9] = 1+15*xi[0]*xi[0]+xi[1]-xi[1]*xi[1]+xi[2]-xi[1]*xi[2]-xi[2]*xi[2]-2*xi[0]*(5+xi[1]+xi[2]); + output[10] = -(xi[0]*(-1+xi[0]+2*xi[1]+xi[2])); + output[11] = -(xi[0]*(-1+xi[0]+xi[1]+2*xi[2])); + output[12] = (5*xi[1]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+3*(1+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2.; + output[13] = 15*sqrt5*xi[1]*xi[1]+5*xi[1]*(-1-3*sqrt5+3*(1+sqrt5)*xi[0]+3*(1+sqrt5)*xi[2])+(5*(-1+xi[0]+xi[2])*(-1-sqrt5+(3+sqrt5)*xi[0]+(3+sqrt5)*xi[2]))/2.; + output[14] = (5*xi[1]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+3*(1+sqrt5)*xi[1]+2*(3+sqrt5)*xi[2]))/2.; + output[15] = -27*xi[1]*(-1+2*xi[0]+xi[1]+xi[2]); + output[16] = -27*xi[0]*(-1+xi[0]+2*xi[1]+xi[2]); + output[17] = -27*xi[0]*xi[1]; + output[18] = (-5*xi[1]*(2-2*(3+sqrt5)*xi[0]+(-3+sqrt5)*xi[1]))/2.; + output[19] = (5*xi[0]*(-2+(3+sqrt5)*xi[0]-2*(-3+sqrt5)*xi[1]))/2.; + output[20] = 0; + output[21] = (-5*xi[1]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2.; + output[22] = -15*sqrt5*xi[1]*xi[1]-(5*(-1+xi[0]+xi[2])*(1-sqrt5+(-3+sqrt5)*xi[0]+(-3+sqrt5)*xi[2]))/2.-5*xi[1]*(1-3*sqrt5+3*(-1+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[2]); + output[23] = (-5*xi[1]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+3*(-1+sqrt5)*xi[1]+2*(-3+sqrt5)*xi[2]))/2.; + output[24] = (5*xi[1]*(-2-2*(-3+sqrt5)*xi[0]+(3+sqrt5)*xi[1]))/2.; + output[25] = (-5*xi[0]*(2+(-3+sqrt5)*xi[0]-2*(3+sqrt5)*xi[1]))/2.; + output[26] = 0; + output[27] = -(xi[1]*(-1+2*xi[0]+xi[1]+xi[2])); + output[28] = 1-xi[0]*xi[0]+15*xi[1]*xi[1]+xi[2]-xi[2]*xi[2]-2*xi[1]*(5+xi[2])-xi[0]*(-1+2*xi[1]+xi[2]); + output[29] = -(xi[1]*(-1+xi[0]+xi[1]+2*xi[2])); + output[30] = (5*xi[2]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+3*(1+sqrt5)*xi[2]))/2.; + output[31] = (5*xi[2]*(-2*(2+sqrt5)+2*(3+sqrt5)*xi[0]+2*(3+sqrt5)*xi[1]+3*(1+sqrt5)*xi[2]))/2.; + output[32] = (5*(1+sqrt5+(3+sqrt5)*xi[0]*xi[0]-2*(2+sqrt5)*xi[1]+(3+sqrt5)*xi[1]*xi[1]+6*(1+sqrt5)*xi[1]*xi[2]+2*xi[2]*(-1-3*sqrt5+3*sqrt5*xi[2])+2*xi[0]*(-2-sqrt5+(3+sqrt5)*xi[1]+3*(1+sqrt5)*xi[2])))/2.; + output[33] = -27*xi[2]*(-1+2*xi[0]+xi[1]+xi[2]); + output[34] = -27*xi[0]*xi[2]; + output[35] = -27*xi[0]*(-1+xi[0]+xi[1]+2*xi[2]); + output[36] = (-5*xi[2]*(2-2*(3+sqrt5)*xi[0]+(-3+sqrt5)*xi[2]))/2.; + output[37] = 0; + output[38] = (5*xi[0]*(-2+(3+sqrt5)*xi[0]-2*(-3+sqrt5)*xi[2]))/2.; + output[39] = -27*xi[1]*xi[2]; + output[40] = -27*xi[2]*(-1+xi[0]+2*xi[1]+xi[2]); + output[41] = -27*xi[1]*(-1+xi[0]+xi[1]+2*xi[2]); + output[42] = 27*xi[1]*xi[2]; + output[43] = 27*xi[0]*xi[2]; + output[44] = 27*xi[0]*xi[1]; + output[45] = 0; + output[46] = (-5*xi[2]*(2-2*(3+sqrt5)*xi[1]+(-3+sqrt5)*xi[2]))/2.; + output[47] = (5*xi[1]*(-2+(3+sqrt5)*xi[1]-2*(-3+sqrt5)*xi[2]))/2.; + output[48] = (-5*xi[2]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2]))/2.; + output[49] = (-5*xi[2]*(4-2*sqrt5+2*(-3+sqrt5)*xi[0]+2*(-3+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2]))/2.; + output[50] = (-5*(-3+sqrt5)*xi[0]*xi[0])/2.-5*xi[0]*(2-sqrt5+(-3+sqrt5)*xi[1]+3*(-1+sqrt5)*xi[2])-(5*(-1+sqrt5+(-3+sqrt5)*xi[1]*xi[1]+2*xi[2]*(1-3*sqrt5+3*sqrt5*xi[2])+xi[1]*(4-2*sqrt5+6*(-1+sqrt5)*xi[2])))/2.; + output[51] = (5*xi[2]*(-2-2*(-3+sqrt5)*xi[0]+(3+sqrt5)*xi[2]))/2.; + output[52] = 0; + output[53] = (-5*xi[0]*(2+(-3+sqrt5)*xi[0]-2*(3+sqrt5)*xi[2]))/2.; + output[54] = 0; + output[55] = (5*xi[2]*(-2-2*(-3+sqrt5)*xi[1]+(3+sqrt5)*xi[2]))/2.; + output[56] = (-5*xi[1]*(2+(-3+sqrt5)*xi[1]-2*(3+sqrt5)*xi[2]))/2.; + output[57] = -(xi[2]*(-1+2*xi[0]+xi[1]+xi[2])); + output[58] = -(xi[2]*(-1+xi[0]+2*xi[1]+xi[2])); + output[59] = 1+xi[0]-xi[0]*xi[0]+xi[1]-xi[0]*xi[1]-xi[1]*xi[1]-2*(5+xi[0]+xi[1])*xi[2]+15*xi[2]*xi[2]; + return; + } +} + +void GaussLobattoInterpolationHexahedron(const double * xi, uint32_t n, double * output) { + double * N[3] = {new double[n], new double[n], new double[n]}; + + GaussLobattoInterpolation(xi[0], n, N[0]); + GaussLobattoInterpolation(xi[1], n, N[1]); + GaussLobattoInterpolation(xi[2], n, N[2]); + + for (uint32_t k = 0; k < n; k++) { + for (uint32_t j = 0; j < n; j++) { + for (uint32_t i = 0; i < n; i++) { + output[(k * n + j) * n + i] = N[0][i] * N[1][j] * N[2][k]; + } + } + } + + delete N[0]; delete N[1]; delete N[2]; +} + +void GaussLobattoInterpolationDerivativeHexahedron(const double * xi, uint32_t n, double * output) { + double * N[3] = {new double[n], new double[n], new double[n]}; + double * dN[3] = {new double[n], new double[n], new double[n]}; + + GaussLobattoInterpolation(xi[0], n, N[0]); + GaussLobattoInterpolation(xi[1], n, N[1]); + GaussLobattoInterpolation(xi[2], n, N[2]); + + GaussLobattoInterpolation(xi[0], n, dN[0]); + GaussLobattoInterpolation(xi[1], n, dN[1]); + GaussLobattoInterpolation(xi[2], n, dN[2]); + + for (uint32_t k = 0; k < n; k++) { + for (uint32_t j = 0; j < n; j++) { + for (uint32_t i = 0; i < n; i++) { + output[3 * ((k * n + j) * n + i) + 0] = dN[0][i] * N[1][j] * N[2][k]; + output[3 * ((k * n + j) * n + i) + 1] = N[0][i] * dN[1][j] * N[2][k]; + output[3 * ((k * n + j) * n + i) + 2] = N[0][i] * N[1][j] * dN[2][k]; + } + } + } + + delete N[0]; delete N[1]; delete N[2]; + delete dN[0]; delete dN[1]; delete dN[2]; +} + +} // namespace refactor diff --git a/src/serac/numerics/refactor/interpolation.hpp b/src/serac/numerics/refactor/interpolation.hpp new file mode 100644 index 0000000000..eb5e911a50 --- /dev/null +++ b/src/serac/numerics/refactor/interpolation.hpp @@ -0,0 +1,180 @@ +#pragma once + +#include "serac/numerics/functional/tensor.hpp" + +namespace refactor { + +template< int n, int i > +constexpr double GaussLegendreNode01() { + if constexpr (n == 1 && i == 0) { return 0.5; } + + if constexpr (n == 2 && i == 0) { return 0.21132486540518711774542560975; } + if constexpr (n == 2 && i == 1) { return 0.78867513459481288225457439025; } + + if constexpr (n == 3 && i == 0) { return 0.11270166537925831148207346002; } + if constexpr (n == 3 && i == 1) { return 0.5000000000000000000000000000; } + if constexpr (n == 3 && i == 2) { return 0.8872983346207416885179265400; } + + if constexpr (n == 4 && i == 0) { return 0.06943184420297371238802675555; } + if constexpr (n == 4 && i == 1) { return 0.3300094782075718675986671204; } + if constexpr (n == 4 && i == 2) { return 0.6699905217924281324013328796; } + if constexpr (n == 4 && i == 3) { return 0.9305681557970262876119732444; } + + if constexpr (n == 5 && i == 0) { return 0.04691007703066800360118656085; } + if constexpr (n == 5 && i == 1) { return 0.2307653449471584544818427896; } + if constexpr (n == 5 && i == 2) { return 0.5000000000000000000000000000; } + if constexpr (n == 5 && i == 3) { return 0.7692346550528415455181572104; } + if constexpr (n == 5 && i == 4) { return 0.9530899229693319963988134391; } + + if constexpr (n == 6 && i == 0) { return 0.03376524289842398609384922275; } + if constexpr (n == 6 && i == 1) { return 0.1693953067668677431693002025; } + if constexpr (n == 6 && i == 2) { return 0.3806904069584015456847491392; } + if constexpr (n == 6 && i == 3) { return 0.6193095930415984543152508608; } + if constexpr (n == 6 && i == 4) { return 0.8306046932331322568306997975; } + if constexpr (n == 6 && i == 5) { return 0.9662347571015760139061507772; } + + return -1000.0; +}; + +template< int n, int i > +constexpr double GaussLegendreInterpolation01(double x) { + + if constexpr (n == 1 && i == 0) { return 1; } + + if constexpr (n == 2 && i == 0) { return 1.3660254037844386467637231708 - 1.732050807568877293527446342*x; } + if constexpr (n == 2 && i == 1) { return -0.3660254037844386467637231708 + 1.7320508075688772935274463415*x; } + + if constexpr (n == 3 && i == 0) { return 1.4788305577012361475298776 + x*(-4.624327782069138961726422 + 3.3333333333333333333333333*x); } + if constexpr (n == 3 && i == 1) { return -0.666666666666666666666666667 + (6.66666666666666666666666667 - 6.666666666666666666666666667*x)*x; } + if constexpr (n == 3 && i == 2) { return 0.1878361089654305191367891 + x*(-2.0423388845975277049402449 + 3.3333333333333333333333333*x); } + + if constexpr (n == 4 && i == 0) { return 1.526788125457266786984328 + x*(-8.54602360787219876597302 + (14.32585835417188815296662 - 7.42054006803894610520064*x)*x); } + if constexpr (n == 4 && i == 1) { return -0.8136324494869272605619 + x*(13.8071669256895770661587 + x*(-31.3882223634460602120582 + 18.7954494075550608112617*x)); } + if constexpr (n == 4 && i == 2) { return 0.400761520311650404800281777 + x*(-7.41707042146263907582738061 + (24.9981258592191222217269164 - 18.79544940755506081126171563*x)*x); } + if constexpr (n == 4 && i == 3) { return -0.11391719628198993122271197 + x*(2.1559271036452607756417044 + x*(-7.935761849944950162635307 + 7.420540068038946105200642*x)); } + + if constexpr (n == 5 && i == 0) { return 1.551408049094313012813028 + x*(-13.47028450119487106120462 + x*(38.6444990553441957009803 + x*(-44.9889850558789977671881 + 18.33972111443117301508323*x))); } + if constexpr (n == 5 && i == 1) { return -0.8931583920000717373262 + x*(22.924333555723729737768 + x*(-88.22281082816288605026 + (117.8634151266470135556 - 51.939721114431173015083*x)*x)); } + if constexpr (n == 5 && i == 2) { return 0.5333333333333333333333 + x*(-14.933333333333333333333 + x*(82.13333333333333333333 + x*(-134.4 + 67.2*x))); } + if constexpr (n == 5 && i == 3) { return -0.26794165222338750930410993 + x*(7.6899271783856937562943889 + x*(-46.270892134808883473969833 + (89.895469331077678504736602 - 51.9397211144311730150832251*x)*x)); } + if constexpr (n == 5 && i == 4) { return 0.07635866179581290048392539 + x*(-2.210642899581219099524808 + x*(13.71587057429424048991553 + x*(-28.36989940184569429314485 + 18.33972111443117301508323*x))); } + + if constexpr (n == 6 && i == 0) { return 1.565673200151071933093717 + x*(-19.38889969575614186464859 + x*(83.3561716652066047719407 + x*(-161.6334485633571811708389 + (144.8933610434784341266087 - 48.8475703740520537090491*x)*x))); } + if constexpr (n == 6 && i == 1) { return -0.94046284317634892902 + x*(33.94755689005745838881 + x*(-194.5900409203250530156 + x*(431.2442105751191477314 + x*(-416.6718961318097255735 + 147.20243244417318935282*x)))); } + if constexpr (n == 6 && i == 2) { return 0.616930055430488708617 + x*(-24.29050650593736015819 + x*(195.3041651669510511719 + x*(-523.416260790836176187 + (568.4164873451100029584 - 217.0100429728326202484*x)*x))); } + if constexpr (n == 6 && i == 3) { return -0.37922770211461375461734918 + x*(15.315224028266875783526055 + x*(-134.54612286322366212220967 + x*(419.85074113872236683695564 + x*(-516.63372751905309828340431 + 217.010042972832620248366597*x)))); } + if constexpr (n == 6 && i == 4) { return 0.1918000140386679548202 + x*(-7.82468446839184002159 + x*(71.1355384559059302654 + x*(-236.5809504896121389654 + (319.3402660890562211905 - 147.2024324441731893528*x)*x))); } + if constexpr (n == 6 && i == 5) { return -0.05471272432926591289350948 + x*(2.241309751761007872094777 + x*(-20.65971150451487107141517 + x*(70.5357081299639817548955 + x*(-99.344490826781834418637 + 48.84757037405205370904914*x)))); } + + return {}; +} + +template< int n, int i > +constexpr double GaussLegendreInterpolationDerivative01(double x) { + + if constexpr (n == 1 && i == 0) { return 0; } + + if constexpr (n == 2 && i == 0) { return -1.7320508075688772935274463415; } + if constexpr (n == 2 && i == 1) { return 1.7320508075688772935274463415; } + + if constexpr (n == 3 && i == 0) { return -4.6243277820691389617264218 + 6.6666666666666666666666667*x; } + if constexpr (n == 3 && i == 1) { return 6.66666666666666666666666667 - 13.3333333333333333333333333*x; } + if constexpr (n == 3 && i == 2) { return -2.04233888459752770494024487 + 6.6666666666666666666666667*x; } + + if constexpr (n == 4 && i == 0) { return -8.546023607872198765973 + (28.6517167083437763059332 - 22.2616202041168383156019*x)*x; } + if constexpr (n == 4 && i == 1) { return 13.80716692568958 + x*(-62.7764447268921 + 56.3863482226652*x); } + if constexpr (n == 4 && i == 2) { return -7.417070421462639075827381 + (49.99625171843824444345383 - 56.38634822266518243378515*x)*x; } + if constexpr (n == 4 && i == 3) { return 2.155927103645260775641704 + x*(-15.87152369988990032527061 + 22.26162020411683831560193*x); } + + if constexpr (n == 5 && i == 0) { return -13.4702845011948710612046 + x*(77.288998110688391401961 + x*(-134.966955167636993301564 + 73.358884457724692060333*x)); } + if constexpr (n == 5 && i == 1) { return 22.92433355572373 + x*(-176.4456216563258 + (353.590245379941 - 207.7588844577247*x)*x); } + if constexpr (n == 5 && i == 2) { return -14.93333333333333 + x*(164.2666666666667 + x*(-403.2 + 268.8*x)); } + if constexpr (n == 5 && i == 3) { return 7.689927178385693756294389 + x*(-92.54178426961776694793967 + (269.6864079932330355142098 - 207.7588844577246920603329*x)*x); } + if constexpr (n == 5 && i == 4) { return -2.21064289958121909952481 + x*(27.4317411485884809798311 + x*(-85.1096982055370828794345 + 73.3588844577246920603329*x)); } + + if constexpr (n == 6 && i == 0) { return -19.3888996957561418646486 + x*(166.712343330413209543881 + x*(-484.90034569007154351252 + (579.57344417391373650643 - 244.23785187026026854525*x)*x)); } + if constexpr (n == 6 && i == 1) { return 33.94755689005746 + x*(-389.18008184065 + x*(1293.732631725357 + x*(-1666.687584527239 + 736.012162220866*x))); } + if constexpr (n == 6 && i == 2) { return -24.29050650593736 + x*(390.6083303339021 + x*(-1570.248782372509 + (2273.66594938044 - 1085.050214864163*x)*x)); } + if constexpr (n == 6 && i == 3) { return 15.31522402826687578352605 + x*(-269.0922457264473242444193 + x*(1259.552223416167100510867 + x*(-2066.534910076212393133617 + 1085.050214864163101241833*x))); } + if constexpr (n == 6 && i == 4) { return -7.82468446839184 + x*(142.2710769118119 + x*(-709.742851468836 + (1277.361064356225 - 736.012162220866*x)*x)); } + if constexpr (n == 6 && i == 5) { return 2.24130975176100787209478 + x*(-41.3194230090297421428303 + x*(211.607124389891945264686 + x*(-397.377963307127337674548 + 244.237851870260268545246*x))); } + + return {}; +} + +template< int n, int i > +constexpr double GaussLobattoNode01() { + if constexpr (n == 1 && i == 0) { return 0.5; } + + if constexpr (n == 2 && i == 0) { return 0.0; } + if constexpr (n == 2 && i == 1) { return 1.0; } + + if constexpr (n == 3 && i == 0) { return 0.0; } + if constexpr (n == 3 && i == 1) { return 0.5; } + if constexpr (n == 3 && i == 2) { return 1.0; } + + if constexpr (n == 4 && i == 0) { return 0.0; } + if constexpr (n == 4 && i == 1) { return 0.2763932022500210; } + if constexpr (n == 4 && i == 2) { return 0.7236067977499790; } + if constexpr (n == 4 && i == 3) { return 1.0; } + + return -1000.0; +} + +void GaussLegendreNodes(uint32_t n, double * output); +void GaussLegendreInterpolation(double x, uint32_t n, double * output); +void GaussLegendreInterpolationDerivative(double x, uint32_t n, double * output); + +void GaussLobattoNodes(uint32_t n, double * output); +void GaussLobattoInterpolation(double x, uint32_t n, double * output); +void GaussLobattoInterpolationDerivative(double x, uint32_t n, double * output); + +constexpr double GaussLobattoInterpolation(double x, uint32_t n, uint32_t i) { + if (n == 1) { return 1.0; } + if (n == 2) { return (i == 0) ? 1.0 - x : x; } + if (n == 3) { + if (i == 0) return (-1.0 + x) * (-1.0 + 2.0 * x); + if (i == 1) return -4.0 * (-1.0 + x) * x; + if (i == 2) return x * (-1.0 + 2.0 * x); + } + if (n == 4) { + constexpr double sqrt5 = 2.23606797749978981; + if (i == 0) return -(-1.0 + x) * (1.0 + 5.0 * (-1.0 + x) * x); + if (i == 1) return -0.5 * sqrt5 * (5.0 + sqrt5 - 10.0 * x) * (-1.0 + x) * x; + if (i == 2) return -0.5 * sqrt5 * (-1.0 + x) * x * (-5.0 + sqrt5 + 10.0 * x); + if (i == 3) return x * (1.0 + 5.0 * (-1.0 + x) * x); + } + return -1.0; +} + +constexpr double GaussLobattoInterpolationDerivative(double x, uint32_t n, uint32_t i) { + if (n == 1) { return 0.0; } + if (n == 2) { return (i == 0) ? -1.0 : 1.0; } + if (n == 3) { + if (i == 0) return -3.0 + 4.0 * x; + if (i == 1) return 4.0 - 8.0 * x; + if (i == 2) return -1.0 + 4.0 * x; + } + if (n == 4) { + constexpr double sqrt5 = 2.23606797749978981; + if (i == 0) return -6.0 + 5.0 * (4.0 - 3.0 * x) * x; + if (i == 1) return 2.5 * (1.0 + sqrt5 + 2.0 * x * (-1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * x)); + if (i == 2) return -2.5 * (-1.0 + sqrt5 + 2.0 * x * (1.0 - 3.0 * sqrt5 + 3.0 * sqrt5 * x)); + if (i == 3) return 1.0 + 5.0 * x * (-2.0 + 3.0 * x); + } + return -1.0; +} + +void GaussLobattoInterpolationTriangle(const double * xi, uint32_t p, double * output); +void GaussLobattoInterpolationDerivativeTriangle(const double * xi, uint32_t p, double * output); + +void GaussLobattoInterpolationQuadrilateral(const double * xi, uint32_t n, double * output); +void GaussLobattoInterpolationDerivativeQuadrilateral(const double * xi, uint32_t n, double * output); + +void GaussLobattoInterpolationTetrahedron(const double * xi, uint32_t p, double * output); +void GaussLobattoInterpolationDerivativeTetrahedron(const double * xi, uint32_t p, double * output); + +void GaussLobattoInterpolationHexahedron(const double * xi, uint32_t n, double * output); +void GaussLobattoInterpolationDerivativeHexahedron(const double * xi, uint32_t n, double * output); + +} // namespace refactor diff --git a/src/serac/numerics/refactor/quadrature.cpp b/src/serac/numerics/refactor/quadrature.cpp new file mode 100644 index 0000000000..b0fd173ba1 --- /dev/null +++ b/src/serac/numerics/refactor/quadrature.cpp @@ -0,0 +1,378 @@ +#include "serac/numerics/refactor/quadrature.hpp" + +#include "serac/numerics/refactor/common.hpp" + +#include + +namespace refactor { + +void gauss_legendre_segment_rule(uint32_t q, double * qpts, double * qwts) { + + // clang-format off + switch (q) { + case 1: + qpts[0] = 0.5; qwts[0] = 1.0; + break; + case 2: + qpts[0] = 0.2113248654051871; qwts[0] = 0.5; + qpts[1] = 0.7886751345948129; qwts[1] = 0.5; + break; + case 3: + qpts[0] = 0.1127016653792583; qwts[0] = 0.277777777777778; + qpts[1] = 0.500000000000000; qwts[1] = 0.444444444444444; + qpts[2] = 0.887298334620742; qwts[2] = 0.277777777777778; + break; + case 4: + qpts[0] = 0.0694318442029737; qwts[0] = 0.173927422568727; + qpts[1] = 0.330009478207572 ; qwts[1] = 0.326072577431273; + qpts[2] = 0.669990521792428 ; qwts[2] = 0.326072577431273; + qpts[3] = 0.930568155797026 ; qwts[3] = 0.173927422568727; + break; + case 5: + qpts[0] = 0.04691007703066800; qwts[0] = 0.11846344252809454; + qpts[1] = 0.2307653449471585 ; qwts[1] = 0.23931433524968323; + qpts[2] = 0.5000000000000000 ; qwts[2] = 0.28444444444444444; + qpts[3] = 0.7692346550528415 ; qwts[3] = 0.23931433524968323; + qpts[4] = 0.9530899229693320 ; qwts[4] = 0.11846344252809454; + break; + case 6: + qpts[0] = 0.03376524289842399; qwts[0] = 0.08566224618958517; + qpts[1] = 0.1693953067668677 ; qwts[1] = 0.18038078652406930; + qpts[2] = 0.3806904069584015 ; qwts[2] = 0.23395696728634552; + qpts[3] = 0.6193095930415985 ; qwts[3] = 0.23395696728634552; + qpts[4] = 0.8306046932331323 ; qwts[4] = 0.18038078652406930; + qpts[5] = 0.9662347571015760 ; qwts[5] = 0.08566224618958517; + break; + } + // clang-format on + +} + +void gauss_legendre_triangle_rule(uint32_t q, double * qpts, double * qwts) { + + // clang-format off + switch(q) { + case 1: + qpts[ 0] = 0.333333333333333; qpts[ 1] = 0.333333333333333; qwts[ 0] = 0.5; + break; + case 2: + qpts[ 0] = 0.166666666666667; qpts[ 1] = 0.166666666666667; qwts[ 0] = 0.166666666666667; + qpts[ 2] = 0.166666666666667; qpts[ 3] = 0.666666666666667; qwts[ 1] = 0.166666666666667; + qpts[ 4] = 0.666666666666667; qpts[ 5] = 0.166666666666667; qwts[ 2] = 0.166666666666667; + break; + case 3: + qpts[ 0] = 0.09157621350978; qpts[ 1] = 0.09157621350978; qwts[ 0] = 0.0549758718276665; + qpts[ 2] = 0.09157621350978; qpts[ 3] = 0.81684757298044; qwts[ 1] = 0.0549758718276665; + qpts[ 4] = 0.81684757298044; qpts[ 5] = 0.09157621350978; qwts[ 2] = 0.0549758718276665; + qpts[ 6] = 0.108103018168071; qpts[ 7] = 0.445948490915964; qwts[ 3] = 0.111690794839; + qpts[ 8] = 0.445948490915964; qpts[ 9] = 0.108103018168071; qwts[ 4] = 0.111690794839; + qpts[10] = 0.445948490915964; qpts[11] = 0.445948490915964; qwts[ 5] = 0.111690794839; + break; + case 4: + qpts[ 0] = 0.055564052669793; qpts[ 1] = 0.055564052669793; qwts[ 0] = 0.0209777564983245; + qpts[ 2] = 0.055564052669793; qpts[ 3] = 0.888871894660413; qwts[ 1] = 0.0209777564983245; + qpts[ 4] = 0.888871894660413; qpts[ 5] = 0.055564052669793; qwts[ 2] = 0.0209777564983245; + qpts[ 6] = 0.070255540518384; qpts[ 7] = 0.634210747745723; qwts[ 3] = 0.0560492060354435; + qpts[ 8] = 0.634210747745723; qpts[ 9] = 0.070255540518384; qwts[ 4] = 0.0560492060354435; + qpts[10] = 0.634210747745723; qpts[11] = 0.295533711735893; qwts[ 5] = 0.0560492060354435; + qpts[12] = 0.070255540518384; qpts[13] = 0.295533711735893; qwts[ 6] = 0.0560492060354435; + qpts[14] = 0.295533711735893; qpts[15] = 0.070255540518384; qwts[ 7] = 0.0560492060354435; + qpts[16] = 0.295533711735893; qpts[17] = 0.634210747745723; qwts[ 8] = 0.0560492060354435; + qpts[18] = 0.333333333333333; qpts[19] = 0.333333333333333; qwts[ 9] = 0.100771494292365; + break; + case 5: + qpts[ 0] = 0.035870877695734; qpts[ 1] = 0.035870877695734; qwts[ 0] = 1.0089577275061515; + qpts[ 2] = 0.035870877695734; qpts[ 3] = 0.928258244608533; qwts[ 1] = 0.0089577275061515; + qpts[ 4] = 0.928258244608533; qpts[ 5] = 0.035870877695734; qwts[ 2] = 0.0089577275061515; + qpts[ 6] = 0.241729395767967; qpts[ 7] = 0.241729395767967; qwts[ 3] = 0.0638560979406325; + qpts[ 8] = 0.241729395767967; qpts[ 9] = 0.516541208464066; qwts[ 4] = 0.0638560979406325; + qpts[10] = 0.516541208464066; qpts[11] = 0.241729395767967; qwts[ 5] = 0.0638560979406325; + qpts[12] = 0.051382424445843; qpts[13] = 0.474308787777079; qwts[ 6] = 0.0381030311927675; + qpts[14] = 0.474308787777079; qpts[15] = 0.051382424445843; qwts[ 7] = 0.0381030311927675; + qpts[16] = 0.474308787777079; qpts[17] = 0.474308787777079; qwts[ 8] = 0.0381030311927675; + qpts[18] = 0.047312487011716; qpts[19] = 0.751183631106484; qwts[ 9] = 0.0278749050135575; + qpts[20] = 0.751183631106484; qpts[21] = 0.047312487011716; qwts[ 0] = 0.0278749050135575; + qpts[22] = 0.751183631106484; qpts[23] = 0.2015038818818; qwts[ 1] = 0.0278749050135575; + qpts[24] = 0.047312487011716; qpts[25] = 0.2015038818818; qwts[ 2] = 0.0278749050135575; + qpts[26] = 0.2015038818818; qpts[27] = 0.047312487011716; qwts[ 3] = 0.0278749050135575; + qpts[28] = 0.2015038818818; qpts[29] = 0.751183631106484; qwts[ 4] = 0.0278749050135575; + break; + case 6: + qpts[ 0] = 0.028112952182664; qpts[ 1] = 0.028112952182664; qwts[ 0] = 0.005179687348269; + qpts[ 2] = 0.028112952182664; qpts[ 3] = 0.943774095634672; qwts[ 1] = 0.005179687348269; + qpts[ 4] = 0.943774095634672; qpts[ 5] = 0.028112952182664; qwts[ 2] = 0.005179687348269; + qpts[ 6] = 0.177139098469317; qpts[ 7] = 0.177139098469317; qwts[ 3] = 0.037697442163369; + qpts[ 8] = 0.177139098469317; qpts[ 9] = 0.645721803061365; qwts[ 4] = 0.037697442163369; + qpts[10] = 0.645721803061365; qpts[11] = 0.177139098469317; qwts[ 5] = 0.037697442163369; + qpts[12] = 0.188982808265134; qpts[13] = 0.405508595867433; qwts[ 6] = 0.048773901186621; + qpts[14] = 0.405508595867433; qpts[15] = 0.188982808265134; qwts[ 7] = 0.048773901186621; + qpts[16] = 0.405508595867433; qpts[17] = 0.405508595867433; qwts[ 8] = 0.048773901186621; + qpts[18] = 0.033533207700614; qpts[19] = 0.817900980028499; qwts[ 9] = 0.0144846346862365; + qpts[20] = 0.817900980028499; qpts[21] = 0.033533207700614; qwts[10] = 0.0144846346862365; + qpts[22] = 0.817900980028499; qpts[23] = 0.148565812270887; qwts[11] = 0.0144846346862365; + qpts[24] = 0.033533207700614; qpts[25] = 0.148565812270887; qwts[12] = 0.0144846346862365; + qpts[26] = 0.148565812270887; qpts[27] = 0.033533207700614; qwts[13] = 0.0144846346862365; + qpts[28] = 0.148565812270887; qpts[29] = 0.817900980028499; qwts[14] = 0.0144846346862365; + qpts[30] = 0.037824789609186; qpts[31] = 0.604978911775132; qwts[15] = 0.0230231832979675; + qpts[32] = 0.604978911775132; qpts[33] = 0.037824789609186; qwts[16] = 0.0230231832979675; + qpts[34] = 0.604978911775132; qpts[35] = 0.357196298615681; qwts[17] = 0.0230231832979675; + qpts[36] = 0.037824789609186; qpts[37] = 0.357196298615681; qwts[18] = 0.0230231832979675; + qpts[38] = 0.357196298615681; qpts[39] = 0.037824789609186; qwts[19] = 0.0230231832979675; + qpts[40] = 0.357196298615681; qpts[41] = 0.604978911775132; qwts[20] = 0.0230231832979675; + break; + } + // clang-format on + +} + +void gauss_legendre_tetrahedron_rule(uint32_t q, double * qpts, double * qwts) { + + // clang-format off + switch(q) { + case(1): + qpts[0] = 0.25; qpts[1] = 0.25; qpts[2] = 0.25; qwts[0] = 0.166666666666666656; + break; + case(2): + qpts[0] = 0.585410196624967936; qpts[1] = 0.138196601125011008; qpts[2] = 0.138196601125011008; qwts[0] = 0.0416666666666666624; + qpts[3] = 0.138196601125011008; qpts[4] = 0.585410196624967936; qpts[5] = 0.138196601125011008; qwts[1] = 0.0416666666666666624; + qpts[6] = 0.138196601125011008; qpts[7] = 0.138196601125011008; qpts[8] = 0.585410196624967936; qwts[2] = 0.0416666666666666624; + qpts[9] = 0.138196601125011008; qpts[10] = 0.138196601125011008; qpts[11] = 0.138196601125011008; qwts[3] = 0.0416666666666666624; + break; + case(3): + qpts[0] = 0.77849529482132992; qpts[1] = 0.0738349017262233984; qpts[2] = 0.0738349017262233984; qwts[0] = 0.00793885580720148224; + qpts[3] = 0.0738349017262233984; qpts[4] = 0.77849529482132992; qpts[5] = 0.0738349017262233984; qwts[1] = 0.00793885580720148224; + qpts[6] = 0.0738349017262233984; qpts[7] = 0.0738349017262233984; qpts[8] = 0.77849529482132992; qwts[2] = 0.00793885580720148224; + qpts[9] = 0.0738349017262233984; qpts[10] = 0.0738349017262233984; qpts[11] = 0.0738349017262233984; qwts[3] = 0.00793885580720148224; + qpts[12] = 0.406244343884051008; qpts[13] = 0.406244343884051008; qpts[14] = 0.0937556561159491072; qwts[4] = 0.022485207239643504; + qpts[15] = 0.406244343884051008; qpts[16] = 0.0937556561159491072; qpts[17] = 0.406244343884051008; qwts[5] = 0.022485207239643504; + qpts[18] = 0.406244343884051008; qpts[19] = 0.0937556561159491072; qpts[20] = 0.0937556561159491072; qwts[6] = 0.022485207239643504; + qpts[21] = 0.0937556561159491072; qpts[22] = 0.406244343884051008; qpts[23] = 0.406244343884051008; qwts[7] = 0.022485207239643504; + qpts[24] = 0.0937556561159491072; qpts[25] = 0.406244343884051008; qpts[26] = 0.0937556561159491072; qwts[8] = 0.022485207239643504; + qpts[27] = 0.0937556561159491072; qpts[28] = 0.0937556561159491072; qpts[29] = 0.406244343884051008; qwts[9] = 0.022485207239643504; + break; + case(4): + qpts[0] = 0.902942215818267904; qpts[1] = 0.0323525947272438976; qpts[2] = 0.0323525947272438976; qwts[0] = 0.00117784579907825008; + qpts[3] = 0.0323525947272438976; qpts[4] = 0.902942215818267904; qpts[5] = 0.0323525947272438976; qwts[1] = 0.00117784579907825008; + qpts[6] = 0.0323525947272438976; qpts[7] = 0.0323525947272438976; qpts[8] = 0.902942215818267904; qwts[2] = 0.00117784579907825008; + qpts[9] = 0.0323525947272438976; qpts[10] = 0.0323525947272438976; qpts[11] = 0.0323525947272438976; qwts[3] = 0.00117784579907825008; + qpts[12] = 0.262682583887778976; qpts[13] = 0.616596533061936896; qpts[14] = 0.0603604415251420928; qwts[4] = 0.0078331114953146176; + qpts[15] = 0.616596533061936896; qpts[16] = 0.262682583887778976; qpts[17] = 0.0603604415251420928; qwts[5] = 0.0078331114953146176; + qpts[18] = 0.262682583887778976; qpts[19] = 0.0603604415251420928; qpts[20] = 0.616596533061936896; qwts[6] = 0.0078331114953146176; + qpts[21] = 0.616596533061936896; qpts[22] = 0.0603604415251420928; qpts[23] = 0.262682583887778976; qwts[7] = 0.0078331114953146176; + qpts[24] = 0.262682583887778976; qpts[25] = 0.0603604415251420928; qpts[26] = 0.0603604415251420928; qwts[8] = 0.0078331114953146176; + qpts[27] = 0.616596533061936896; qpts[28] = 0.0603604415251420928; qpts[29] = 0.0603604415251420928; qwts[9] = 0.0078331114953146176; + qpts[30] = 0.0603604415251420928; qpts[31] = 0.262682583887778976; qpts[32] = 0.616596533061936896; qwts[10] = 0.0078331114953146176; + qpts[33] = 0.0603604415251420928; qpts[34] = 0.616596533061936896; qpts[35] = 0.262682583887778976; qwts[11] = 0.0078331114953146176; + qpts[36] = 0.0603604415251420928; qpts[37] = 0.262682583887778976; qpts[38] = 0.0603604415251420928; qwts[12] = 0.0078331114953146176; + qpts[39] = 0.0603604415251420928; qpts[40] = 0.616596533061936896; qpts[41] = 0.0603604415251420928; qwts[13] = 0.0078331114953146176; + qpts[42] = 0.0603604415251420928; qpts[43] = 0.0603604415251420928; qpts[44] = 0.262682583887778976; qwts[14] = 0.0078331114953146176; + qpts[45] = 0.0603604415251420928; qpts[46] = 0.0603604415251420928; qpts[47] = 0.616596533061936896; qwts[15] = 0.0078331114953146176; + qpts[48] = 0.309769304272861952; qpts[49] = 0.309769304272861952; qpts[50] = 0.309769304272861952; qwts[16] = 0.0169894863816446688; + qpts[51] = 0.309769304272861952; qpts[52] = 0.309769304272861952; qpts[53] = 0.0706920871814129024; qwts[17] = 0.0169894863816446688; + qpts[54] = 0.309769304272861952; qpts[55] = 0.0706920871814129024; qpts[56] = 0.309769304272861952; qwts[18] = 0.0169894863816446688; + qpts[57] = 0.0706920871814129024; qpts[58] = 0.309769304272861952; qpts[59] = 0.309769304272861952; qwts[19] = 0.0169894863816446688; + break; + case(5): + qpts[0] = 0.91978967333688; qpts[1] = 0.0267367755543734976; qpts[2] = 0.0267367755543734976; qwts[0] = 0.000365007732756466624; + qpts[3] = 0.0267367755543734976; qpts[4] = 0.91978967333688; qpts[5] = 0.0267367755543734976; qwts[1] = 0.000365007732756466624; + qpts[6] = 0.0267367755543734976; qpts[7] = 0.0267367755543734976; qpts[8] = 0.91978967333688; qwts[2] = 0.000365007732756466624; + qpts[9] = 0.0267367755543734976; qpts[10] = 0.0267367755543734976; qpts[11] = 0.0267367755543734976; qwts[3] = 0.000365007732756466624; + qpts[12] = 0.174035630246894016; qpts[13] = 0.747759888481809024; qpts[14] = 0.0391022406356488; qwts[4] = 0.00238992783629441664; + qpts[15] = 0.747759888481809024; qpts[16] = 0.174035630246894016; qpts[17] = 0.0391022406356488; qwts[5] = 0.00238992783629441664; + qpts[18] = 0.174035630246894016; qpts[19] = 0.0391022406356488; qpts[20] = 0.747759888481809024; qwts[6] = 0.00238992783629441664; + qpts[21] = 0.747759888481809024; qpts[22] = 0.0391022406356488; qpts[23] = 0.174035630246894016; qwts[7] = 0.00238992783629441664; + qpts[24] = 0.174035630246894016; qpts[25] = 0.0391022406356488; qpts[26] = 0.0391022406356488; qwts[8] = 0.00238992783629441664; + qpts[27] = 0.747759888481809024; qpts[28] = 0.0391022406356488; qpts[29] = 0.0391022406356488; qwts[9] = 0.00238992783629441664; + qpts[30] = 0.0391022406356488; qpts[31] = 0.174035630246894016; qpts[32] = 0.747759888481809024; qwts[10] = 0.00238992783629441664; + qpts[33] = 0.0391022406356488; qpts[34] = 0.747759888481809024; qpts[35] = 0.174035630246894016; qwts[11] = 0.00238992783629441664; + qpts[36] = 0.0391022406356488; qpts[37] = 0.174035630246894016; qpts[38] = 0.0391022406356488; qwts[12] = 0.00238992783629441664; + qpts[39] = 0.0391022406356488; qpts[40] = 0.747759888481809024; qpts[41] = 0.0391022406356488; qwts[13] = 0.00238992783629441664; + qpts[42] = 0.0391022406356488; qpts[43] = 0.0391022406356488; qpts[44] = 0.174035630246894016; qwts[14] = 0.00238992783629441664; + qpts[45] = 0.0391022406356488; qpts[46] = 0.0391022406356488; qpts[47] = 0.747759888481809024; qwts[15] = 0.00238992783629441664; + qpts[48] = 0.454754599984483008; qpts[49] = 0.454754599984483008; qpts[50] = 0.0452454000155171968; qwts[16] = 0.0041717565947791008; + qpts[51] = 0.454754599984483008; qpts[52] = 0.0452454000155171968; qpts[53] = 0.454754599984483008; qwts[17] = 0.0041717565947791008; + qpts[54] = 0.454754599984483008; qpts[55] = 0.0452454000155171968; qpts[56] = 0.0452454000155171968; qwts[18] = 0.0041717565947791008; + qpts[57] = 0.0452454000155171968; qpts[58] = 0.454754599984483008; qpts[59] = 0.454754599984483008; qwts[19] = 0.0041717565947791008; + qpts[60] = 0.0452454000155171968; qpts[61] = 0.454754599984483008; qpts[62] = 0.0452454000155171968; qwts[20] = 0.0041717565947791008; + qpts[63] = 0.0452454000155171968; qpts[64] = 0.0452454000155171968; qpts[65] = 0.454754599984483008; qwts[21] = 0.0041717565947791008; + qpts[66] = 0.503118645014598016; qpts[67] = 0.223201037962315008; qpts[68] = 0.223201037962315008; qwts[22] = 0.00799732221762589952; + qpts[69] = 0.223201037962315008; qpts[70] = 0.503118645014598016; qpts[71] = 0.223201037962315008; qwts[23] = 0.00799732221762589952; + qpts[72] = 0.223201037962315008; qpts[73] = 0.223201037962315008; qpts[74] = 0.503118645014598016; qwts[24] = 0.00799732221762589952; + qpts[75] = 0.503118645014598016; qpts[76] = 0.223201037962315008; qpts[77] = 0.050479279060772; qwts[25] = 0.00799732221762589952; + qpts[78] = 0.223201037962315008; qpts[79] = 0.503118645014598016; qpts[80] = 0.050479279060772; qwts[26] = 0.00799732221762589952; + qpts[81] = 0.223201037962315008; qpts[82] = 0.223201037962315008; qpts[83] = 0.050479279060772; qwts[27] = 0.00799732221762589952; + qpts[84] = 0.503118645014598016; qpts[85] = 0.050479279060772; qpts[86] = 0.223201037962315008; qwts[28] = 0.00799732221762589952; + qpts[87] = 0.223201037962315008; qpts[88] = 0.050479279060772; qpts[89] = 0.503118645014598016; qwts[29] = 0.00799732221762589952; + qpts[90] = 0.223201037962315008; qpts[91] = 0.050479279060772; qpts[92] = 0.223201037962315008; qwts[30] = 0.00799732221762589952; + qpts[93] = 0.050479279060772; qpts[94] = 0.503118645014598016; qpts[95] = 0.223201037962315008; qwts[31] = 0.00799732221762589952; + qpts[96] = 0.050479279060772; qpts[97] = 0.223201037962315008; qpts[98] = 0.503118645014598016; qwts[32] = 0.00799732221762589952; + qpts[99] = 0.050479279060772; qpts[100] = 0.223201037962315008; qpts[101] = 0.223201037962315008; qwts[33] = 0.00799732221762589952; + qpts[102] = 0.25; qpts[103] = 0.25; qpts[104] = 0.25; qwts[34] = 0.0155290955199223328; + break; + case(6): + qpts[0] = 0.955143804540822016; qpts[1] = 0.0149520651530592; qpts[2] = 0.0149520651530592; qwts[0] = 0.000172885205602333344; + qpts[3] = 0.0149520651530592; qpts[4] = 0.955143804540822016; qpts[5] = 0.0149520651530592; qwts[1] = 0.000172885205602333344; + qpts[6] = 0.0149520651530592; qpts[7] = 0.0149520651530592; qpts[8] = 0.955143804540822016; qwts[2] = 0.000172885205602333344; + qpts[9] = 0.0149520651530592; qpts[10] = 0.0149520651530592; qpts[11] = 0.0149520651530592; qwts[3] = 0.000172885205602333344; + qpts[12] = 0.779976008441539968; qpts[13] = 0.151831949165936992; qpts[14] = 0.0340960211962614976; qwts[4] = 0.00160027742332466656; + qpts[15] = 0.151831949165936992; qpts[16] = 0.779976008441539968; qpts[17] = 0.0340960211962614976; qwts[5] = 0.00160027742332466656; + qpts[18] = 0.779976008441539968; qpts[19] = 0.0340960211962614976; qpts[20] = 0.151831949165936992; qwts[6] = 0.00160027742332466656; + qpts[21] = 0.151831949165936992; qpts[22] = 0.0340960211962614976; qpts[23] = 0.779976008441539968; qwts[7] = 0.00160027742332466656; + qpts[24] = 0.779976008441539968; qpts[25] = 0.0340960211962614976; qpts[26] = 0.0340960211962614976; qwts[8] = 0.00160027742332466656; + qpts[27] = 0.151831949165936992; qpts[28] = 0.0340960211962614976; qpts[29] = 0.0340960211962614976; qwts[9] = 0.00160027742332466656; + qpts[30] = 0.0340960211962614976; qpts[31] = 0.779976008441539968; qpts[32] = 0.151831949165936992; qwts[10] = 0.00160027742332466656; + qpts[33] = 0.0340960211962614976; qpts[34] = 0.151831949165936992; qpts[35] = 0.779976008441539968; qwts[11] = 0.00160027742332466656; + qpts[36] = 0.0340960211962614976; qpts[37] = 0.779976008441539968; qpts[38] = 0.0340960211962614976; qwts[12] = 0.00160027742332466656; + qpts[39] = 0.0340960211962614976; qpts[40] = 0.151831949165936992; qpts[41] = 0.0340960211962614976; qwts[13] = 0.00160027742332466656; + qpts[42] = 0.0340960211962614976; qpts[43] = 0.0340960211962614976; qpts[44] = 0.779976008441539968; qwts[14] = 0.00160027742332466656; + qpts[45] = 0.0340960211962614976; qpts[46] = 0.0340960211962614976; qpts[47] = 0.151831949165936992; qwts[15] = 0.00160027742332466656; + qpts[48] = 0.354934056063979008; qpts[49] = 0.552655643106017024; qpts[50] = 0.0462051504150017024; qwts[16] = 0.00274156627997053312; + qpts[51] = 0.552655643106017024; qpts[52] = 0.354934056063979008; qpts[53] = 0.0462051504150017024; qwts[17] = 0.00274156627997053312; + qpts[54] = 0.354934056063979008; qpts[55] = 0.0462051504150017024; qpts[56] = 0.552655643106017024; qwts[18] = 0.00274156627997053312; + qpts[57] = 0.552655643106017024; qpts[58] = 0.0462051504150017024; qpts[59] = 0.354934056063979008; qwts[19] = 0.00274156627997053312; + qpts[60] = 0.354934056063979008; qpts[61] = 0.0462051504150017024; qpts[62] = 0.0462051504150017024; qwts[20] = 0.00274156627997053312; + qpts[63] = 0.552655643106017024; qpts[64] = 0.0462051504150017024; qpts[65] = 0.0462051504150017024; qwts[21] = 0.00274156627997053312; + qpts[66] = 0.0462051504150017024; qpts[67] = 0.354934056063979008; qpts[68] = 0.552655643106017024; qwts[22] = 0.00274156627997053312; + qpts[69] = 0.0462051504150017024; qpts[70] = 0.552655643106017024; qpts[71] = 0.354934056063979008; qwts[23] = 0.00274156627997053312; + qpts[72] = 0.0462051504150017024; qpts[73] = 0.354934056063979008; qpts[74] = 0.0462051504150017024; qwts[24] = 0.00274156627997053312; + qpts[75] = 0.0462051504150017024; qpts[76] = 0.552655643106017024; qpts[77] = 0.0462051504150017024; qwts[25] = 0.00274156627997053312; + qpts[78] = 0.0462051504150017024; qpts[79] = 0.0462051504150017024; qpts[80] = 0.354934056063979008; qwts[26] = 0.00274156627997053312; + qpts[81] = 0.0462051504150017024; qpts[82] = 0.0462051504150017024; qpts[83] = 0.552655643106017024; qwts[27] = 0.00274156627997053312; + qpts[84] = 0.538104322888002048; qpts[85] = 0.228190461068760992; qpts[86] = 0.228190461068760992; qwts[28] = 0.00256246277522183328; + qpts[87] = 0.228190461068760992; qpts[88] = 0.538104322888002048; qpts[89] = 0.228190461068760992; qwts[29] = 0.00256246277522183328; + qpts[90] = 0.228190461068760992; qpts[91] = 0.228190461068760992; qpts[92] = 0.538104322888002048; qwts[30] = 0.00256246277522183328; + qpts[93] = 0.538104322888002048; qpts[94] = 0.228190461068760992; qpts[95] = 0.00551475497447749952; qwts[31] = 0.00256246277522183328; + qpts[96] = 0.228190461068760992; qpts[97] = 0.538104322888002048; qpts[98] = 0.00551475497447749952; qwts[32] = 0.00256246277522183328; + qpts[99] = 0.228190461068760992; qpts[100] = 0.228190461068760992; qpts[101] = 0.00551475497447749952; qwts[33] = 0.00256246277522183328; + qpts[102] = 0.538104322888002048; qpts[103] = 0.00551475497447749952; qpts[104] = 0.228190461068760992; qwts[34] = 0.00256246277522183328; + qpts[105] = 0.228190461068760992; qpts[106] = 0.00551475497447749952; qpts[107] = 0.538104322888002048; qwts[35] = 0.00256246277522183328; + qpts[108] = 0.228190461068760992; qpts[109] = 0.00551475497447749952; qpts[110] = 0.228190461068760992; qwts[36] = 0.00256246277522183328; + qpts[111] = 0.00551475497447749952; qpts[112] = 0.538104322888002048; qpts[113] = 0.228190461068760992; qwts[37] = 0.00256246277522183328; + qpts[114] = 0.00551475497447749952; qpts[115] = 0.228190461068760992; qpts[116] = 0.538104322888002048; qwts[38] = 0.00256246277522183328; + qpts[117] = 0.00551475497447749952; qpts[118] = 0.228190461068760992; qpts[119] = 0.228190461068760992; qwts[39] = 0.00256246277522183328; + qpts[120] = 0.19618375957456; qpts[121] = 0.352305260087993984; qpts[122] = 0.352305260087993984; qwts[40] = 0.00489200197292049984; + qpts[123] = 0.352305260087993984; qpts[124] = 0.19618375957456; qpts[125] = 0.352305260087993984; qwts[41] = 0.00489200197292049984; + qpts[126] = 0.352305260087993984; qpts[127] = 0.352305260087993984; qpts[128] = 0.19618375957456; qwts[42] = 0.00489200197292049984; + qpts[129] = 0.19618375957456; qpts[130] = 0.352305260087993984; qpts[131] = 0.0992057202494530048; qwts[43] = 0.00489200197292049984; + qpts[132] = 0.352305260087993984; qpts[133] = 0.19618375957456; qpts[134] = 0.0992057202494530048; qwts[44] = 0.00489200197292049984; + qpts[135] = 0.352305260087993984; qpts[136] = 0.352305260087993984; qpts[137] = 0.0992057202494530048; qwts[45] = 0.00489200197292049984; + qpts[138] = 0.19618375957456; qpts[139] = 0.0992057202494530048; qpts[140] = 0.352305260087993984; qwts[46] = 0.00489200197292049984; + qpts[141] = 0.352305260087993984; qpts[142] = 0.0992057202494530048; qpts[143] = 0.19618375957456; qwts[47] = 0.00489200197292049984; + qpts[144] = 0.352305260087993984; qpts[145] = 0.0992057202494530048; qpts[146] = 0.352305260087993984; qwts[48] = 0.00489200197292049984; + qpts[147] = 0.0992057202494530048; qpts[148] = 0.19618375957456; qpts[149] = 0.352305260087993984; qwts[49] = 0.00489200197292049984; + qpts[150] = 0.0992057202494530048; qpts[151] = 0.352305260087993984; qpts[152] = 0.19618375957456; qwts[50] = 0.00489200197292049984; + qpts[153] = 0.0992057202494530048; qpts[154] = 0.352305260087993984; qpts[155] = 0.352305260087993984; qwts[51] = 0.00489200197292049984; + qpts[156] = 0.59656499562101696; qpts[157] = 0.134478334792994016; qpts[158] = 0.134478334792994016; qwts[52] = 0.00610485610675179904; + qpts[159] = 0.134478334792994016; qpts[160] = 0.59656499562101696; qpts[161] = 0.134478334792994016; qwts[53] = 0.00610485610675179904; + qpts[162] = 0.134478334792994016; qpts[163] = 0.134478334792994016; qpts[164] = 0.59656499562101696; qwts[54] = 0.00610485610675179904; + qpts[165] = 0.134478334792994016; qpts[166] = 0.134478334792994016; qpts[167] = 0.134478334792994016; qwts[55] = 0.00610485610675179904; + break; + } + // clang-format on + +} + +MeshQuadratureRule::MeshQuadratureRule(uint32_t q, bool compact) { + + if (q > 6) { + std::cout << "error: gauss_legendre_rule only supports up to q=6" << std::endl; + exit(1); + } + + type = QuadratureRuleType::UniformStructured; + + edge.compact = false; + edge.points = nd::array({q, 1}); + edge.weights = nd::array({q}); + gauss_legendre_segment_rule(q, edge.points.data(), edge.weights.data()); + + tri.compact = false; + tri.points = nd::array({(q * (q + 1)) / 2, 2}); + tri.weights = nd::array({(q * (q + 1)) / 2}); + gauss_legendre_triangle_rule(q, tri.points.data(), tri.weights.data()); + + tet.compact = false; + tet.points = nd::array({(q * (q + 1) * (q + 2)) / 6, 3}); + tet.weights = nd::array({(q * (q + 1) * (q + 2)) / 6}); + gauss_legendre_tetrahedron_rule(q, tet.points.data(), tet.weights.data()); + +//////////////////////////////////////////////////////////////////////////////////// + + if (compact) { + // note: quadrilaterals and hexahedra are treated differently here, + // they only store a 1D quadrature rule, and the + // cartesian-product structure is implied + quad.compact = true; + quad.points = nd::array({q, 1}); + quad.weights = nd::array({q}); + gauss_legendre_segment_rule(q, quad.points.data(), quad.weights.data()); + + hex.compact = true; + hex.points = nd::array({q, 1}); + hex.weights = nd::array({q}); + gauss_legendre_segment_rule(q, hex.points.data(), hex.weights.data()); + } else { + quad.compact = false; + quad.points = nd::array({q * q, 2}); + quad.weights = nd::array({q * q}); + uint32_t count = 0; + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + quad.points(count, 0) = edge.points(i, 0); + quad.points(count, 1) = edge.points(j, 0); + quad.weights(count) = edge.weights(i) * edge.weights(j); + } + } + + hex.compact = false; + hex.points = nd::array({q * q * q, 3}); + hex.weights = nd::array({q * q * q}); + count = 0; + for (uint32_t k = 0; k < q; k++) { + for (uint32_t j = 0; j < q; j++) { + for (uint32_t i = 0; i < q; i++) { + hex.points(count, 0) = edge.points(i, 0); + hex.points(count, 1) = edge.points(j, 0); + hex.points(count, 2) = edge.points(k, 0); + hex.weights(count) = edge.weights(i) * edge.weights(j) * edge.weights(k); + } + } + } + + } + +//////////////////////////////////////////////////////////////////////////////////// + +} + +GeometryInfo qpts_per_geom(const MeshQuadratureRule & qrule) { + return GeometryInfo { + 0, + qrule.edge.points.shape[0], + qrule.tri.points.shape[0], + qrule.quad.points.shape[0] * qrule.quad.points.shape[0], + qrule.tet.points.shape[0], + qrule.hex.points.shape[0] * qrule.hex.points.shape[0] * qrule.hex.points.shape[0] + }; +} + +GeometryInfo qpts_per_geom(const MeshQuadratureRule & qrule, int dim) { + return GeometryInfo { + 0, + (dim == 1) * qrule.edge.points.shape[0], + (dim == 2) * qrule.tri.points.shape[0], + (dim == 2) * qrule.quad.points.shape[0] * qrule.quad.points.shape[0], + (dim == 3) * qrule.tet.points.shape[0], + (dim == 3) * qrule.hex.points.shape[0] * qrule.hex.points.shape[0] * qrule.hex.points.shape[0] + }; +} + + +GeometryInfo MeshQuadratureRule::num_qpts(const serac::Domain & domain) const { + int gdim = domain.dim_; + GeometryInfo gcounts = refactor::geometry_counts(domain); + GeometryInfo qpts = qpts_per_geom(*this, gdim); + return gcounts * qpts; +}; + +} // namespace refactor diff --git a/src/serac/numerics/refactor/quadrature.hpp b/src/serac/numerics/refactor/quadrature.hpp new file mode 100644 index 0000000000..b8fe85f9b5 --- /dev/null +++ b/src/serac/numerics/refactor/quadrature.hpp @@ -0,0 +1,59 @@ +#pragma once + +#include "serac/numerics/refactor/geometry.hpp" +#include "serac/numerics/functional/domain.hpp" +#include "serac/numerics/refactor/containers/ndarray.hpp" + +namespace refactor { + +struct ElementQuadratureRule { + bool compact; + nd::array points; + nd::array weights; +}; + +enum class QuadratureRuleType { UniformStructured, UniformUnstructured, Nonuniform }; + +struct MeshQuadratureRule : public GeometryData< ElementQuadratureRule >{ + MeshQuadratureRule(uint32_t q, bool compact = true); + QuadratureRuleType type; + + GeometryInfo num_qpts(const serac::Domain & domain) const; +}; + +void gauss_legendre_segment_rule(uint32_t q, double * qpts, double * qwts); +void gauss_legendre_triangle_rule(uint32_t q, double * qpts, double * qwts); +void gauss_legendre_tetrahedron_rule(uint32_t q, double * qpts, double * qwts); + +GeometryInfo qpts_per_geom(const MeshQuadratureRule & qrule); +GeometryInfo qpts_per_geom(const MeshQuadratureRule & qrule, int dim); + +namespace impl { + +template < mfem::Geometry::Type geom > +uint32_t qpe(uint32_t q) { + if (geom == mfem::Geometry::SQUARE) { return q * q; } + if (geom == mfem::Geometry::CUBE) { return q * q * q; } + return q; +} + +template < mfem::Geometry::Type geom > +double integration_weight(uint32_t i, const nd::view w) { + uint32_t Q = w.shape[0]; + if constexpr (geom == mfem::Geometry::SQUARE) { + uint32_t ix = i % Q; + uint32_t iy = i / Q; + return w(ix) * w(iy); + } + if constexpr (geom == mfem::Geometry::CUBE) { + uint32_t ix = i % Q; + uint32_t iy = (i % (Q * Q)) / Q; + uint32_t iz = i / (Q * Q); + return w(ix) * w(iy) * w(iz); + } + return w(i); +} + +} + +} diff --git a/src/serac/numerics/refactor/tests/CMakeLists.txt b/src/serac/numerics/refactor/tests/CMakeLists.txt new file mode 100644 index 0000000000..c5bf6536a2 --- /dev/null +++ b/src/serac/numerics/refactor/tests/CMakeLists.txt @@ -0,0 +1,24 @@ +# Copyright (c) 2019-2024, Lawrence Livermore National Security, LLC and +# other Serac Project Developers. See the top-level LICENSE file for +# details. +# +# SPDX-License-Identifier: (BSD-3-Clause) + +set(refactor_test_dependencies serac_refactor serac_boundary_conditions gtest) + +set(refactor_serial_test_sources + h1_evaluation_tests.cpp + hcurl_evaluation_tests.cpp + + integrate_residual_H1_flux_tests.cpp + integrate_residual_H1_source_tests.cpp + integrate_residual_H1v_flux_tests.cpp + integrate_residual_Hcurl_flux_tests.cpp + integrate_residual_Hcurl_source_tests.cpp + + nodal_coordinates_and_directions_tests.cpp +) + +serac_add_tests( SOURCES ${refactor_serial_test_sources} + DEPENDS_ON ${refactor_test_dependencies} + NUM_MPI_TASKS 1) diff --git a/src/serac/numerics/refactor/tests/common.hpp b/src/serac/numerics/refactor/tests/common.hpp new file mode 100644 index 0000000000..f69e983f14 --- /dev/null +++ b/src/serac/numerics/refactor/tests/common.hpp @@ -0,0 +1,13 @@ +#pragma once + +#include "serac/mesh/mesh_utils.hpp" +#include "serac/serac_config.hpp" +#include "serac/infrastructure/initialize.hpp" +#include "serac/infrastructure/terminator.hpp" + +#define SERAC_MESH_DIR SERAC_REPO_DIR "/data/meshes/" + +mfem::ParMesh load_parmesh(std::string filename) { + mfem::Mesh mesh(filename); + return mfem::ParMesh(*serac::mesh::refineAndDistribute(std::move(mesh), 0, 0)); +} diff --git a/src/serac/numerics/refactor/tests/h1_evaluation_tests.cpp b/src/serac/numerics/refactor/tests/h1_evaluation_tests.cpp new file mode 100644 index 0000000000..3ab889e55d --- /dev/null +++ b/src/serac/numerics/refactor/tests/h1_evaluation_tests.cpp @@ -0,0 +1,137 @@ +#include + +#include +#include + +#include "serac/numerics/refactor/forall.hpp" +#include "serac/numerics/refactor/evaluate.hpp" +#include "serac/numerics/refactor/tests/common.hpp" + +using namespace refactor; + +constexpr int dimension(double) { return 1; } + +template < int dim > +constexpr int dimension(vec < dim >) { return dim; } + +template < typename grad_t, typename jac_t > +auto contravariant_piola(const grad_t & du_dxi, const jac_t & dx_dxi) { + return dot(du_dxi, inv(dx_dxi)); +}; + +template < typename vec_t > +void evaluation_test(std::string filename, + std::function f, + std::function grad_f, + int p, + double tolerance) { + + constexpr int dim = dimension(vec_t{}); + constexpr int components = 1; + + using mat_t = mat; + + mfem::ParMesh mesh = load_parmesh(SERAC_MESH_DIR + filename); + Domain domain = EntireDomain(mesh); + + Field u(mesh, refactor::Family::H1, p, components); + + mfem::FunctionCoefficient mfem_f([&](const mfem::Vector & mfem_X) { + vec_t X; + for (int i = 0; i < dim; i++) { + X[i] = mfem_X[i]; + } + return f(X); + }); + + u.project(mfem_f); + + Field X = mesh_coordinates(mesh); + + for (uint32_t q = 1; q <= 4; q++) { + + MeshQuadratureRule qrule(q); + + auto X_q = evaluate(X, domain, qrule); + auto dX_dxi_q = evaluate(grad(X), domain, qrule); + auto u_q = evaluate(u, domain, qrule); + + auto du_dxi_q = evaluate(grad(u), domain, qrule); + auto du_dX_q_2 = forall(contravariant_piola, du_dxi_q, dX_dxi_q); + + // evaluate f, df_dx directly at each quadrature point + auto f_q = forall(f, X_q); + auto df_dX_q = forall(grad_f, X_q); + + EXPECT_LT(relative_error(flatten(u_q), flatten(f_q)), tolerance); + EXPECT_LT(relative_error(du_dX_q_2, df_dX_q), tolerance); + + } + +} + +#define GENERATE_TEST_2D(NAME, mesh, p, tolerance) \ +TEST(InterpolationTest2D, NAME) { \ + evaluation_test( \ + mesh, \ + std::function< double(vec2) >([](vec2 x) { return 3 * pow(x[0], p) + 2 * x[1] - 1; }),\ + std::function< vec2(vec2) >([](vec2 x) { return vec2{3 * p * pow(x[0], p - 1), 2}; }),\ + p, \ + tolerance \ + ); \ +} + +GENERATE_TEST_2D(PatchTestTriP1, "patch2D_tris.mesh", 1, 1.0e-15); +GENERATE_TEST_2D(PatchTestTriP2, "patch2D_tris.mesh", 2, 1.0e-14); +GENERATE_TEST_2D(PatchTestTriP3, "patch2D_tris.mesh", 3, 1.5e-14); + +GENERATE_TEST_2D(PatchTestQuadP1, "patch2D_quads.mesh", 1, 1.0e-15); +GENERATE_TEST_2D(PatchTestQuadP2, "patch2D_quads.mesh", 2, 1.0e-14); +GENERATE_TEST_2D(PatchTestQuadP3, "patch2D_quads.mesh", 3, 1.0e-14); + +GENERATE_TEST_2D(PatchTestTriAndQuadP1, "patch2D_tris_and_quads.mesh", 1, 1.0e-15); +GENERATE_TEST_2D(PatchTestTriAndQuadP2, "patch2D_tris_and_quads.mesh", 2, 1.0e-14); +GENERATE_TEST_2D(PatchTestTriAndQuadP3, "patch2D_tris_and_quads.mesh", 3, 2.0e-14); + +///////////////////////////////////////////////////////////////////////////////////////////////// + +#define GENERATE_TEST_3D(NAME, mesh, p, tolerance) \ +TEST(InterpolationTest3D, NAME) { \ + evaluation_test( \ + mesh, \ + std::function< double(vec3) >([](vec3 x) { return 3 * pow(x[0], p) + 2 * x[1] + x[2]; }), \ + std::function< vec3(vec3) >([](vec3 x) { return vec3{3 * p * pow(x[0], p - 1), 2, 1}; }), \ + p, \ + tolerance \ + ); \ +} + +GENERATE_TEST_3D(PatchTestTetP1, "patch3D_tets.mesh", 1, 5.0e-16); +GENERATE_TEST_3D(PatchTestTetP2, "patch3D_tets.mesh", 2, 5.0e-15); +GENERATE_TEST_3D(PatchTestTetP3, "patch3D_tets.mesh", 3, 2.0e-14); + +GENERATE_TEST_3D(PatchTestHexP1, "patch3D_hexes.mesh", 1, 2.0e-15); +GENERATE_TEST_3D(PatchTestHexP2, "patch3D_hexes.mesh", 2, 2.0e-14); +GENERATE_TEST_3D(PatchTestHexP3, "patch3D_hexes.mesh", 3, 4.5e-13); + +GENERATE_TEST_3D(PatchTestTetAndHexP1, "patch3D_tets_and_hexes.mesh", 1, 1.5e-15); +GENERATE_TEST_3D(PatchTestTetAndHexP2, "patch3D_tets_and_hexes.mesh", 2, 1.5e-14); +GENERATE_TEST_3D(PatchTestTetAndHexP3, "patch3D_tets_and_hexes.mesh", 3, 3.5e-13); + +int main(int argc, char* argv[]) { + int num_procs, myid; + + ::testing::InitGoogleTest(&argc, argv); + + MPI_Init(&argc, &argv); + MPI_Comm_size(MPI_COMM_WORLD, &num_procs); + MPI_Comm_rank(MPI_COMM_WORLD, &myid); + + axom::slic::SimpleLogger logger; + + int result = RUN_ALL_TESTS(); + + MPI_Finalize(); + + return result; +} diff --git a/src/serac/numerics/refactor/tests/hcurl_evaluation_tests.cpp b/src/serac/numerics/refactor/tests/hcurl_evaluation_tests.cpp new file mode 100644 index 0000000000..f72fc97a6d --- /dev/null +++ b/src/serac/numerics/refactor/tests/hcurl_evaluation_tests.cpp @@ -0,0 +1,125 @@ +#include + +#include +#include + +#include "refactor/mesh.hpp" +#include "refactor/field.hpp" +#include "refactor/piola_transformations.hpp" + +#include "refactor/domain.hpp" + +#include "misc/for_constexpr.hpp" +#include "forall.hpp" + +#include "serac/numerics/functional/tensor.hpp" + + +using namespace serac; +using namespace refactor; + +template < typename vec_t, typename curl_t> +void evaluation_test(std::string filename, + std::function f, + std::function curl_f, + int p, + double tolerance) { + + constexpr int dim = dimension(vec_t{}); + + using mat_t = mat; + + auto mesh = Mesh::load(SERAC_MESH_DIR + filename); + + Field u = create_field(mesh, Family::HCURL, p); + nd::array nodes = nodes_for(u, mesh); + nd::array directions = directions_for(u, mesh); + + u = forall(std::function< double(vec_t, vec_t)> ([=](vec_t x, vec_t n){ + return dot(f(x), n); + }), nodes, directions); + + for (int q = 1; q <= 1; q++) { + + Domain domain(mesh, MeshQuadratureRule(q)); + + auto x_q = evaluate(mesh.X, domain); + auto dx_dxi_q = evaluate(grad(mesh.X), isoparametric(domain)); + + auto u_q_1 = evaluate(u, domain); + auto u_xi_q = evaluate(u, isoparametric(domain)); + auto curl_u_q_1 = evaluate(curl(u), domain); + auto curl_u_xi_q = evaluate(curl(u), isoparametric(domain)); + auto u_q_2 = forall(contravariant_piola, u_xi_q, dx_dxi_q); + auto curl_u_q_2 = forall(covariant_piola, curl_u_xi_q, dx_dxi_q); + + // evaluate f, df_dx directly at each quadrature point + auto f_q = forall(f, x_q); + auto curl_f_q = forall(curl_f, x_q); + + EXPECT_LT(relative_error(flatten(u_q_1), flatten(f_q)), tolerance); + EXPECT_LT(relative_error(u_q_2, f_q), tolerance); + EXPECT_LT(relative_error(flatten(curl_u_q_1), flatten(curl_f_q)), tolerance); + EXPECT_LT(relative_error(curl_u_q_2, curl_f_q), tolerance); + + } + +} + +#if 1 +#define GENERATE_TEST_2D(NAME, mesh, p, tolerance) \ +TEST(InterpolationTest2D, NAME) { \ + evaluation_test( \ + mesh, \ + std::function< vec2(vec2) >([](vec2 x) { return vec2{x[1], -x[0]}; }), \ + std::function< double(vec2) >([](vec2 x) { return -2; }), \ + p, \ + tolerance \ + ); \ +} + +GENERATE_TEST_2D(AffineTestQuadP1, "one_quad_pure_shear.json", 1, 1.0e-15); + +//GENERATE_TEST_2D(PatchTestQuadP1, "patch_test_quads.json", 1, 1.0e-15); +GENERATE_TEST_2D(PatchTestQuadP2, "patch_test_quads.json", 2, 1.0e-14); +GENERATE_TEST_2D(PatchTestQuadP3, "patch_test_quads.json", 3, 1.0e-14); + +GENERATE_TEST_2D(HcurlPatchTestTriP1, "patch_test_tris.json", 1, 1.0e-15); +GENERATE_TEST_2D(HcurlPatchTestTriP2, "patch_test_tris.json", 2, 1.0e-14); +GENERATE_TEST_2D(HcurlPatchTestTriP3, "patch_test_tris.json", 3, 1.5e-14); + +//GENERATE_TEST_2D(PatchTestTriAndQuadP1, "patch_test_tris_and_quads.json", 1, 1.0e-15); +GENERATE_TEST_2D(PatchTestTriAndQuadP2, "patch_test_tris_and_quads.json", 2, 1.0e-14); +GENERATE_TEST_2D(PatchTestTriAndQuadP3, "patch_test_tris_and_quads.json", 3, 2.0e-14); + +GENERATE_TEST_2D(WrenchTestP1, "wrench.json", 1, 1.0e-12); +GENERATE_TEST_2D(WrenchTestP2, "wrench.json", 2, 1.0e-12); +GENERATE_TEST_2D(WrenchTestP3, "wrench.json", 3, 1.0e-12); +#endif + +///////////////////////////////////////////////////////////////////////////////////////////////// + +#define GENERATE_TEST_3D(NAME, mesh, p, tolerance) \ +TEST(InterpolationTest3D, NAME) { \ + evaluation_test( \ + mesh, \ + std::function< vec3(vec3) >([](vec3 x) { return vec3{1 + 2*x[1], 3 - 2*x[0], 4}; }), \ + std::function< vec3(vec3) >([](vec3 x) { return vec3{0, 0, -4}; }), \ + p, \ + tolerance \ + ); \ +} + +GENERATE_TEST_3D(PatchTestHexesP1, "one_hex.json", 1, 2.0e-15); + +//GENERATE_TEST_3D(PatchTestHexP1, "patch_test_hexes.json", 1, 2.0e-15); +GENERATE_TEST_3D(PatchTestHexP2, "patch_test_hexes.json", 2, 2.0e-14); +GENERATE_TEST_3D(PatchTestHexP3, "patch_test_hexes.json", 3, 4.5e-13); + +GENERATE_TEST_3D(PatchTestTetP1, "patch_test_tets.json", 1, 3.5e-16); +GENERATE_TEST_3D(PatchTestTetP2, "patch_test_tets.json", 2, 5.0e-15); +GENERATE_TEST_3D(PatchTestTetP3, "patch_test_tets.json", 3, 2.0e-14); + +//GENERATE_TEST_3D(PatchTestTetAndHexP1, "patch_test_tets_and_hexes.json", 1, 1.5e-15); +GENERATE_TEST_3D(PatchTestTetAndHexP2, "patch_test_tets_and_hexes.json", 2, 1.5e-14); +GENERATE_TEST_3D(PatchTestTetAndHexP3, "patch_test_tets_and_hexes.json", 3, 3.5e-13); diff --git a/src/serac/numerics/refactor/tests/integrate_residual_H1_flux_tests.cpp b/src/serac/numerics/refactor/tests/integrate_residual_H1_flux_tests.cpp new file mode 100644 index 0000000000..38f96eadf2 --- /dev/null +++ b/src/serac/numerics/refactor/tests/integrate_residual_H1_flux_tests.cpp @@ -0,0 +1,146 @@ +#include + +#include +#include +#include + +#include "serac/numerics/refactor/forall.hpp" +#include "serac/numerics/refactor/evaluate.hpp" +#include "serac/numerics/refactor/tests/common.hpp" + +using namespace serac; +using namespace refactor; + +// ---------------------------------------------------------------------------- + +template < typename vec_t > +void flux_test(std::string filename, + std::function< double(vec_t, int) > f, + std::function< vec_t(vec_t) > g, + std::function< double(int) > answer, + double tolerance) { + + constexpr int components = 1; + constexpr int dim = size(vec_t{}); + using mat_t = decltype(outer(vec_t{}, vec_t{})); + + mfem::ParMesh mesh = load_parmesh(SERAC_MESH_DIR + filename); + Domain domain = EntireDomain(mesh); + + Field X = mesh_coordinates(mesh); + + // evaluate g at each quadrature point + std::function< vec_t(vec_t, mat_t) > g_xi = [g](vec_t x, mat_t J) { + return dot(serac::inv(J), g(x)) * det(J); + }; + + for (int p = 1; p < 4; p++) { + + std::function< double(vec_t) > f_p = [f, p](vec_t x) { return f(x, p); }; + + Field u(mesh, refactor::Family::H1, p, components); + + mfem::FunctionCoefficient mfem_f([&](const mfem::Vector & mfem_X) { + vec_t X; + if constexpr (dim == 1) { + X = mfem_X[0]; + } else { + for (int i = 0; i < dim; i++) { + X[i] = mfem_X[i]; + } + } + return f(X, p); + }); + + u.project(mfem_f); + + BasisFunction phi(u); + + for (int q = p + 1; q < 5; q++) { + + MeshQuadratureRule qrule(static_cast(q)); + + auto X_q = evaluate(X, domain, qrule); + auto dX_dxi_q = evaluate(grad(X), domain, qrule); + + auto g_q = forall(g, X_q); + auto g_xi_q = forall(g_xi, X_q, dX_dxi_q); + + Residual r = integrate(dot(g_q, grad(phi)), domain, qrule); + + SCOPED_TRACE("p = " + std::to_string(p) + ", q = " + std::to_string(q)); + EXPECT_NEAR(dot(r, u), answer(p), tolerance); + + } + } + +} + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[x_] := x^p + 3; + gradf[x_] := p x^(p-1); + g[x_] := x; + Integrate[gradf[x] g[x], {x, 0, 1}] + + -------------------- + + Out[] := + 1/2 +*/ + +//std::function f3([](double x, int p){ return pow(x, p); }); +//std::function g3([](double x){ return x; }); +//std::function answer3([](int p){ return double(p) / double(1 + p); }); +// +//TEST(IntegrateTest, FluxH1Edges) { flux_test("patch_test_edges.json", f3, g3, answer3, 3.0e-15); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_}] := x^p - y + 3; + gradf[{x_, y_}] := {p x^(-1 + p), -1}; + g[{x_, y_}] := {y, -x}; + Integrate[gradf[{x, y}] . g[{x, y}], {x, y} \[Element] Rectangle[{0, 0}, {1, 1}]] + + -------------------- + + Out[] := + 1 +*/ + +std::function f4([](vec2 x, int p){ return pow(x[0], p) - x[1] + 3.0; }); +std::function g4([](vec2 x){ return vec2{x[1], -x[0]}; }); +std::function answer4([](int){ return 1.0; }); + +TEST(IntegrateTest, FluxH1Tris) { flux_test("patch_test_tris.json", f4, g4, answer4, 5.0e-15); } +TEST(IntegrateTest, FluxH1Quads) { flux_test("patch_test_quads.json", f4, g4, answer4, 5.0e-15); } +TEST(IntegrateTest, FluxH1Both) { flux_test("patch_test_tris_and_quads.json", f4, g4, answer4, 5.0e-15); } +TEST(IntegrateTest, FluxH1TrisFine) { flux_test("unit_square_of_tris_fine.json", f4, g4, answer4, 8.0e-14); } +TEST(IntegrateTest, FluxH1QuadsFine) { flux_test("unit_square_of_quads_fine.json", f4, g4, answer4, 8.0e-14); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_, z_}] := x^p - y - 2 z + 3; + gradf[{x_, y_, z_}] := {p x^(-1 + p), -1, -2}; + g[{x_, y_, z_}] := {z, x, -y}; + Integrate[gradf[{x, y, z}] . g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {1, 1, 1}]] + + -------------------- + + Out[] := + 1 +*/ +std::function f5([](vec3 x, int p){ return pow(x[0], p) - x[1] - 2 * x[2] + 3.0; }); +std::function g5([](vec3 x){ return vec3{x[2], x[0], -x[1]}; }); +std::function answer5([](int){ return 1.0; }); + +TEST(IntegrateTest, FluxH1Tets) { flux_test("patch_test_tets.json", f5, g5, answer5, 5.0e-15); } +TEST(IntegrateTest, FluxH1Hexes) { flux_test("patch_test_hexes.json", f5, g5, answer5, 5.0e-15); } +TEST(IntegrateTest, FluxH1TetsFine) { flux_test("unit_cube_of_tets_fine.json", f5, g5, answer5, 5.0e-14); } +TEST(IntegrateTest, FluxH1HexesFine) { flux_test("unit_cube_of_hexes_fine.json", f5, g5, answer5, 5.0e-15); } diff --git a/src/serac/numerics/refactor/tests/integrate_residual_H1_source_tests.cpp b/src/serac/numerics/refactor/tests/integrate_residual_H1_source_tests.cpp new file mode 100644 index 0000000000..0c32287ee9 --- /dev/null +++ b/src/serac/numerics/refactor/tests/integrate_residual_H1_source_tests.cpp @@ -0,0 +1,131 @@ +#include + +#include +#include +#include + +#include "refactor/mesh.hpp" +#include "refactor/domain.hpp" + +#include + +#include "forall.hpp" +#include "serac/numerics/functional/tensor.hpp" + +#include "containers/ndarray_conversions.hpp" + +using namespace refactor; + +// ---------------------------------------------------------------------------- + +template < typename vecd > +void integrate_source_test(std::string filename, + std::function< double(vecd, int) > f, + std::function< double(vecd) > g, + std::function< double(int) > answer, + double tolerance) { + + using matd = decltype(outer(vecd{}, vecd{})); + + auto mesh = Mesh::load(SERAC_MESH_DIR + filename); + + std::cout << std::setprecision(15); + + // evaluate g at each quadrature point + std::function< double(vecd, matd) > g_detJ = [g](vecd x, matd J) { + return g(x) * det(J); + }; + + for (int p = 1; p < 4; p++) { + + std::function< double(vecd) > f_p = [f, p](vecd x) { return f(x,p); }; + + Field u = create_field(mesh, Family::H1, p, 1); + nd::array nodes = nodes_for(u, mesh); + u = forall(f_p, nodes); + + BasisFunction phi(u); + + for (int q = p + 1; q < 5; q++) { + + Domain domain(mesh, MeshQuadratureRule(q)); + + auto x_q = evaluate(mesh.X, domain); + auto dx_dxi_q = evaluate(grad(mesh.X), isoparametric(domain)); + + auto g_q = forall(g, x_q); + auto g_detJ_q = forall(g_detJ, x_q, dx_dxi_q); + + Residual r1 = integrate(g_q * phi, domain); + Residual r2 = integrate(g_detJ_q * phi, isoparametric(domain)); + + SCOPED_TRACE("p = " + std::to_string(p) + ", q = " + std::to_string(q)); + EXPECT_NEAR(dot(r1, u), answer(p), tolerance); + EXPECT_NEAR(dot(r2, u), answer(p), tolerance); + + } + } + +} + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[x_] := x^p + 3; + g[x_] := x; + Integrate[f[x] g[x], {x, 0, 1}] + + -------------------- + + Out[] := + (3.0/2.0) + 1.0 / (2.0 + p) +*/ +std::function f0([](double x, int p){ return pow(x, p) + 3.0; }); +std::function g0([](double x){ return x; }); +std::function answer0([](int p){ return 1.5 + 1.0 / (2 + p); }); + +TEST(IntegrateTest, SourceH1Edge) { integrate_source_test("patch_test_edges.json", f0, g0, answer0, 3.0e-2); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_}] := x^p - y + 3; + g[{x_, y_}] := y; + Integrate[f[{x, y}] g[{x, y}], {x, y} \[Element] Rectangle[{0, 0}, {1, 1}]] + + -------------------- + + Out[] := + (7.0/6.0) + 1.0 /(2.0 + 2.0 * p) +*/ +std::function f1([](vec2 x, int p){ return pow(x[0], p) - x[1] + 3.0; }); +std::function g1([](vec2 x){ return x[1]; }); +std::function answer1([](int p){ return (7.0/6.0) + 1.0 /(2.0 + 2.0 * p); }); + +TEST(IntegrateTest, SourceH1Tris) { integrate_source_test("patch_test_tris.json", f1, g1, answer1, 3.0e-15); } +TEST(IntegrateTest, SourceH1Quads) { integrate_source_test("patch_test_quads.json", f1, g1, answer1, 1.0e-15); } +TEST(IntegrateTest, SourceH1Both) { integrate_source_test("patch_test_tris_and_quads.json", f1, g1, answer1, 1.0e-15); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_, z_}] := x^p - y - z + 3; + g[{x_, y_, z_}] := 1; + Integrate[f[{x, y, z}] g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {1, 1, 1}]] + + -------------------- + + Out[] := + 2.0 + 1.0 / (1.0 + p) +*/ +std::function f2([](vec3 x, int p){ return pow(x[0], p) - x[1] - x[2] + 3.0; }); +std::function g2([](vec3 x){ return 1.0; }); +std::function answer2([](int p){ return 2.0 + 1.0 / (1.0 + p); }); + +TEST(IntegrateTest, SourceH1Tets) { integrate_source_test("patch_test_tets.json", f2, g2, answer2, 7.0e-15); } +TEST(IntegrateTest, SourceH1Hexes) { integrate_source_test("patch_test_hexes.json", f2, g2, answer2, 1.0e-15); } +TEST(IntegrateTest, SourceH1TetsFine) { integrate_source_test("unit_cube_of_tets_fine.json", f2, g2, answer2, 5.0e-14); } +TEST(IntegrateTest, SourceH1HexesFine) { integrate_source_test("unit_cube_of_hexes_fine.json", f2, g2, answer2, 2.0e-14); } diff --git a/src/serac/numerics/refactor/tests/integrate_residual_H1v_flux_tests.cpp b/src/serac/numerics/refactor/tests/integrate_residual_H1v_flux_tests.cpp new file mode 100644 index 0000000000..052cff750f --- /dev/null +++ b/src/serac/numerics/refactor/tests/integrate_residual_H1v_flux_tests.cpp @@ -0,0 +1,131 @@ +#include + +#include +#include +#include + +#include "refactor/mesh.hpp" +#include "refactor/domain.hpp" + +#include + +#include "forall.hpp" +#include "serac/numerics/functional/tensor.hpp" + +#include "containers/ndarray_conversions.hpp" + +using namespace refactor; + +// ---------------------------------------------------------------------------- + +template < typename vecd > +void flux_test(std::string filename, + std::function< double(vecd, int) > f, + std::function< vecd(vecd) > g, + std::function< double(int) > answer, + double tolerance) { + + constexpr int dim = dimension(vecd{}); + + double scale_factor = (dim == 2) ? 5.0 : 14.0; + + using matd = decltype(outer(vecd{}, vecd{})); + + auto mesh = Mesh::load(SERAC_MESH_DIR + filename); + + // evaluate g at each quadrature point + std::function< matd(vecd, matd) > qf = [g](vecd x, matd J) { + matd output{}; + for (int i = 0; i < dim; i++) { + output[i] = dot(inv(J), g(x)) * det(J) * (i + 1); + } + return output; + }; + + for (int p = 1; p < 4; p++) { + + std::function< vecd(vecd) > f_p = [f, p](vecd x) { + vecd output; + for (int i = 0; i < dim; i++) { + output[i] = f(x, p) * (i + 1); + } + return output; + }; + + Field u = create_field(mesh, Family::H1, p, dim); + nd::array nodes = nodes_for(u, mesh); + u = forall(f_p, nodes); + + BasisFunction phi(u); + + for (int q = p + 1; q < 5; q++) { + + Domain domain(mesh, MeshQuadratureRule(q)); + + auto x_q = evaluate(mesh.X, domain); + auto dx_dxi_q = evaluate(grad(mesh.X), isoparametric(domain)); + + auto g_q = forall(qf, x_q, dx_dxi_q); + + Residual r = integrate(dot(g_q, grad(phi)), isoparametric(domain)); + + SCOPED_TRACE("p = " + std::to_string(p) + ", q = " + std::to_string(q)); + EXPECT_NEAR(dot(r, u), scale_factor * answer(p), tolerance); + + } + } + +} + +// ---------------------------------------------------------------------------- + +// note: edge element tests omitted, since they are 1D elements so this test would +// just duplicate what is already in integrate_H1_flux_tests.cpp + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_}] := x^p - y + 3; + gradf[{x_, y_}] := {p x^(-1 + p), -1}; + g[{x_, y_}] := {y, -x}; + Integrate[gradf[{x, y}] . g[{x, y}], {x, y} \[Element] Rectangle[{0, 0}, {1, 1}]] + + -------------------- + + Out[] := + 1 +*/ + +std::function f4([](vec2 x, int p){ return pow(x[0], p) - x[1] + 3.0; }); +std::function g4([](vec2 x){ return vec2{x[1], -x[0]}; }); +std::function answer4([](int){ return 1.0; }); + +TEST(IntegrateTest, FluxH1Tris) { flux_test("patch_test_tris.json", f4, g4, answer4, 5.0e-14); } +TEST(IntegrateTest, FluxH1Quads) { flux_test("patch_test_quads.json", f4, g4, answer4, 5.0e-14); } +TEST(IntegrateTest, FluxH1Both) { flux_test("patch_test_tris_and_quads.json", f4, g4, answer4, 5.0e-14); } +TEST(IntegrateTest, FluxH1TrisFine) { flux_test("unit_square_of_tris_fine.json", f4, g4, answer4, 8.0e-13); } +TEST(IntegrateTest, FluxH1QuadsFine) { flux_test("unit_square_of_quads_fine.json", f4, g4, answer4, 8.0e-13); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_, z_}] := x^p - y - 2 z + 3; + gradf[{x_, y_, z_}] := {p x^(-1 + p), -1, -2}; + g[{x_, y_, z_}] := {z, x, -y}; + Integrate[gradf[{x, y, z}] . g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {1, 1, 1}]] + + -------------------- + + Out[] := + 1 +*/ +std::function f5([](vec3 x, int p){ return pow(x[0], p) - x[1] - 2 * x[2] + 3.0; }); +std::function g5([](vec3 x){ return vec3{x[2], x[0], -x[1]}; }); +std::function answer5([](int){ return 1.0; }); + +TEST(IntegrateTest, FluxH1Tets) { flux_test("patch_test_tets.json", f5, g5, answer5, 1.0e-13); } +TEST(IntegrateTest, FluxH1Hexes) { flux_test("patch_test_hexes.json", f5, g5, answer5, 1.0e-13); } +TEST(IntegrateTest, FluxH1TetsFine) { flux_test("unit_cube_of_tets_fine.json", f5, g5, answer5, 1.0e-13); } +TEST(IntegrateTest, FluxH1HexesFine) { flux_test("unit_cube_of_hexes_fine.json", f5, g5, answer5, 1.0e-13); } diff --git a/src/serac/numerics/refactor/tests/integrate_residual_Hcurl_flux_tests.cpp b/src/serac/numerics/refactor/tests/integrate_residual_Hcurl_flux_tests.cpp new file mode 100644 index 0000000000..f3a39cf5fc --- /dev/null +++ b/src/serac/numerics/refactor/tests/integrate_residual_Hcurl_flux_tests.cpp @@ -0,0 +1,135 @@ +#include + +#include +#include +#include + +#include "refactor/mesh.hpp" +#include "refactor/domain.hpp" + +#include + +#include "forall.hpp" +#include "serac/numerics/functional/tensor.hpp" + +#include "containers/ndarray_conversions.hpp" + +using namespace refactor; + +// ---------------------------------------------------------------------------- + +template < typename vec_t, typename curl_t > +void integrate_flux_test(std::string filename, + std::function< vec_t(vec_t, int) > f, + std::function< curl_t(vec_t) > g, + std::function< double(int) > answer, + double tolerance) { + + using mat_t = decltype(outer(vec_t{}, vec_t{})); + + auto mesh = Mesh::load(SERAC_MESH_DIR + filename); + + std::cout << std::setprecision(15); + + // evaluate g at each quadrature point + std::function< curl_t(vec_t, mat_t) > g_xi = [g](vec_t x, mat_t J) { + // note: detJ cancels out here, since it appears in the numerator from + // the change of coordinates, but also in the denominator from the covariant piola + if constexpr (std::is_same< mat_t, mat2 >::value) { + return g(x); + } else { + return dot(transpose(J), g(x)); + } + }; + + for (int p = 1; p < 4; p++) { + + std::function< double(vec_t, vec_t) > f_p = [f, p](vec_t x, vec_t n) { + return dot(f(x,p), n) ; + }; + + Field u = create_field(mesh, Family::HCURL, p, 1); + nd::array nodes = nodes_for(u, mesh); + nd::array directions = directions_for(u, mesh); + u = forall(f_p, nodes, directions); + + BasisFunction phi(u); + + for (int q = p + 1; q < 5; q++) { + + Domain domain(mesh, MeshQuadratureRule(q)); + + auto x_q = evaluate(mesh.X, domain); + auto dx_dxi_q = evaluate(grad(mesh.X), isoparametric(domain)); + + nd::array g_q = forall(g, x_q); + nd::array g_xi_q = forall(g_xi, x_q, dx_dxi_q); + + Residual r1 = integrate(dot(g_q, curl(phi)), domain); + Residual r2 = integrate(dot(g_xi_q, curl(phi)), isoparametric(domain)); + + SCOPED_TRACE("p = " + std::to_string(p) + ", q = " + std::to_string(q)); + EXPECT_NEAR(dot(r1, u), answer(p), tolerance); + EXPECT_NEAR(dot(r2, u), answer(p), tolerance); + + } + } + +} + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_}] := {3 + y, 2 - x}; + g[{x_, y_}] := x + y; + Integrate[Curl[f[{x, y}], {x, y}] g[{x, y}], {x, y} \[Element] Rectangle[{0, 0}, {1, 1}]] + + -------------------- + + Out[] := + -2.0 +*/ +std::function f1([](vec2 x, int p){ return vec2{3 + x[1], 2 - x[0]}; }); +std::function g1([](vec2 x){ return x[0] + x[1]; }); +std::function answer1([](int p){ return -2.0; }); + +// note: non affinely-transformed low-order quadrilateral elements can't exactly reproduce the +// functions in this test, so for p=1 those tests have some small finite error +// which decreases with mesh refinement +TEST(IntegrateTest, FluxHcurlTris) { integrate_flux_test("patch_test_tris.json", f1, g1, answer1, 5.0e-14); } +TEST(IntegrateTest, FluxHcurlQuads) { integrate_flux_test("patch_test_quads.json", f1, g1, answer1, 1.0e-2); } +TEST(IntegrateTest, FluxHcurlQuadsFine) { integrate_flux_test("unit_square_of_quads_fine.json", f1, g1, answer1, 1.0e-5); } +TEST(IntegrateTest, FluxHcurlBoth) { integrate_flux_test("patch_test_tris_and_quads.json", f1, g1, answer1, 1.0e-3); } +TEST(IntegrateTest, FluxHcurlTrisFine) { integrate_flux_test("unit_square_of_tris_fine.json", f1, g1, answer1, 1.5e-13); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_, z_}] := {y + 3, 2 - x - z, 1 + y}; + g[{x_, y_, z_}] := {y, z, 2 x}; + Integrate[Curl[f[{x, y, z}], {x, y, z}] g[{x, y, z}], {x, y, z} \[Element] Tetrahedron[{{0, 0, 0}, {1, 0, 0}, {0, 1, 0}, {0, 0, 1}}]] + Integrate[Curl[f[{x, y, z}], {x, y, z}] g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {1, 1, 1}]] + Integrate[Curl[f[{x, y, z}], {x, y, z}] g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {2, 1, 1}]] + + -------------------- + + Out[] := + -1.0 / 12.0 + -1.0 + -6.0 +*/ +std::function< vec3(vec3, int) > f2([](vec3 x, int p) { return vec3{3 + x[1], 2 - x[0] - x[2], 1 + x[1]}; }); +std::function< vec3(vec3) > g2([](vec3 x) { return vec3{x[1], x[2], 2 * x[0]}; }); +std::function< double(int)> answer2([](int p){ return -1.0 / 12.0; }); +std::function< double(int)> answer3([](int p){ return -1.0; }); +std::function< double(int)> answer4([](int p){ return -6.0; }); + +TEST(IntegrateTest, FluxHcurlOneTet) { integrate_flux_test("one_tet.json", f2, g2, answer2, 1.0e-13); } +TEST(IntegrateTest, FluxHcurlOneHex) { integrate_flux_test("one_hex.json", f2, g2, answer3, 1.0e-13); } + +TEST(IntegrateTest, FluxHcurlTets) { integrate_flux_test("patch_test_tets.json", f2, g2, answer3, 1.0e-13); } +TEST(IntegrateTest, FluxHcurlHexes) { integrate_flux_test("patch_test_hexes.json", f2, g2, answer3, 1.0e-1); } +TEST(IntegrateTest, FluxHcurlHexesFine) { integrate_flux_test("unit_cube_of_hexes_fine.json", f2, g2, answer3, 5.0e-4); } +TEST(IntegrateTest, FluxHcurlTetsAndHexes) { integrate_flux_test("patch_test_tets_and_hexes.json", f2, g2, answer4, 1.0e-1); } diff --git a/src/serac/numerics/refactor/tests/integrate_residual_Hcurl_source_tests.cpp b/src/serac/numerics/refactor/tests/integrate_residual_Hcurl_source_tests.cpp new file mode 100644 index 0000000000..fbfca4b6a8 --- /dev/null +++ b/src/serac/numerics/refactor/tests/integrate_residual_Hcurl_source_tests.cpp @@ -0,0 +1,143 @@ +#include + +#include +#include +#include + +#include "refactor/mesh.hpp" +#include "refactor/domain.hpp" + +#include + +#include "forall.hpp" +#include "serac/numerics/functional/tensor.hpp" + +#include "containers/ndarray_conversions.hpp" + +using namespace refactor; + +// ---------------------------------------------------------------------------- + +template < typename vecd > +void integrate_source_test(std::string filename, + std::function< vecd(vecd, int) > f, + std::function< vecd(vecd) > g, + std::function< double(int) > answer, + double tolerance) { + + using matd = decltype(outer(vecd{}, vecd{})); + + auto mesh = Mesh::load(SERAC_MESH_DIR + filename); + + std::cout << std::setprecision(15); + + // evaluate g at each quadrature point + std::function< vecd(vecd, matd) > g_xi = [g](vecd x, matd J) { + return dot(inv(J), g(x)) * det(J); + }; + + for (int p = 1; p < 4; p++) { + + std::function< double(vecd, vecd) > f_p = [f, p](vecd x, vecd n) { return dot(f(x,p), n) ; }; + + Field u = create_field(mesh, Family::HCURL, p, 1); + nd::array nodes = nodes_for(u, mesh); + nd::array directions = directions_for(u, mesh); + u = forall(f_p, nodes, directions); + + BasisFunction phi(u); + + for (int q = p + 1; q < 5; q++) { + + Domain domain(mesh, MeshQuadratureRule(q)); + + auto x_q = evaluate(mesh.X, domain); + auto dx_dxi_q = evaluate(grad(mesh.X), isoparametric(domain)); + + nd::array g_q = forall(g, x_q); + nd::array g_xi_q = forall(g_xi, x_q, dx_dxi_q); + + Residual r1 = integrate(g_q * phi, domain); + Residual r2 = integrate(g_xi_q * phi, isoparametric(domain)); + + SCOPED_TRACE("p = " + std::to_string(p) + ", q = " + std::to_string(q)); + EXPECT_NEAR(dot(r1, u), answer(p), tolerance); + EXPECT_NEAR(dot(r2, u), answer(p), tolerance); + + EXPECT_NEAR(relative_error(r1.data, r2.data), 0.0, 1.0e-14); + + } + } + +} + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_}] := {1, 3}; + g[{x_, y_}] := {1 + y, 2 - x}; + Integrate[f[{x, y}] . g[{x, y}], {x, y} \[Element] Rectangle[{0, 0}, {1, 1}]] + + -------------------- + + Out[] := + 6.0 +*/ +std::function f1([](vec2 x, int p){ return vec2{1, 3}; }); +std::function g1([](vec2 x){ return vec2{1 + x[1], 2 - x[0]}; }); +std::function answer1([](int p){ return 6.0; }); +TEST(IntegrateTest, SourceHcurlTris) { integrate_source_test("patch_test_tris.json", f1, g1, answer1, 1.5e-14); } +TEST(IntegrateTest, SourceHcurlQuads) { integrate_source_test("patch_test_quads.json", f1, g1, answer1, 1.0e-14); } +TEST(IntegrateTest, SourceHcurlBoth) { integrate_source_test("patch_test_tris_and_quads.json", f1, g1, answer1, 1.0e-14); } + +/* + In[] := + f[{x_, y_}] := {1 + 2 y, 3 - 2 x}; + g[{x_, y_}] := {2, 3}; + Integrate[f[{x, y}] . g[{x, y}], {x, y} \[Element] Triangle[{{0, 0}, {1, 0}, {0, 1}}]] + Integrate[f[{x, y}] . g[{x, y}], {x, y} \[Element] Triangle[{{0, 0}, {1, 0}, {1, 1}}]] + + -------------------- + + Out[] := + 31.0 / 6.0 + 25.0 / 6.0 +*/ +std::function f2([](vec2 x, int p){ return vec2{1 + 2 * x[1], 3 - 2 * x[0]}; }); +std::function g2([](vec2 x){ return vec2{2.0, 3.0}; }); +std::function answer2([](int p){ return 31.0 / 6.0; }); +std::function answer3([](int p){ return 25.0 / 6.0; }); +TEST(IntegrateTest, SourceHcurlOneTri) { integrate_source_test("one_tri.json", f2, g2, answer2, 3.0e-14); } +TEST(IntegrateTest, SourceHcurlOneTriRotated) { integrate_source_test("one_tri_rotated.json", f2, g2, answer2, 3.0e-14); } +TEST(IntegrateTest, SourceHcurlOneTriSheared) { integrate_source_test("one_tri_sheared.json", f2, g2, answer3, 3.0e-14); } + +// ---------------------------------------------------------------------------- + +/* + In[] := + f[{x_, y_, z_}] := {1, 2, 3}; + g[{x_, y_, z_}] := {2, 2, 4}; + Integrate[f[{x, y, z}] . g[{x, y, z}], {x, y, z} \[Element] Tetrahedron[{{0, 0, 0}, {1, 0, 0}, {0, 1, 0}, {0, 0, 1}}]] + Integrate[f[{x, y, z}] . g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {1, 1, 1}]] + Integrate[f[{x, y, z}] . g[{x, y, z}], {x, y, z} \[Element] Cuboid[{0, 0, 0}, {2, 1, 1}]] + + -------------------- + + Out[] := + 3 + 18 + 36 +*/ +std::function< vec3(vec3, int) > f3([](vec3 x, int p) { return vec3{1, 2, 3}; }); +std::function< vec3(vec3) > g3([](vec3 x) { return vec3{2, 2, 4}; }); +std::function answer4([](int p){ return 3.0; }); +std::function answer5([](int p){ return 18.0; }); +std::function answer6([](int p){ return 36.0; }); + +TEST(IntegrateTest, SourceHcurlOneTet) { integrate_source_test("one_tet.json", f3, g3, answer4, 1.0e-13); } +TEST(IntegrateTest, SourceHcurlOneHex) { integrate_source_test("one_hex.json", f3, g3, answer5, 1.0e-13); } + +TEST(IntegrateTest, SourceHcurlTets) { integrate_source_test("patch_test_tets.json", f3, g3, answer5, 1.0e-13); } +TEST(IntegrateTest, SourceHcurlHexes) { integrate_source_test("patch_test_hexes.json", f3, g3, answer5, 1.0e-13); } +TEST(IntegrateTest, SourceHcurlTetsAndHexes) { integrate_source_test("patch_test_tets_and_hexes.json", f3, g3, answer6, 1.0e-13); } diff --git a/src/serac/numerics/refactor/tests/nodal_coordinates_and_directions_tests.cpp b/src/serac/numerics/refactor/tests/nodal_coordinates_and_directions_tests.cpp new file mode 100644 index 0000000000..f381eabf1d --- /dev/null +++ b/src/serac/numerics/refactor/tests/nodal_coordinates_and_directions_tests.cpp @@ -0,0 +1,51 @@ +#include + +#include +#include + +#include "serac/numerics/refactor/evaluate.hpp" +#include "serac/numerics/refactor/tests/common.hpp" + +using namespace refactor; + +template< int dim, int p > +void nodal_coordinates_test(std::string mesh_filename) { + + std::function< double(tensor) > f; + + mfem::ParMesh pmesh = load_parmesh(SERAC_MESH_DIR + mesh_filename); + + serac::FiniteElementState u(pmesh, H1

{}); + + nd::array nodal_coords = get_nodal_coordinates(u); + uint32_t num_nodes = nodal_coords.shape[0]; + + //void FiniteElementState::project(mfem::Coefficient& coef, const Domain& domain) + + mfem::FunctionCoefficient mfem_func([](mfem::Vector x, double /*t*/) { + return x[0] + 2 * x[1]; + }); + + u.project(mfem_func); + + std::cout << u.Size() << std::endl; + std::cout << num_nodes << std::endl; + + //for (uint32_t i = 0; i < num_nodes; i++) { + // std::cout << u[i] + //} + +} + +TEST(nodal_coords, triangles) { nodal_coordinates_test<2, 1>("patch2D_tris.mesh"); } + +int main(int argc, char* argv[]) +{ + testing::InitGoogleTest(&argc, argv); + + serac::initialize(argc, argv); + + int result = RUN_ALL_TESTS(); + + serac::exitGracefully(result); +} diff --git a/src/serac/numerics/refactor/type_traits.hpp b/src/serac/numerics/refactor/type_traits.hpp new file mode 100644 index 0000000000..fc5d944de4 --- /dev/null +++ b/src/serac/numerics/refactor/type_traits.hpp @@ -0,0 +1,70 @@ +#pragma once + +#include + +#include "serac/numerics/refactor/containers/ndarray.hpp" + +namespace refactor { + +template < typename T > +struct always_true { + static constexpr bool value = true; +}; + +//////////////////////////////////////////////////////////////////////////////// + +template < typename T > +struct is_a_1D_ndarray { + static constexpr bool value = false; +}; + +template < typename T > +struct is_a_1D_ndarray < nd::array< T, 1 > >{ + static constexpr bool value = true; +}; + +template < typename T > +struct is_a_1D_ndview { + static constexpr bool value = false; +}; + +template < typename T > +struct is_a_1D_ndview < nd::view< T, 1 > >{ + static constexpr bool value = true; +}; + +template < typename T > +struct is_ndarray { + static constexpr bool value = false; +}; + +template < typename T, uint32_t n > +struct is_ndarray< nd::array > { + static constexpr bool value = true; +}; + +//////////////////////////////////////////////////////////////////////////////// + +template < typename T > +struct is_a_function_pointer { + static constexpr bool value = false; +}; + +template < typename return_type, typename ... argument_types > +struct is_a_function_pointer < return_type (*)(argument_types ...) >{ + static constexpr bool value = true; +}; + +template < typename T > +struct is_a_stdfunction { + static constexpr bool value = false; +}; + +template < typename return_type, typename ... argument_types > +struct is_a_stdfunction < std::function< return_type(argument_types ...) > >{ + static constexpr bool value = true; +}; + +//////////////////////////////////////////////////////////////////////////////// + +} \ No newline at end of file diff --git a/src/serac/physics/boundary_conditions/boundary_conditions.hpp b/src/serac/physics/boundary_conditions/boundary_conditions.hpp new file mode 100644 index 0000000000..f25abe93b9 --- /dev/null +++ b/src/serac/physics/boundary_conditions/boundary_conditions.hpp @@ -0,0 +1,22 @@ +#include +#include + +#include "serac/numerics/functional/tensor.hpp" + +struct BC { + + BC(std::function< double(vec3, t) > f, Domain domain, mfem::FiniteElementSpace & fes) { + + } + + void evaluate(mfem::Vector & v, double t) { + + } + + mfem::Array< int > dof_ids; + + bool is_vector_valued; + std::unique_ptr< mfem::Coefficient > func; + std::unique_ptr< mfem::VectorCoefficient > vfunc; + +}; diff --git a/src/serac/physics/state/CMakeLists.txt b/src/serac/physics/state/CMakeLists.txt index 863df13db3..5475745977 100644 --- a/src/serac/physics/state/CMakeLists.txt +++ b/src/serac/physics/state/CMakeLists.txt @@ -12,8 +12,9 @@ set(state_headers ) set(state_sources - finite_element_vector.cpp + finite_element_dual.cpp finite_element_state.cpp + finite_element_vector.cpp state_manager.cpp ) diff --git a/src/serac/physics/state/finite_element_dual.cpp b/src/serac/physics/state/finite_element_dual.cpp new file mode 100644 index 0000000000..294fb463ce --- /dev/null +++ b/src/serac/physics/state/finite_element_dual.cpp @@ -0,0 +1,27 @@ +#include "serac/physics/state/finite_element_dual.hpp" + +namespace refactor { + +Family get_family(const Residual & r) { + switch(r.linearForm().FESpace()->FEColl()->GetContType()) { + case mfem::FiniteElementCollection::CONTINUOUS: return Family::H1; + case mfem::FiniteElementCollection::TANGENTIAL: return Family::HCURL; + case mfem::FiniteElementCollection::NORMAL: return Family::HDIV; + case mfem::FiniteElementCollection::DISCONTINUOUS: return Family::L2; + } + return Family::H1; // unreachable +} + +uint32_t get_degree(const Residual & r) { + return uint32_t(r.linearForm().FESpace()->FEColl()->GetOrder()); +} + +uint32_t get_num_component(const Residual & r) { + return uint32_t(r.linearForm().ParFESpace()->GetVDim()); +} + +uint32_t get_num_nodes(const Residual & r) { + return uint32_t(r.linearForm().FESpace()->GetNDofs()); +} + +} diff --git a/src/serac/physics/state/finite_element_dual.hpp b/src/serac/physics/state/finite_element_dual.hpp index 8b144b5a05..af7aa89082 100644 --- a/src/serac/physics/state/finite_element_dual.hpp +++ b/src/serac/physics/state/finite_element_dual.hpp @@ -140,3 +140,14 @@ class FiniteElementDual : public FiniteElementVector { }; } // namespace serac + +namespace refactor { + + using Residual = serac::FiniteElementDual; + + Family get_family(const Residual & r); + uint32_t get_degree(const Residual & r); + uint32_t get_num_components(const Residual & r); + uint32_t get_num_nodes(const Residual & r); + +} diff --git a/src/serac/physics/state/finite_element_state.cpp b/src/serac/physics/state/finite_element_state.cpp index 257a893a7a..d9e44312d5 100644 --- a/src/serac/physics/state/finite_element_state.cpp +++ b/src/serac/physics/state/finite_element_state.cpp @@ -123,3 +123,52 @@ double computeL2Error(const FiniteElementState& state, mfem::Coefficient& exact_ } } // namespace serac + + +namespace refactor { + +serac::Family get_family(const Field & f) { + switch(f.gridFunction().FESpace()->FEColl()->GetContType()) { + case mfem::FiniteElementCollection::CONTINUOUS: return Family::H1; + case mfem::FiniteElementCollection::TANGENTIAL: return Family::HCURL; + case mfem::FiniteElementCollection::NORMAL: return Family::HDIV; + case mfem::FiniteElementCollection::DISCONTINUOUS: return Family::L2; + } + return Family::H1; // unreachable +} + +mfem::FiniteElementSpace * get_FES(const Field & f) { + return f.gridFunction().FESpace(); +} + +uint32_t get_degree(const Field & f) { + return uint32_t(f.gridFunction().FESpace()->FEColl()->GetOrder()); +} + +uint32_t get_num_components(const Field & f) { + return uint32_t(f.gridFunction().VectorDim()); +} + +uint32_t get_num_nodes(const Field & f) { + return uint32_t(f.gridFunction().FESpace()->GetNDofs()); +} + +Field mesh_coordinates(mfem::ParMesh & mesh) { + + // sam: as I understand it mfem::Mesh::GetNodes() requires mfem::Mesh::EnsureNodes() + // be called ahead of time, or else it will not return a valid (mfem::ParGridFunction *) + // + // this is also why the mesh is passed as non-const & + mesh.EnsureNodes(); + + mfem::ParGridFunction* mesh_nodes = dynamic_cast(mesh.GetNodes()); + + Field X(*mesh_nodes->ParFESpace()); + + X.setFromGridFunction(*mesh_nodes); + + return X; + +} + +} diff --git a/src/serac/physics/state/finite_element_state.hpp b/src/serac/physics/state/finite_element_state.hpp index ae8534c6c4..ccabd0502c 100644 --- a/src/serac/physics/state/finite_element_state.hpp +++ b/src/serac/physics/state/finite_element_state.hpp @@ -65,6 +65,8 @@ class FiniteElementState : public FiniteElementVector { */ FiniteElementState(FiniteElementState&& rhs) : FiniteElementVector(std::move(rhs)) {} + + /** * @brief Copy assignment * @@ -251,3 +253,56 @@ double computeL2Error(const FiniteElementState& state, mfem::VectorCoefficient& double computeL2Error(const FiniteElementState& state, mfem::Coefficient& exact_solution); } // namespace serac + +namespace refactor { + + using Field = serac::FiniteElementState; + + Family get_family(const Field & f); + uint32_t get_degree(const Field & f); + uint32_t get_num_components(const Field & f); + uint32_t get_num_nodes(const Field & f); + mfem::FiniteElementSpace * get_FES(const Field & f); + + Field mesh_coordinates(mfem::ParMesh & mesh); + + nd::array< double, 2 > get_nodal_coordinates(const Field & f); + nd::array< double, 2 > get_nodal_directions(const Field & f); + + struct FunctionSpace { + Family family; + uint32_t degree; + uint32_t components; + FunctionSpace() : family{}, degree{}, components{} {} + FunctionSpace(Family f, uint32_t d = 2, uint32_t c = 1) : family{f}, degree{d}, components{c}{} + FunctionSpace(Field f) { + family = get_family(f); + degree = get_degree(f); + components = get_num_components(f); + } + + bool operator==(const FunctionSpace & other) const { + return (components == other.components) && + (degree == other.degree) && + (family == other.family); + } + }; + + struct BasisFunction { + FunctionSpace space; + BasisFunction(Field f) : space(f) {} + BasisFunction(FunctionSpace s) : space(s) {} + bool operator==(const BasisFunction & other) const { + return (space.components == other.space.components) && + (space.degree == other.space.degree) && + (space.family == other.space.family); + } + }; + + GeometryInfo nodes_per_geom(FunctionSpace space); + GeometryInfo interior_nodes_per_geom(FunctionSpace space); + + GeometryInfo dofs_per_geom(FunctionSpace space); + GeometryInfo interior_dofs_per_geom(FunctionSpace space); + +} diff --git a/src/serac/physics/state/finite_element_vector.hpp b/src/serac/physics/state/finite_element_vector.hpp index 399b34ce5d..8b10690b55 100644 --- a/src/serac/physics/state/finite_element_vector.hpp +++ b/src/serac/physics/state/finite_element_vector.hpp @@ -20,6 +20,7 @@ #include "serac/serac_config.hpp" #include "serac/infrastructure/variant.hpp" #include "serac/numerics/functional/functional.hpp" +#include "serac/numerics/refactor/finite_element.hpp" namespace serac { @@ -81,6 +82,45 @@ class FiniteElementVector : public mfem::HypreParVector { HypreParVector::operator=(0.0); } + + FiniteElementVector(mfem::ParMesh& mesh, Family family, int p, int components, const std::string& name = "") + : mesh_(mesh), name_(name) + { + const int dim = mesh.Dimension(); + + switch (family) { + case Family::QOI: + SLIC_ERROR("invalid family choice for FiniteElementVector ctor"); + break; + + case Family::H1: + coll_ = std::make_unique(p, dim); + break; + case Family::HCURL: + coll_ = std::make_unique(p, dim); + break; + case Family::HDIV: + coll_ = std::make_unique(p, dim); + break; + case Family::L2: + // We use GaussLobatto basis functions as this is what is used for the serac::Functional FE kernels + coll_ = std::make_unique(p, dim, mfem::BasisType::GaussLobatto); + break; + } + + space_ = std::make_unique(&mesh, coll_.get(), components, serac::ordering); + + // Construct a hypre par vector based on the new finite element space + HypreParVector new_vector(space_.get()); + + // Move the data from this new hypre vector into this object without doubly allocating the data + auto* parallel_vec = new_vector.StealParVector(); + WrapHypreParVector(parallel_vec); + + // Initialize the vector to zero + HypreParVector::operator=(0.0); + } + /** * @brief Copy constructor *