switch C code prefix to NIF
This commit is contained in:
@@ -75,7 +75,7 @@ namespace Nitload.Common.HighPerformance.ProcessorAbstraction
|
|||||||
NumaFreeNative(address, size, numaId);
|
NumaFreeNative(address, size, numaId);
|
||||||
}
|
}
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_get_numa_each")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_get_numa_each")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
public static partial int GetNumaEach(
|
public static partial int GetNumaEach(
|
||||||
@@ -84,7 +84,7 @@ namespace Nitload.Common.HighPerformance.ProcessorAbstraction
|
|||||||
Span<uint> globalCpuIdInNuma
|
Span<uint> globalCpuIdInNuma
|
||||||
);
|
);
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_get_numa_overall")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_get_numa_overall")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
public static partial int GetNumaOverall(
|
public static partial int GetNumaOverall(
|
||||||
@@ -119,7 +119,7 @@ namespace Nitload.Common.HighPerformance.ProcessorAbstraction
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_set_thread_affinity")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_set_thread_affinity")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
internal static partial void SetThreadAffinity(
|
internal static partial void SetThreadAffinity(
|
||||||
@@ -138,7 +138,7 @@ namespace Nitload.Common.HighPerformance.ProcessorAbstraction
|
|||||||
return new(numaId, count, globalIndex);
|
return new(numaId, count, globalIndex);
|
||||||
}
|
}
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_numa_alloc")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_numa_alloc")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static unsafe partial void* NumaAllocNative(
|
private static unsafe partial void* NumaAllocNative(
|
||||||
@@ -146,7 +146,7 @@ namespace Nitload.Common.HighPerformance.ProcessorAbstraction
|
|||||||
int numaId
|
int numaId
|
||||||
);
|
);
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_numa_free")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_numa_free")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static unsafe partial void NumaFreeNative(
|
private static unsafe partial void NumaFreeNative(
|
||||||
|
|||||||
@@ -51,7 +51,7 @@ namespace Nitload.Threading
|
|||||||
|
|
||||||
#pragma warning disable CA5393
|
#pragma warning disable CA5393
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_set_thread_affinity")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_set_thread_affinity")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static partial void SetThreadAffinity(
|
private static partial void SetThreadAffinity(
|
||||||
|
|||||||
@@ -47,13 +47,13 @@ namespace Nitload.Graphics.OpenGL
|
|||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// <para>Forwards to the native OpenGL entry point.</para>
|
/// <para>Forwards to the native OpenGL entry point.</para>
|
||||||
/// <para><c>void glGetShaderPrecisionFormat(GLenum shadertype, GLenum precisiontype, GLint *range, GLint *precision);</c></para>
|
/// <para><c>void glGetShaderPrecisionFormat(GLenum shaderType, GLenum precisiontype, GLint *range, GLint *precision);</c></para>
|
||||||
/// <para>See <see href="https://docs.gl/gl4/glGetShaderPrecisionFormat">docs.gl</see>.</para>
|
/// <para>See <see href="https://docs.gl/gl4/glGetShaderPrecisionFormat">docs.gl</see>.</para>
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public void GetShaderPrecisionFormat(ShaderType shadertype, PrecisionType precisiontype, int* range, int* precision)
|
public void GetShaderPrecisionFormat(ShaderType shaderType, PrecisionType precisiontype, int* range, int* precision)
|
||||||
{
|
{
|
||||||
__context->glGetShaderPrecisionFormat((uint)shadertype, (uint)precisiontype, range, precision);
|
__context->glGetShaderPrecisionFormat((uint)shaderType, (uint)precisiontype, range, precision);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -176,24 +176,24 @@ namespace Nitload.Graphics.OpenGL
|
|||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// <para>Forwards to the native OpenGL entry point.</para>
|
/// <para>Forwards to the native OpenGL entry point.</para>
|
||||||
/// <para><c>void glMultiDrawArraysIndirect(GLenum mode, const void *indirect, GLsizei drawcount, GLsizei stride);</c></para>
|
/// <para><c>void glMultiDrawArraysIndirect(GLenum mode, const void *indirect, GLsizei drawCount, GLsizei stride);</c></para>
|
||||||
/// <para>See <see href="https://docs.gl/gl4/glMultiDrawArraysIndirect">docs.gl</see>.</para>
|
/// <para>See <see href="https://docs.gl/gl4/glMultiDrawArraysIndirect">docs.gl</see>.</para>
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public void MultiDrawArraysIndirect(PrimitiveType mode, void* indirect, int drawcount, int stride)
|
public void MultiDrawArraysIndirect(PrimitiveType mode, void* indirect, int drawCount, int stride)
|
||||||
{
|
{
|
||||||
__context->glMultiDrawArraysIndirect((uint)mode, indirect, drawcount, stride);
|
__context->glMultiDrawArraysIndirect((uint)mode, indirect, drawCount, stride);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// <para>Forwards to the native OpenGL entry point.</para>
|
/// <para>Forwards to the native OpenGL entry point.</para>
|
||||||
/// <para><c>void glMultiDrawElementsIndirect(GLenum mode, GLenum type, const void *indirect, GLsizei drawcount, GLsizei stride);</c></para>
|
/// <para><c>void glMultiDrawElementsIndirect(GLenum mode, GLenum type, const void *indirect, GLsizei drawCount, GLsizei stride);</c></para>
|
||||||
/// <para>See <see href="https://docs.gl/gl4/glMultiDrawElementsIndirect">docs.gl</see>.</para>
|
/// <para>See <see href="https://docs.gl/gl4/glMultiDrawElementsIndirect">docs.gl</see>.</para>
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public void MultiDrawElementsIndirect(PrimitiveType mode, DrawElementsType type, void* indirect, int drawcount, int stride)
|
public void MultiDrawElementsIndirect(PrimitiveType mode, DrawElementsType type, void* indirect, int drawCount, int stride)
|
||||||
{
|
{
|
||||||
__context->glMultiDrawElementsIndirect((uint)mode, (uint)type, indirect, drawcount, stride);
|
__context->glMultiDrawElementsIndirect((uint)mode, (uint)type, indirect, drawCount, stride);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ namespace Nitload.Graphics
|
|||||||
|
|
||||||
public static GLFWFunction glfwContext => _glfw;
|
public static GLFWFunction glfwContext => _glfw;
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "load_glfw_functions")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_load_glfw_functions")]
|
||||||
internal static unsafe partial void glfwLoadLibrary(
|
internal static unsafe partial void glfwLoadLibrary(
|
||||||
GLFWFunction* context
|
GLFWFunction* context
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -170,7 +170,7 @@ namespace Nitload.Mathematics.Numeric
|
|||||||
|
|
||||||
#region C invoke
|
#region C invoke
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_compare_simd")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_compare_simd")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static partial int CompareSIMDID(
|
private static partial int CompareSIMDID(
|
||||||
@@ -178,7 +178,7 @@ namespace Nitload.Mathematics.Numeric
|
|||||||
SIMDID right
|
SIMDID right
|
||||||
);
|
);
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "load_intrinsic_function")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_load_intrinsic_function")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static partial void LoadIntrinsicFunction(
|
private static partial void LoadIntrinsicFunction(
|
||||||
@@ -186,7 +186,7 @@ namespace Nitload.Mathematics.Numeric
|
|||||||
ulong id
|
ulong id
|
||||||
);
|
);
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_get_unite_simd")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_get_unite_simd")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static partial SIMDID UniteSIMDID(
|
private static partial SIMDID UniteSIMDID(
|
||||||
|
|||||||
@@ -155,12 +155,12 @@ namespace Nitload.Mathematics.Numeric
|
|||||||
}
|
}
|
||||||
|
|
||||||
#pragma warning disable CA5393
|
#pragma warning disable CA5393
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "sn_get_simd_level_local")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_get_simd_level_local")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
internal static partial ulong GetSimdId();
|
internal static partial ulong GetSimdId();
|
||||||
|
|
||||||
[LibraryImport(Native.LibName, EntryPoint = "load_intrinsic_function")]
|
[LibraryImport(Native.LibName, EntryPoint = "nif_load_intrinsic_function")]
|
||||||
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
[UnmanagedCallConv(CallConvs = [typeof(CallConvCdecl)])]
|
||||||
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
[DefaultDllImportSearchPaths(DllImportSearchPath.AssemblyDirectory)]
|
||||||
private static unsafe partial void LoadIntrinsicFunction(
|
private static unsafe partial void LoadIntrinsicFunction(
|
||||||
|
|||||||
@@ -2,8 +2,8 @@
|
|||||||
---
|
---
|
||||||
AccessModifierOffset: -4
|
AccessModifierOffset: -4
|
||||||
AlignAfterOpenBracket: Align
|
AlignAfterOpenBracket: Align
|
||||||
AlignConsecutiveAssignments: false
|
AlignConsecutiveAssignments: true
|
||||||
AlignConsecutiveDeclarations: false
|
AlignConsecutiveDeclarations: true
|
||||||
AlignEscapedNewlines: Left
|
AlignEscapedNewlines: Left
|
||||||
AlignOperands: true
|
AlignOperands: true
|
||||||
AlignTrailingComments: false
|
AlignTrailingComments: false
|
||||||
|
|||||||
@@ -1,2 +1,2 @@
|
|||||||
CompileFlags:
|
CompileFlags:
|
||||||
CompilationDatabase: .
|
CompilationDatabase: ../..
|
||||||
|
|||||||
@@ -3,94 +3,112 @@ project(Nitload.Native LANGUAGES C)
|
|||||||
|
|
||||||
include(${CMAKE_CURRENT_LIST_DIR}/ExternalLibs.cmake OPTIONAL)
|
include(${CMAKE_CURRENT_LIST_DIR}/ExternalLibs.cmake OPTIONAL)
|
||||||
|
|
||||||
set(SN_TARGET_OS "auto" CACHE STRING "Target OS identifier: auto, windows, linux, macos, ios, android, unknown")
|
set(NIF_TARGET_OS "auto" CACHE STRING "Target OS identifier: auto, windows, linux, macos, ios, android, unknown")
|
||||||
set_property(CACHE SN_TARGET_OS PROPERTY STRINGS auto windows linux macos ios android unknown)
|
set_property(CACHE NIF_TARGET_OS PROPERTY STRINGS auto windows linux macos ios android unknown)
|
||||||
|
|
||||||
set(SN_TARGET_ARCH "auto" CACHE STRING "Target ISA identifier: auto, x86_64, arm64, riscv64, ppc64le")
|
set(NIF_TARGET_ARCH "auto" CACHE STRING "Target ISA identifier: auto, x86_64, arm64, riscv64, ppc64le")
|
||||||
set_property(CACHE SN_TARGET_ARCH PROPERTY STRINGS auto x86_64 arm64 riscv64 ppc64le)
|
set_property(CACHE NIF_TARGET_ARCH PROPERTY STRINGS auto x86_64 arm64 riscv64 ppc64le)
|
||||||
|
|
||||||
sn_resolve_target_identifiers(
|
nif_resolve_target_identifiers(
|
||||||
"${SN_TARGET_OS}"
|
"${NIF_TARGET_OS}"
|
||||||
"${SN_TARGET_ARCH}"
|
"${NIF_TARGET_ARCH}"
|
||||||
SN_RESOLVED_OS_NAME
|
NIF_RESOLVED_OS_NAME
|
||||||
SN_RESOLVED_OS_DEFINE
|
NIF_RESOLVED_OS_DEFINE
|
||||||
SN_RESOLVED_ARCH_NAME
|
NIF_RESOLVED_ARCH_NAME
|
||||||
SN_RESOLVED_ARCH_DEFINE)
|
NIF_RESOLVED_ARCH_DEFINE)
|
||||||
|
|
||||||
file(GLOB STGSHARP_NATIVE_SOURCES CONFIGURE_DEPENDS
|
set(NIF_NATIVE_SOURCES
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-src/*.c)
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/dllmain.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/load_glfw.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/load_intrinsic.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/m.bufop.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/m.solve.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/m.transpose.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/mk.fma.pack.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/mk.fma.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/mk.p_scan.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/s.factorial.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/s.hash.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/simdid_compare.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/simdid.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/sk.fma.x86.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/thread.linux.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/thread.windows.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/vector.c
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-src/vector_dot.c)
|
||||||
|
|
||||||
file(GLOB STGSHARP_NATIVE_HEADERS CONFIGURE_DEPENDS
|
set(NIF_NATIVE_HEADERS
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-head/*.h)
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/glfw_function.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_internal.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_intrinsic.context.base.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_intrinsic.context.x86.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_intrinsic.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_intrinsic.matkernel.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_intrinsic.std.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/nif_target.h
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/nif-head/NitloadFrameWork.h)
|
||||||
|
|
||||||
file(GLOB STGSHARP_NATIVE_TEMPLATES CONFIGURE_DEPENDS
|
set(NIF_NATIVE_TEMPLATES
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-template/*.h
|
${CMAKE_CURRENT_LIST_DIR}/nif-template/nif_template.fma.x86.h)
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-template/*.inl
|
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-template/*.inc
|
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-template/*.ipp)
|
|
||||||
|
|
||||||
if(NOT STGSHARP_NATIVE_SOURCES)
|
|
||||||
message(FATAL_ERROR "No source files found under sn-src/.")
|
|
||||||
endif()
|
|
||||||
|
|
||||||
# Nitload.Native now lives under <root>/src/Nitload.Native, so walk up two
|
# Nitload.Native now lives under <root>/src/Nitload.Native, so walk up two
|
||||||
# levels (project dir -> src -> solution root) to reach the solution root.
|
# levels (project dir -> src -> solution root) to reach the solution root.
|
||||||
get_filename_component(STGSHARP_NATIVE_SRC_ROOT ${CMAKE_CURRENT_LIST_DIR} DIRECTORY)
|
get_filename_component(NIF_NATIVE_SRC_ROOT ${CMAKE_CURRENT_LIST_DIR} DIRECTORY)
|
||||||
get_filename_component(STGSHARP_SOLUTION_ROOT ${STGSHARP_NATIVE_SRC_ROOT} DIRECTORY)
|
get_filename_component(NIF_SOLUTION_ROOT ${NIF_NATIVE_SRC_ROOT} DIRECTORY)
|
||||||
|
|
||||||
if(SN_RESOLVED_OS_NAME STREQUAL "windows")
|
if(NIF_RESOLVED_OS_NAME STREQUAL "windows")
|
||||||
set(STGSHARP_OS_TAG win)
|
set(NIF_OS_TAG win)
|
||||||
elseif(SN_RESOLVED_OS_NAME STREQUAL "linux")
|
elseif(NIF_RESOLVED_OS_NAME STREQUAL "linux")
|
||||||
set(STGSHARP_OS_TAG linux)
|
set(NIF_OS_TAG linux)
|
||||||
else()
|
else()
|
||||||
set(STGSHARP_OS_TAG unknown)
|
set(NIF_OS_TAG unknown)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
if(SN_RESOLVED_ARCH_NAME STREQUAL "x86_64")
|
if(NIF_RESOLVED_ARCH_NAME STREQUAL "x86_64")
|
||||||
set(STGSHARP_ARCH_TAG x64)
|
set(NIF_ARCH_TAG x64)
|
||||||
else()
|
else()
|
||||||
set(STGSHARP_ARCH_TAG ${SN_RESOLVED_ARCH_NAME})
|
set(NIF_ARCH_TAG ${NIF_RESOLVED_ARCH_NAME})
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
set(STGSHARP_BUILD_OUTPUT_DIR ${STGSHARP_SOLUTION_ROOT}/bin/${STGSHARP_OS_TAG}-${STGSHARP_ARCH_TAG})
|
set(NIF_BUILD_OUTPUT_DIR ${NIF_SOLUTION_ROOT}/bin/${NIF_OS_TAG}-${NIF_ARCH_TAG})
|
||||||
# Compile-time intermediates (native PDB / .obj side files) live inside the CMake
|
# Compile-time intermediates (native PDB / .obj side files) live inside the CMake
|
||||||
# build tree (cmake_build/<preset>) so they get cleaned up with it.
|
# build tree (cmake_build/<preset>) so they get cleaned up with it.
|
||||||
set(STGSHARP_OBJECT_ROOT_DIR ${CMAKE_CURRENT_BINARY_DIR}/obj/${PROJECT_NAME})
|
set(NIF_OBJECT_ROOT_DIR ${CMAKE_CURRENT_BINARY_DIR}/obj/${PROJECT_NAME})
|
||||||
set(STGSHARP_NATIVE_PROJECT_FILES
|
set(NIF_NATIVE_PROJECT_FILES
|
||||||
${STGSHARP_NATIVE_SOURCES}
|
${NIF_NATIVE_SOURCES}
|
||||||
${STGSHARP_NATIVE_HEADERS}
|
${NIF_NATIVE_HEADERS}
|
||||||
${STGSHARP_NATIVE_TEMPLATES})
|
${NIF_NATIVE_TEMPLATES})
|
||||||
|
|
||||||
add_library(${PROJECT_NAME} SHARED ${STGSHARP_NATIVE_PROJECT_FILES})
|
add_library(${PROJECT_NAME} SHARED ${NIF_NATIVE_PROJECT_FILES})
|
||||||
|
|
||||||
source_group(TREE ${CMAKE_CURRENT_LIST_DIR} FILES ${STGSHARP_NATIVE_PROJECT_FILES})
|
source_group(TREE ${CMAKE_CURRENT_LIST_DIR} FILES ${NIF_NATIVE_PROJECT_FILES})
|
||||||
|
|
||||||
set_target_properties(${PROJECT_NAME} PROPERTIES
|
set_target_properties(${PROJECT_NAME} PROPERTIES
|
||||||
C_STANDARD 11
|
C_STANDARD 11
|
||||||
C_STANDARD_REQUIRED ON
|
C_STANDARD_REQUIRED ON
|
||||||
RUNTIME_OUTPUT_DIRECTORY ${STGSHARP_BUILD_OUTPUT_DIR}
|
RUNTIME_OUTPUT_DIRECTORY ${NIF_BUILD_OUTPUT_DIR}
|
||||||
LIBRARY_OUTPUT_DIRECTORY ${STGSHARP_BUILD_OUTPUT_DIR}
|
LIBRARY_OUTPUT_DIRECTORY ${NIF_BUILD_OUTPUT_DIR}
|
||||||
ARCHIVE_OUTPUT_DIRECTORY ${STGSHARP_BUILD_OUTPUT_DIR})
|
ARCHIVE_OUTPUT_DIRECTORY ${NIF_BUILD_OUTPUT_DIR})
|
||||||
|
|
||||||
foreach(_config Debug Release RelWithDebInfo MinSizeRel)
|
foreach(_config Debug Release RelWithDebInfo MinSizeRel)
|
||||||
string(TOUPPER ${_config} _config_upper)
|
string(TOUPPER ${_config} _config_upper)
|
||||||
set_target_properties(${PROJECT_NAME} PROPERTIES
|
set_target_properties(${PROJECT_NAME} PROPERTIES
|
||||||
RUNTIME_OUTPUT_DIRECTORY_${_config_upper} ${STGSHARP_BUILD_OUTPUT_DIR}
|
RUNTIME_OUTPUT_DIRECTORY_${_config_upper} ${NIF_BUILD_OUTPUT_DIR}
|
||||||
LIBRARY_OUTPUT_DIRECTORY_${_config_upper} ${STGSHARP_BUILD_OUTPUT_DIR}
|
LIBRARY_OUTPUT_DIRECTORY_${_config_upper} ${NIF_BUILD_OUTPUT_DIR}
|
||||||
ARCHIVE_OUTPUT_DIRECTORY_${_config_upper} ${STGSHARP_BUILD_OUTPUT_DIR}
|
ARCHIVE_OUTPUT_DIRECTORY_${_config_upper} ${NIF_BUILD_OUTPUT_DIR}
|
||||||
PDB_OUTPUT_DIRECTORY_${_config_upper} ${STGSHARP_BUILD_OUTPUT_DIR}
|
PDB_OUTPUT_DIRECTORY_${_config_upper} ${NIF_BUILD_OUTPUT_DIR}
|
||||||
COMPILE_PDB_OUTPUT_DIRECTORY_${_config_upper} ${STGSHARP_OBJECT_ROOT_DIR}/${_config}/${STGSHARP_ARCH_TAG})
|
COMPILE_PDB_OUTPUT_DIRECTORY_${_config_upper} ${NIF_OBJECT_ROOT_DIR}/${_config}/${NIF_ARCH_TAG})
|
||||||
endforeach()
|
endforeach()
|
||||||
|
|
||||||
set_target_properties(${PROJECT_NAME} PROPERTIES
|
set_target_properties(${PROJECT_NAME} PROPERTIES
|
||||||
COMPILE_PDB_OUTPUT_DIRECTORY ${STGSHARP_OBJECT_ROOT_DIR}/$<CONFIG>/${STGSHARP_ARCH_TAG})
|
COMPILE_PDB_OUTPUT_DIRECTORY ${NIF_OBJECT_ROOT_DIR}/$<CONFIG>/${NIF_ARCH_TAG})
|
||||||
|
|
||||||
if(MSVC OR (CMAKE_C_COMPILER_ID STREQUAL "Clang" AND CMAKE_C_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC"))
|
if(MSVC OR (CMAKE_C_COMPILER_ID STREQUAL "Clang" AND CMAKE_C_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC"))
|
||||||
target_compile_options(${PROJECT_NAME} PRIVATE
|
target_compile_options(${PROJECT_NAME} PRIVATE
|
||||||
/Fd${STGSHARP_OBJECT_ROOT_DIR}/$<CONFIG>/${STGSHARP_ARCH_TAG}/)
|
/Fd${NIF_OBJECT_ROOT_DIR}/$<CONFIG>/${NIF_ARCH_TAG}/)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
if(CMAKE_C_COMPILER_ID STREQUAL "Clang" AND SN_RESOLVED_ARCH_NAME STREQUAL "x86_64")
|
if(CMAKE_C_COMPILER_ID STREQUAL "Clang" AND NIF_RESOLVED_ARCH_NAME STREQUAL "x86_64")
|
||||||
# Keep the intrinsic type system and builtin declarations visible to all TUs.
|
# Keep the intrinsic type system and builtin declarations visible to all TUs.
|
||||||
# The runtime dispatch contract still follows T_arch/T_feature at the function level.
|
# The runtime dispatch contract still follows T_arch/T_feature at the function level.
|
||||||
if(CMAKE_C_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
|
if(CMAKE_C_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
|
||||||
@@ -120,19 +138,19 @@ endif()
|
|||||||
|
|
||||||
target_include_directories(${PROJECT_NAME}
|
target_include_directories(${PROJECT_NAME}
|
||||||
PRIVATE
|
PRIVATE
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-head
|
${CMAKE_CURRENT_LIST_DIR}/nif-head
|
||||||
${CMAKE_CURRENT_LIST_DIR}/sn-template
|
${CMAKE_CURRENT_LIST_DIR}/nif-template
|
||||||
${CMAKE_CURRENT_LIST_DIR}/lib)
|
${CMAKE_CURRENT_LIST_DIR}/lib)
|
||||||
|
|
||||||
target_compile_definitions(${PROJECT_NAME}
|
target_compile_definitions(${PROJECT_NAME}
|
||||||
PRIVATE
|
PRIVATE
|
||||||
SN_EXTERN_TARGET
|
NIF_EXTERN_TARGET
|
||||||
SN_OS_TARGET=${SN_RESOLVED_OS_DEFINE}
|
NIF_OS_TARGET=${NIF_RESOLVED_OS_DEFINE}
|
||||||
SN_ARCH_TARGET=${SN_RESOLVED_ARCH_DEFINE})
|
NIF_ARCH_TARGET=${NIF_RESOLVED_ARCH_DEFINE})
|
||||||
|
|
||||||
set(STGSHARP_NATIVE_EXTERNAL_TARGET ${PROJECT_NAME})
|
set(NIF_NATIVE_EXTERNAL_TARGET ${PROJECT_NAME})
|
||||||
add_subdirectory(${CMAKE_CURRENT_LIST_DIR}/lib)
|
add_subdirectory(${CMAKE_CURRENT_LIST_DIR}/lib)
|
||||||
|
|
||||||
message(STATUS "Nitload.Native target OS: ${SN_RESOLVED_OS_NAME} (${SN_RESOLVED_OS_DEFINE})")
|
message(STATUS "Nitload.Native target OS: ${NIF_RESOLVED_OS_NAME} (${NIF_RESOLVED_OS_DEFINE})")
|
||||||
message(STATUS "Nitload.Native target ISA: ${SN_RESOLVED_ARCH_NAME} (${SN_RESOLVED_ARCH_DEFINE})")
|
message(STATUS "Nitload.Native target ISA: ${NIF_RESOLVED_ARCH_NAME} (${NIF_RESOLVED_ARCH_DEFINE})")
|
||||||
message(STATUS "Nitload.Native output dir: ${STGSHARP_BUILD_OUTPUT_DIR}")
|
message(STATUS "Nitload.Native output dir: ${NIF_BUILD_OUTPUT_DIR}")
|
||||||
|
|||||||
@@ -24,18 +24,6 @@
|
|||||||
"CMAKE_C_COMPILER": "clang",
|
"CMAKE_C_COMPILER": "clang",
|
||||||
"CMAKE_CXX_COMPILER": "clang++"
|
"CMAKE_CXX_COMPILER": "clang++"
|
||||||
}
|
}
|
||||||
},
|
|
||||||
{
|
|
||||||
"name": "使用工具链文件配置预设",
|
|
||||||
"displayName": "使用工具链文件配置预设",
|
|
||||||
"description": "设置 Ninja 生成器、版本和安装目录",
|
|
||||||
"generator": "Ninja",
|
|
||||||
"binaryDir": "${sourceDir}/../../cmake_build/${presetName}",
|
|
||||||
"cacheVariables": {
|
|
||||||
"CMAKE_BUILD_TYPE": "Debug",
|
|
||||||
"CMAKE_TOOLCHAIN_FILE": "",
|
|
||||||
"CMAKE_INSTALL_PREFIX": "${sourceDir}/out/install/${presetName}"
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"buildPresets": [
|
"buildPresets": [
|
||||||
|
|||||||
@@ -1,74 +1,74 @@
|
|||||||
function(sn_normalize_os_identifier INPUT_VALUE OUTPUT_NAME OUTPUT_DEFINE)
|
function(nif_normalize_os_identifier INPUT_VALUE OUTPUT_NAME OUTPUT_DEFINE)
|
||||||
string(TOLOWER "${INPUT_VALUE}" _sn_os)
|
string(TOLOWER "${INPUT_VALUE}" _nif_os)
|
||||||
|
|
||||||
if(_sn_os STREQUAL "auto")
|
if(_nif_os STREQUAL "auto")
|
||||||
string(TOLOWER "${CMAKE_SYSTEM_NAME}" _sn_system_name)
|
string(TOLOWER "${CMAKE_SYSTEM_NAME}" _nif_system_name)
|
||||||
if(_sn_system_name STREQUAL "windows")
|
if(_nif_system_name STREQUAL "windows")
|
||||||
set(_sn_os "windows")
|
set(_nif_os "windows")
|
||||||
elseif(_sn_system_name STREQUAL "linux")
|
elseif(_nif_system_name STREQUAL "linux")
|
||||||
set(_sn_os "linux")
|
set(_nif_os "linux")
|
||||||
endif()
|
endif()
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
if(_sn_os STREQUAL "windows")
|
if(_nif_os STREQUAL "windows")
|
||||||
set(_sn_define SN_OS_WINDOWS)
|
set(_nif_define NIF_OS_WINDOWS)
|
||||||
elseif(_sn_os STREQUAL "linux")
|
elseif(_nif_os STREQUAL "linux")
|
||||||
set(_sn_define SN_OS_LINUX)
|
set(_nif_define NIF_OS_LINUX)
|
||||||
else()
|
else()
|
||||||
message(FATAL_ERROR "Unsupported SN_TARGET_OS='${INPUT_VALUE}'.")
|
message(FATAL_ERROR "Unsupported NIF_TARGET_OS='${INPUT_VALUE}'.")
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
set(${OUTPUT_NAME} "${_sn_os}" PARENT_SCOPE)
|
set(${OUTPUT_NAME} "${_nif_os}" PARENT_SCOPE)
|
||||||
set(${OUTPUT_DEFINE} "${_sn_define}" PARENT_SCOPE)
|
set(${OUTPUT_DEFINE} "${_nif_define}" PARENT_SCOPE)
|
||||||
endfunction()
|
endfunction()
|
||||||
|
|
||||||
function(sn_normalize_arch_identifier INPUT_VALUE OUTPUT_NAME OUTPUT_DEFINE)
|
function(nif_normalize_arch_identifier INPUT_VALUE OUTPUT_NAME OUTPUT_DEFINE)
|
||||||
string(TOLOWER "${INPUT_VALUE}" _sn_arch)
|
string(TOLOWER "${INPUT_VALUE}" _nif_arch)
|
||||||
|
|
||||||
if(_sn_arch STREQUAL "auto")
|
if(_nif_arch STREQUAL "auto")
|
||||||
string(TOLOWER "${CMAKE_SYSTEM_PROCESSOR}" _sn_processor)
|
string(TOLOWER "${CMAKE_SYSTEM_PROCESSOR}" _nif_processor)
|
||||||
if(_sn_processor MATCHES "^(amd64|x86_64|x64)$")
|
if(_nif_processor MATCHES "^(amd64|x86_64|x64)$")
|
||||||
set(_sn_arch "x86_64")
|
set(_nif_arch "x86_64")
|
||||||
elseif(_sn_processor MATCHES "^(arm64|aarch64)$")
|
elseif(_nif_processor MATCHES "^(arm64|aarch64)$")
|
||||||
set(_sn_arch "arm64")
|
set(_nif_arch "arm64")
|
||||||
elseif(_sn_processor STREQUAL "riscv64")
|
elseif(_nif_processor STREQUAL "riscv64")
|
||||||
set(_sn_arch "riscv64")
|
set(_nif_arch "riscv64")
|
||||||
elseif(_sn_processor MATCHES "^(ppc64le|powerpc64le)$")
|
elseif(_nif_processor MATCHES "^(ppc64le|powerpc64le)$")
|
||||||
set(_sn_arch "ppc64le")
|
set(_nif_arch "ppc64le")
|
||||||
else()
|
else()
|
||||||
message(FATAL_ERROR "Unable to infer ISA from CMAKE_SYSTEM_PROCESSOR='${CMAKE_SYSTEM_PROCESSOR}'. Set SN_TARGET_ARCH explicitly.")
|
message(FATAL_ERROR "Unable to infer ISA from CMAKE_SYSTEM_PROCESSOR='${CMAKE_SYSTEM_PROCESSOR}'. Set NIF_TARGET_ARCH explicitly.")
|
||||||
endif()
|
endif()
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
if(_sn_arch STREQUAL "x86_64")
|
if(_nif_arch STREQUAL "x86_64")
|
||||||
set(_sn_define SN_ARCH_X86_64)
|
set(_nif_define NIF_ARCH_X86_64)
|
||||||
elseif(_sn_arch STREQUAL "arm64")
|
elseif(_nif_arch STREQUAL "arm64")
|
||||||
set(_sn_define SN_ARCH_ARM64)
|
set(_nif_define NIF_ARCH_ARM64)
|
||||||
elseif(_sn_arch STREQUAL "riscv64")
|
elseif(_nif_arch STREQUAL "riscv64")
|
||||||
set(_sn_define SN_ARCH_RISCV64)
|
set(_nif_define NIF_ARCH_RISCV64)
|
||||||
elseif(_sn_arch STREQUAL "ppc64le")
|
elseif(_nif_arch STREQUAL "ppc64le")
|
||||||
set(_sn_define SN_ARCH_PPC64le)
|
set(_nif_define NIF_ARCH_PPC64le)
|
||||||
else()
|
else()
|
||||||
message(FATAL_ERROR "Unsupported SN_TARGET_ARCH='${INPUT_VALUE}'.")
|
message(FATAL_ERROR "Unsupported NIF_TARGET_ARCH='${INPUT_VALUE}'.")
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
set(${OUTPUT_NAME} "${_sn_arch}" PARENT_SCOPE)
|
set(${OUTPUT_NAME} "${_nif_arch}" PARENT_SCOPE)
|
||||||
set(${OUTPUT_DEFINE} "${_sn_define}" PARENT_SCOPE)
|
set(${OUTPUT_DEFINE} "${_nif_define}" PARENT_SCOPE)
|
||||||
endfunction()
|
endfunction()
|
||||||
|
|
||||||
function(sn_resolve_target_identifiers INPUT_OS INPUT_ARCH OUTPUT_OS_NAME OUTPUT_OS_DEFINE OUTPUT_ARCH_NAME OUTPUT_ARCH_DEFINE)
|
function(nif_resolve_target_identifiers INPUT_OS INPUT_ARCH OUTPUT_OS_NAME OUTPUT_OS_DEFINE OUTPUT_ARCH_NAME OUTPUT_ARCH_DEFINE)
|
||||||
sn_normalize_os_identifier("${INPUT_OS}" _sn_os_name _sn_os_define)
|
nif_normalize_os_identifier("${INPUT_OS}" _nif_os_name _nif_os_define)
|
||||||
sn_normalize_arch_identifier("${INPUT_ARCH}" _sn_arch_name _sn_arch_define)
|
nif_normalize_arch_identifier("${INPUT_ARCH}" _nif_arch_name _nif_arch_define)
|
||||||
|
|
||||||
set(${OUTPUT_OS_NAME} "${_sn_os_name}" PARENT_SCOPE)
|
set(${OUTPUT_OS_NAME} "${_nif_os_name}" PARENT_SCOPE)
|
||||||
set(${OUTPUT_OS_DEFINE} "${_sn_os_define}" PARENT_SCOPE)
|
set(${OUTPUT_OS_DEFINE} "${_nif_os_define}" PARENT_SCOPE)
|
||||||
set(${OUTPUT_ARCH_NAME} "${_sn_arch_name}" PARENT_SCOPE)
|
set(${OUTPUT_ARCH_NAME} "${_nif_arch_name}" PARENT_SCOPE)
|
||||||
set(${OUTPUT_ARCH_DEFINE} "${_sn_arch_define}" PARENT_SCOPE)
|
set(${OUTPUT_ARCH_DEFINE} "${_nif_arch_define}" PARENT_SCOPE)
|
||||||
endfunction()
|
endfunction()
|
||||||
|
|
||||||
function(sn_register_external_package TARGET PACKAGE_NAME PACKAGE_DIR)
|
function(nif_register_external_package TARGET PACKAGE_NAME PACKAGE_DIR)
|
||||||
if(NOT TARGET ${TARGET})
|
if(NOT TARGET ${TARGET})
|
||||||
message(FATAL_ERROR "sn_register_external_package: target '${TARGET}' does not exist.")
|
message(FATAL_ERROR "nif_register_external_package: target '${TARGET}' does not exist.")
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
if(EXISTS "${PACKAGE_DIR}")
|
if(EXISTS "${PACKAGE_DIR}")
|
||||||
@@ -79,7 +79,7 @@ function(sn_register_external_package TARGET PACKAGE_NAME PACKAGE_DIR)
|
|||||||
endif()
|
endif()
|
||||||
endfunction()
|
endfunction()
|
||||||
|
|
||||||
function(sn_link_external_binary_if_exists TARGET LIBRARY_PATH)
|
function(nif_link_external_binary_if_exists TARGET LIBRARY_PATH)
|
||||||
if(EXISTS "${LIBRARY_PATH}")
|
if(EXISTS "${LIBRARY_PATH}")
|
||||||
target_link_libraries(${TARGET} PRIVATE "${LIBRARY_PATH}")
|
target_link_libraries(${TARGET} PRIVATE "${LIBRARY_PATH}")
|
||||||
message(STATUS "Linked external binary: ${LIBRARY_PATH}")
|
message(STATUS "Linked external binary: ${LIBRARY_PATH}")
|
||||||
|
|||||||
@@ -110,7 +110,7 @@
|
|||||||
<LanguageStandard_C>stdc11</LanguageStandard_C>
|
<LanguageStandard_C>stdc11</LanguageStandard_C>
|
||||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||||
<FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
|
<FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
|
||||||
<AdditionalIncludeDirectories>$(ProjectDir)lib;$(ProjectDir)sn-head;$(ProjectDir)sn-template;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
<AdditionalIncludeDirectories>$(ProjectDir)lib;$(ProjectDir)nif-head;$(ProjectDir)nif-template;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<Link>
|
<Link>
|
||||||
<!-- DLL 应该用 Windows,不是 Console -->
|
<!-- DLL 应该用 Windows,不是 Console -->
|
||||||
@@ -172,23 +172,23 @@
|
|||||||
<!-- source files -->
|
<!-- source files -->
|
||||||
<!-- ════════════════════════════════════════════════════════ -->
|
<!-- ════════════════════════════════════════════════════════ -->
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClCompile Include="sn-src\dllmain.c" />
|
<ClCompile Include="nif-src\dllmain.c" />
|
||||||
<ClCompile Include="sn-src\m.bufop.x86.c" />
|
<ClCompile Include="nif-src\m.bufop.x86.c" />
|
||||||
<ClCompile Include="sn-src\m.solve.x86.c" />
|
<ClCompile Include="nif-src\m.solve.x86.c" />
|
||||||
<ClCompile Include="sn-src\m.transpose.x86.c" />
|
<ClCompile Include="nif-src\m.transpose.x86.c" />
|
||||||
<ClCompile Include="sn-src\mk.fma.x86.c" />
|
<ClCompile Include="nif-src\mk.fma.x86.c" />
|
||||||
<ClCompile Include="sn-src\mk.p_scan.x86.c" />
|
<ClCompile Include="nif-src\mk.p_scan.x86.c" />
|
||||||
<ClCompile Include="sn-src\s.factorial.x86.c" />
|
<ClCompile Include="nif-src\s.factorial.x86.c" />
|
||||||
<ClCompile Include="sn-src\sk.fma.x86.c" />
|
<ClCompile Include="nif-src\sk.fma.x86.c" />
|
||||||
<ClCompile Include="sn-src\s.hash.x86.c" />
|
<ClCompile Include="nif-src\s.hash.x86.c" />
|
||||||
<ClCompile Include="sn-src\load_intrinsic.x86.c" />
|
<ClCompile Include="nif-src\load_intrinsic.x86.c" />
|
||||||
<ClCompile Include="sn-src\load_glfw.c" />
|
<ClCompile Include="nif-src\load_glfw.c" />
|
||||||
<ClCompile Include="sn-src\simdid.x86.c" />
|
<ClCompile Include="nif-src\simdid.x86.c" />
|
||||||
<ClCompile Include="sn-src\simdid_compare.x86.c" />
|
<ClCompile Include="nif-src\simdid_compare.x86.c" />
|
||||||
<ClCompile Include="sn-src\thread.linux.c" />
|
<ClCompile Include="nif-src\thread.linux.c" />
|
||||||
<ClCompile Include="sn-src\thread.windows.c" />
|
<ClCompile Include="nif-src\thread.windows.c" />
|
||||||
<ClCompile Include="sn-src\vector.c" />
|
<ClCompile Include="nif-src\vector.c" />
|
||||||
<ClCompile Include="sn-src\vector_dot.c" />
|
<ClCompile Include="nif-src\vector_dot.c" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<!-- ════════════════════════════════════════════════════════ -->
|
<!-- ════════════════════════════════════════════════════════ -->
|
||||||
<!-- header files -->
|
<!-- header files -->
|
||||||
@@ -197,15 +197,15 @@
|
|||||||
<ClInclude Include="lib\glfw\glfw3.h" />
|
<ClInclude Include="lib\glfw\glfw3.h" />
|
||||||
<ClInclude Include="lib\glfw\glfw3native.h" />
|
<ClInclude Include="lib\glfw\glfw3native.h" />
|
||||||
<ClInclude Include="lib\stbi\stb_image.h" />
|
<ClInclude Include="lib\stbi\stb_image.h" />
|
||||||
<ClInclude Include="sn-head\glfw_function.h" />
|
<ClInclude Include="nif-head\glfw_function.h" />
|
||||||
<ClInclude Include="sn-head\sn_internal.h" />
|
<ClInclude Include="nif-head\nif_internal.h" />
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.context.x86.h" />
|
<ClInclude Include="nif-head\nif_intrinsic.context.x86.h" />
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.std.h" />
|
<ClInclude Include="nif-head\nif_intrinsic.std.h" />
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.h" />
|
<ClInclude Include="nif-head\nif_intrinsic.h" />
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.matkernel.h" />
|
<ClInclude Include="nif-head\nif_intrinsic.matkernel.h" />
|
||||||
<ClInclude Include="sn-head\sn_target.h" />
|
<ClInclude Include="nif-head\nif_target.h" />
|
||||||
<ClInclude Include="sn-head\StgSharpNative.h" />
|
<ClInclude Include="nif-head\NitloadFrameWork.h" />
|
||||||
<ClInclude Include="sn-template\sn_template.fma.x86.h" />
|
<ClInclude Include="nif-template\nif_template.fma.x86.h" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<None Include="naming.md" />
|
<None Include="naming.md" />
|
||||||
|
|||||||
@@ -21,69 +21,69 @@
|
|||||||
</Filter>
|
</Filter>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClCompile Include="sn-src\dllmain.c">
|
<ClCompile Include="nif-src\dllmain.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\s.factorial.x86.c">
|
<ClCompile Include="nif-src\s.factorial.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\s.hash.x86.c">
|
<ClCompile Include="nif-src\s.hash.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\vector.c">
|
<ClCompile Include="nif-src\vector.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\vector_dot.c">
|
<ClCompile Include="nif-src\vector_dot.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\load_glfw.c">
|
<ClCompile Include="nif-src\load_glfw.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\sk.fma.x86.c">
|
<ClCompile Include="nif-src\sk.fma.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\load_intrinsic.x86.c">
|
<ClCompile Include="nif-src\load_intrinsic.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\m.bufop.x86.c">
|
<ClCompile Include="nif-src\m.bufop.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\m.solve.x86.c">
|
<ClCompile Include="nif-src\m.solve.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\simdid.x86.c">
|
<ClCompile Include="nif-src\simdid.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\mk.fma.x86.c">
|
<ClCompile Include="nif-src\mk.fma.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\simdid_compare.x86.c">
|
<ClCompile Include="nif-src\simdid_compare.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\thread.linux.c">
|
<ClCompile Include="nif-src\thread.linux.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\thread.windows.c">
|
<ClCompile Include="nif-src\thread.windows.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\m.transpose.x86.c">
|
<ClCompile Include="nif-src\m.transpose.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="sn-src\mk.p_scan.x86.c">
|
<ClCompile Include="nif-src\mk.p_scan.x86.c">
|
||||||
<Filter>源文件</Filter>
|
<Filter>源文件</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClInclude Include="sn-head\sn_internal.h">
|
<ClInclude Include="nif-head\nif_internal.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\StgSharpNative.h">
|
<ClInclude Include="nif-head\NitloadFrameWork.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\glfw_function.h">
|
<ClInclude Include="nif-head\glfw_function.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.matkernel.h">
|
<ClInclude Include="nif-head\nif_intrinsic.matkernel.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="lib\glfw\glfw3.h">
|
<ClInclude Include="lib\glfw\glfw3.h">
|
||||||
@@ -95,19 +95,19 @@
|
|||||||
<ClInclude Include="lib\stbi\stb_image.h">
|
<ClInclude Include="lib\stbi\stb_image.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\sn_target.h">
|
<ClInclude Include="nif-head\nif_target.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.context.x86.h">
|
<ClInclude Include="nif-head\nif_intrinsic.context.x86.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.h">
|
<ClInclude Include="nif-head\nif_intrinsic.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-head\sn_intrinsic.std.h">
|
<ClInclude Include="nif-head\nif_intrinsic.std.h">
|
||||||
<Filter>头文件</Filter>
|
<Filter>头文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="sn-template\sn_template.fma.x86.h">
|
<ClInclude Include="nif-template\nif_template.fma.x86.h">
|
||||||
<Filter>模板文件</Filter>
|
<Filter>模板文件</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|||||||
@@ -217,7 +217,7 @@ Detection:
|
|||||||
- **Unknown hybrid** (flag set but core type unrecognised): leave topology at 00.
|
- **Unknown hybrid** (flag set but core type unrecognised): leave topology at 00.
|
||||||
- **SIMD_DUAL**: set when any of the following: `AVX Feature DUAL=1` (glued YMM), or `AVX512_IMPL=DUAL`.
|
- **SIMD_DUAL**: set when any of the following: `AVX Feature DUAL=1` (glued YMM), or `AVX512_IMPL=DUAL`.
|
||||||
|
|
||||||
`sn_get_unite_simd` computes topology bits [1..0] with bitwise **AND** (conservative intersection — weaker topology wins) and SIMD_DUAL with bitwise **OR** (dual if either core is dual). `sn_compare_simd` compares topology value numerically as step 6 and SIMD_DUAL as the final (step 7) tie-break.
|
`nif_get_unite_simd` computes topology bits [1..0] with bitwise **AND** (conservative intersection — weaker topology wins) and SIMD_DUAL with bitwise **OR** (dual if either core is dual). `nif_compare_simd` compares topology value numerically as step 6 and SIMD_DUAL as the final (step 7) tie-break.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
cmake_minimum_required(VERSION 3.16)
|
cmake_minimum_required(VERSION 3.16)
|
||||||
|
|
||||||
if(NOT DEFINED STGSHARP_NATIVE_EXTERNAL_TARGET)
|
if(NOT DEFINED NIF_NATIVE_EXTERNAL_TARGET)
|
||||||
message(FATAL_ERROR "STGSHARP_NATIVE_EXTERNAL_TARGET must be set before adding lib/.")
|
message(FATAL_ERROR "NIF_NATIVE_EXTERNAL_TARGET must be set before adding lib/.")
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
include(${CMAKE_CURRENT_LIST_DIR}/../ExternalLibs.cmake OPTIONAL)
|
include(${CMAKE_CURRENT_LIST_DIR}/../ExternalLibs.cmake OPTIONAL)
|
||||||
@@ -17,6 +17,6 @@ foreach(_pkg ${LIB_PACKAGE_DIRS})
|
|||||||
if(EXISTS ${_pkg_dir}/CMakeLists.txt)
|
if(EXISTS ${_pkg_dir}/CMakeLists.txt)
|
||||||
add_subdirectory(${_pkg_dir})
|
add_subdirectory(${_pkg_dir})
|
||||||
else()
|
else()
|
||||||
sn_register_external_package(${STGSHARP_NATIVE_EXTERNAL_TARGET} ${_pkg} ${_pkg_dir})
|
nif_register_external_package(${NIF_NATIVE_EXTERNAL_TARGET} ${_pkg} ${_pkg_dir})
|
||||||
endif()
|
endif()
|
||||||
endforeach()
|
endforeach()
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
cmake_minimum_required(VERSION 3.16)
|
cmake_minimum_required(VERSION 3.16)
|
||||||
|
|
||||||
sn_register_external_package(${STGSHARP_NATIVE_EXTERNAL_TARGET} glfw ${CMAKE_CURRENT_LIST_DIR})
|
nif_register_external_package(${NIF_NATIVE_EXTERNAL_TARGET} glfw ${CMAKE_CURRENT_LIST_DIR})
|
||||||
|
|
||||||
if(WIN32)
|
if(WIN32)
|
||||||
if(NOT EXISTS ${CMAKE_CURRENT_LIST_DIR}/glfw3_mt.lib)
|
if(NOT EXISTS ${CMAKE_CURRENT_LIST_DIR}/glfw3_mt.lib)
|
||||||
message(FATAL_ERROR "Required GLFW static library not found: ${CMAKE_CURRENT_LIST_DIR}/glfw3_mt.lib")
|
message(FATAL_ERROR "Required GLFW static library not found: ${CMAKE_CURRENT_LIST_DIR}/glfw3_mt.lib")
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
sn_link_external_binary_if_exists(${STGSHARP_NATIVE_EXTERNAL_TARGET} ${CMAKE_CURRENT_LIST_DIR}/glfw3_mt.lib)
|
nif_link_external_binary_if_exists(${NIF_NATIVE_EXTERNAL_TARGET} ${CMAKE_CURRENT_LIST_DIR}/glfw3_mt.lib)
|
||||||
endif()
|
endif()
|
||||||
@@ -1,3 +1,3 @@
|
|||||||
cmake_minimum_required(VERSION 3.16)
|
cmake_minimum_required(VERSION 3.16)
|
||||||
|
|
||||||
sn_register_external_package(${STGSHARP_NATIVE_EXTERNAL_TARGET} stbi ${CMAKE_CURRENT_LIST_DIR})
|
nif_register_external_package(${NIF_NATIVE_EXTERNAL_TARGET} stbi ${CMAKE_CURRENT_LIST_DIR})
|
||||||
@@ -0,0 +1,35 @@
|
|||||||
|
#ifndef NIF_NATIVE_H
|
||||||
|
#define NIF_NATIVE_H
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
#error "This header is not meant to be included in C++ code. Nitload.Native is a C library and should be used with C linkage."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include "nif_internal.h"
|
||||||
|
#include "nif_target.h"
|
||||||
|
|
||||||
|
#include <immintrin.h>
|
||||||
|
#include <assert.h>
|
||||||
|
#include <glfw_function.h>
|
||||||
|
|
||||||
|
#define byte char
|
||||||
|
#define cs_char uint16_t
|
||||||
|
#define nif_null_assert(ptr) assert(ptr != NULL)
|
||||||
|
|
||||||
|
#ifndef NIF_
|
||||||
|
#endif
|
||||||
|
|
||||||
|
NIF_API void NIF_DECL nif_load_glfw_functions(GLFWFunctionTable *table);
|
||||||
|
NIF_API void NIF_DECL nif_load_intrinsic_function(void *intrinsic_context, uint64_t id);
|
||||||
|
NIF_API SIMDID NIF_DECL nif_get_simd_level_global();
|
||||||
|
/* Per-core variant: always re-executes CPUID, never caches.
|
||||||
|
* Must be called on the target core (after affinity is set). */
|
||||||
|
NIF_API SIMDID NIF_DECL nif_get_simd_level_local();
|
||||||
|
NIF_API SIMDID NIF_DECL nif_get_unite_simd(SIMDID left, SIMDID right);
|
||||||
|
NIF_API int NIF_DECL nif_compare_simd(SIMDID left, SIMDID right);
|
||||||
|
NIF_API void NIF_DECL nif_set_thread_affinity(int core_id, int numa_id);
|
||||||
|
NIF_API void* NIF_DECL nif_numa_alloc(size_t size, int numa_id);
|
||||||
|
NIF_API void NIF_DECL nif_numa_free(void *ptr, size_t size, int numa_id);
|
||||||
|
NIF_API int NIF_DECL nif_get_numa_each(int numa_id, uint64_t *internal, uint32_t *global);
|
||||||
|
NIF_API int NIF_DECL nif_get_numa_overall(int *out_numa_count, int *count_of_each_numa);
|
||||||
|
#endif
|
||||||
+14
-14
@@ -1,6 +1,6 @@
|
|||||||
|
|
||||||
#ifndef SN_INTERNAL
|
#ifndef NIF_INTERNAL
|
||||||
#define SN_INTERNAL
|
#define NIF_INTERNAL
|
||||||
|
|
||||||
#include <xmmintrin.h>
|
#include <xmmintrin.h>
|
||||||
|
|
||||||
@@ -9,33 +9,33 @@
|
|||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
#define _CRT_SECURE_NO_WARNINGS 1
|
#define _CRT_SECURE_NO_WARNINGS 1
|
||||||
#define WIN32_LEAN_AND_MEAN
|
#define WIN32_LEAN_AND_MEAN
|
||||||
#define SN_DECL __cdecl
|
#define NIF_DECL __cdecl
|
||||||
#define SN_MAT_DECL __cdecl __forceinline
|
#define NIF_MAT_DECL __cdecl __forceinline
|
||||||
#define SN_API __declspec(dllexport)
|
#define NIF_API __declspec(dllexport)
|
||||||
#define FORCEINLINE __forceinline
|
#define FORCEINLINE __forceinline
|
||||||
#define NOINLINE __declspec(noinline)
|
#define NOINLINE __declspec(noinline)
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#elif defined(__clang__) || defined(__GNUC__)
|
#elif defined(__clang__) || defined(__GNUC__)
|
||||||
#define SN_DECL __attribute__((cdecl))
|
#define NIF_DECL __attribute__((cdecl))
|
||||||
#define SN_MAT_DECL __attribute__((cdecl)) __attribute__((always_inline))
|
#define NIF_MAT_DECL __attribute__((cdecl)) __attribute__((always_inline))
|
||||||
#define SN_API __attribute__((dllexport))
|
#define NIF_API __attribute__((dllexport))
|
||||||
#define FORCEINLINE __attribute__((always_inline))
|
#define FORCEINLINE __attribute__((always_inline))
|
||||||
#define NOINLINE __attribute__((noinline))
|
#define NOINLINE __attribute__((noinline))
|
||||||
#else
|
#else
|
||||||
#define SN_API
|
#define NIF_API
|
||||||
#define SN_DECL
|
#define NIF_DECL
|
||||||
#define SN_MAT_DECL
|
#define NIF_MAT_DECL
|
||||||
#define FORCEINLINE
|
#define FORCEINLINE
|
||||||
#define NOINLINE
|
#define NOINLINE
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(_MSC_VER)
|
#if defined(_MSC_VER)
|
||||||
#define SN_ALIGNAS(n) __declspec(align(n))
|
#define NIF_ALIGNAS(n) __declspec(align(n))
|
||||||
#else
|
#else
|
||||||
#define SN_ALIGNAS(n) __attribute__((aligned(n)))
|
#define NIF_ALIGNAS(n) __attribute__((aligned(n)))
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define SN_APIDEF
|
#define NIF_APIDEF
|
||||||
|
|
||||||
#define PRIVATE static
|
#define PRIVATE static
|
||||||
#define INTERNAL extern
|
#define INTERNAL extern
|
||||||
+2
-2
@@ -1,5 +1,5 @@
|
|||||||
#ifndef SN_INTRINSIC_CONTEXT_BASE
|
#ifndef NIF_INTRINSIC_CONTEXT_BASE
|
||||||
#define SN_INTRINSIC_CONTEXT_BASE
|
#define NIF_INTRINSIC_CONTEXT_BASE
|
||||||
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
+107
-107
@@ -1,20 +1,20 @@
|
|||||||
#ifndef SN_INTRINSIC_CONTEXT_X86_H
|
#ifndef NIF_INTRINSIC_CONTEXT_X86_H
|
||||||
#define SN_INTRINSIC_CONTEXT_X86_H
|
#define NIF_INTRINSIC_CONTEXT_X86_H
|
||||||
|
|
||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.context.base.h"
|
#include "nif_intrinsic.context.base.h"
|
||||||
|
|
||||||
#ifndef SN_X86_TARGET_ATTR_sse
|
#ifndef NIF_X86_TARGET_ATTR_sse
|
||||||
#define SN_STD_TARGET_ATTR_IMPL(T_arch, T_feature) SN_X86_TARGET_ATTR_##T_arch##T_feature
|
#define NIF_STD_TARGET_ATTR_IMPL(T_arch, T_feature) NIF_X86_TARGET_ATTR_##T_arch##T_feature
|
||||||
#define SN_X86_TARGET_ATTR_sse SN_CLANG_TARGET_ATTR("sse4.2")
|
#define NIF_X86_TARGET_ATTR_sse NIF_CLANG_TARGET_ATTR("sse4.2")
|
||||||
#define SN_X86_TARGET_ATTR_avx SN_CLANG_TARGET_ATTR("avx")
|
#define NIF_X86_TARGET_ATTR_avx NIF_CLANG_TARGET_ATTR("avx")
|
||||||
#define SN_X86_TARGET_ATTR_avx_fma SN_CLANG_TARGET_ATTR("avx,avx2,fma")
|
#define NIF_X86_TARGET_ATTR_avx_fma NIF_CLANG_TARGET_ATTR("avx,avx2,fma")
|
||||||
#define SN_X86_TARGET_ATTR_512 SN_CLANG_TARGET_ATTR("avx512f,avx512vl")
|
#define NIF_X86_TARGET_ATTR_512 NIF_CLANG_TARGET_ATTR("avx512f,avx512vl")
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
@@ -111,45 +111,45 @@
|
|||||||
|
|
||||||
INTERNAL void f32_normalize(VEC_SEGMENT(float) * source, VEC_SEGMENT(float) * target);
|
INTERNAL void f32_normalize(VEC_SEGMENT(float) * source, VEC_SEGMENT(float) * target);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , k_quality);
|
NIF_MK_PROC_DECL_STD(float, sse, , k_quality);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , add);
|
NIF_MK_PROC_DECL_STD(float, sse, , add);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , add);
|
NIF_MK_PROC_DECL_STD(float, avx, , add);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , add);
|
NIF_MK_PROC_DECL_STD(float, 512, , add);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , add);
|
NIF_MK_PROC_DECL_STD(double, sse, , add);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , add);
|
NIF_MK_PROC_DECL_STD(double, avx, , add);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , add);
|
NIF_MK_PROC_DECL_STD(double, 512, , add);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , sub);
|
NIF_MK_PROC_DECL_STD(float, sse, , sub);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , sub);
|
NIF_MK_PROC_DECL_STD(float, avx, , sub);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , sub);
|
NIF_MK_PROC_DECL_STD(float, 512, , sub);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , sub);
|
NIF_MK_PROC_DECL_STD(double, sse, , sub);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , sub);
|
NIF_MK_PROC_DECL_STD(double, avx, , sub);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , sub);
|
NIF_MK_PROC_DECL_STD(double, 512, , sub);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , transpose);
|
NIF_MK_PROC_DECL_STD(float, sse, , transpose);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , transpose);
|
NIF_MK_PROC_DECL_STD(float, avx, , transpose);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , transpose);
|
NIF_MK_PROC_DECL_STD(float, 512, , transpose);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , scalar_mul);
|
NIF_MK_PROC_DECL_STD(float, sse, , scalar_mul);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , scalar_mul);
|
NIF_MK_PROC_DECL_STD(float, avx, , scalar_mul);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , scalar_mul);
|
NIF_MK_PROC_DECL_STD(float, 512, , scalar_mul);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , scalar_mul);
|
NIF_MK_PROC_DECL_STD(double, sse, , scalar_mul);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , scalar_mul);
|
NIF_MK_PROC_DECL_STD(double, avx, , scalar_mul);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , scalar_mul);
|
NIF_MK_PROC_DECL_STD(double, 512, , scalar_mul);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fill);
|
NIF_MK_PROC_DECL_STD(float, sse, , fill);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fill);
|
NIF_MK_PROC_DECL_STD(float, avx, , fill);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fill);
|
NIF_MK_PROC_DECL_STD(float, 512, , fill);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , fill);
|
NIF_MK_PROC_DECL_STD(double, sse, , fill);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , fill);
|
NIF_MK_PROC_DECL_STD(double, avx, , fill);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , fill);
|
NIF_MK_PROC_DECL_STD(double, 512, , fill);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , quality);
|
NIF_MK_PROC_DECL_STD(float, sse, , quality);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* pack left matrix data to L4 buffer
|
* pack left matrix data to L4 buffer
|
||||||
@@ -166,9 +166,9 @@ SN_MK_PROC_DECL_STD(float, sse, , quality);
|
|||||||
* scalar pack carries column length and offset data:
|
* scalar pack carries column length and offset data:
|
||||||
* [column length, empty, empty, empty]
|
* [column length, empty, empty, empty]
|
||||||
*/
|
*/
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma_pack_left);
|
NIF_MK_PROC_DECL_STD(float, sse, , fma_pack_left);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma_pack_left);
|
NIF_MK_PROC_DECL_STD(float, avx, , fma_pack_left);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma_pack_left);
|
NIF_MK_PROC_DECL_STD(float, 512, , fma_pack_left);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* pack right matrix data to L4 buffer
|
* pack right matrix data to L4 buffer
|
||||||
@@ -185,104 +185,104 @@ SN_MK_PROC_DECL_STD(float, 512, , fma_pack_left);
|
|||||||
* scalar pack carries column length and offset data:
|
* scalar pack carries column length and offset data:
|
||||||
* [column length, empty, empty, empty]
|
* [column length, empty, empty, empty]
|
||||||
*/
|
*/
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma_pack_right);
|
NIF_MK_PROC_DECL_STD(float, sse, , fma_pack_right);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma_pack_right);
|
NIF_MK_PROC_DECL_STD(float, avx, , fma_pack_right);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma_pack_right);
|
NIF_MK_PROC_DECL_STD(float, 512, , fma_pack_right);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma);
|
NIF_MK_PROC_DECL_STD(float, sse, , fma);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma);
|
NIF_MK_PROC_DECL_STD(float, avx, , fma);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, _fma, fma);
|
NIF_MK_PROC_DECL_STD(float, avx, _fma, fma);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma);
|
NIF_MK_PROC_DECL_STD(float, 512, , fma);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma_unpack);
|
NIF_MK_PROC_DECL_STD(float, sse, , fma_unpack);
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma_unpack);
|
NIF_MK_PROC_DECL_STD(float, avx, , fma_unpack);
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma_unpack);
|
NIF_MK_PROC_DECL_STD(float, 512, , fma_unpack);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , fma_pack_left);
|
NIF_MK_PROC_DECL_STD(double, sse, , fma_pack_left);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , fma_pack_left);
|
NIF_MK_PROC_DECL_STD(double, avx, , fma_pack_left);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , fma_pack_left);
|
NIF_MK_PROC_DECL_STD(double, 512, , fma_pack_left);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , fma);
|
NIF_MK_PROC_DECL_STD(double, sse, , fma);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , fma);
|
NIF_MK_PROC_DECL_STD(double, avx, , fma);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, _fma, fma);
|
NIF_MK_PROC_DECL_STD(double, avx, _fma, fma);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , fma);
|
NIF_MK_PROC_DECL_STD(double, 512, , fma);
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , fma_unpack);
|
NIF_MK_PROC_DECL_STD(double, sse, , fma_unpack);
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , fma_unpack);
|
NIF_MK_PROC_DECL_STD(double, avx, , fma_unpack);
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , fma_unpack);
|
NIF_MK_PROC_DECL_STD(double, 512, , fma_unpack);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , add);
|
NIF_SK_PROC_DECL_STD(float, avx, , add);
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , add);
|
NIF_SK_PROC_DECL_STD(float, 512, , add);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, sse, , add);
|
NIF_SK_PROC_DECL_STD(double, sse, , add);
|
||||||
SN_SK_PROC_DECL_STD(double, avx, , add);
|
NIF_SK_PROC_DECL_STD(double, avx, , add);
|
||||||
SN_SK_PROC_DECL_STD(double, 512, , add);
|
NIF_SK_PROC_DECL_STD(double, 512, , add);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , sub);
|
NIF_SK_PROC_DECL_STD(float, sse, , sub);
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , sub);
|
NIF_SK_PROC_DECL_STD(float, avx, , sub);
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , sub);
|
NIF_SK_PROC_DECL_STD(float, 512, , sub);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, sse, , sub);
|
NIF_SK_PROC_DECL_STD(double, sse, , sub);
|
||||||
SN_SK_PROC_DECL_STD(double, avx, , sub);
|
NIF_SK_PROC_DECL_STD(double, avx, , sub);
|
||||||
SN_SK_PROC_DECL_STD(double, 512, , sub);
|
NIF_SK_PROC_DECL_STD(double, 512, , sub);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , transpose);
|
NIF_SK_PROC_DECL_STD(float, sse, , transpose);
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , transpose);
|
NIF_SK_PROC_DECL_STD(float, avx, , transpose);
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , transpose);
|
NIF_SK_PROC_DECL_STD(float, 512, , transpose);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , scalar_mul);
|
NIF_SK_PROC_DECL_STD(float, sse, , scalar_mul);
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , scalar_mul);
|
NIF_SK_PROC_DECL_STD(float, avx, , scalar_mul);
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , scalar_mul);
|
NIF_SK_PROC_DECL_STD(float, 512, , scalar_mul);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, sse, , scalar_mul);
|
NIF_SK_PROC_DECL_STD(double, sse, , scalar_mul);
|
||||||
SN_SK_PROC_DECL_STD(double, avx, , scalar_mul);
|
NIF_SK_PROC_DECL_STD(double, avx, , scalar_mul);
|
||||||
SN_SK_PROC_DECL_STD(double, 512, , scalar_mul);
|
NIF_SK_PROC_DECL_STD(double, 512, , scalar_mul);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , fill);
|
NIF_SK_PROC_DECL_STD(float, sse, , fill);
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , fill);
|
NIF_SK_PROC_DECL_STD(float, avx, , fill);
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , fill);
|
NIF_SK_PROC_DECL_STD(float, 512, , fill);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, sse, , fill);
|
NIF_SK_PROC_DECL_STD(double, sse, , fill);
|
||||||
SN_SK_PROC_DECL_STD(double, avx, , fill);
|
NIF_SK_PROC_DECL_STD(double, avx, , fill);
|
||||||
SN_SK_PROC_DECL_STD(double, 512, , fill);
|
NIF_SK_PROC_DECL_STD(double, 512, , fill);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , quality);
|
NIF_SK_PROC_DECL_STD(float, sse, , quality);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , fma);
|
NIF_SK_PROC_DECL_STD(float, sse, , fma);
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , fma);
|
NIF_SK_PROC_DECL_STD(float, avx, , fma);
|
||||||
SN_SK_PROC_DECL_STD(float, avx, _fma, fma);
|
NIF_SK_PROC_DECL_STD(float, avx, _fma, fma);
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , fma);
|
NIF_SK_PROC_DECL_STD(float, 512, , fma);
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, sse, , fma);
|
NIF_SK_PROC_DECL_STD(double, sse, , fma);
|
||||||
SN_SK_PROC_DECL_STD(double, avx, , fma);
|
NIF_SK_PROC_DECL_STD(double, avx, , fma);
|
||||||
SN_SK_PROC_DECL_STD(double, avx, _fma, fma);
|
NIF_SK_PROC_DECL_STD(double, avx, _fma, fma);
|
||||||
SN_SK_PROC_DECL_STD(double, 512, , fma);
|
NIF_SK_PROC_DECL_STD(double, 512, , fma);
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
#pragma region scaler_simd
|
#pragma region scaler_simd
|
||||||
|
|
||||||
INTERNAL uint64_t SN_DECL factorial_simd_sse(int n);
|
INTERNAL uint64_t NIF_DECL factorial_simd_sse(int n);
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
#pragma region dot_product
|
#pragma region dot_product
|
||||||
|
|
||||||
INTERNAL void FORCEINLINE SN_DECL dot_41_sse(MAT_KERNEL(float) const *transpose,
|
INTERNAL void FORCEINLINE NIF_DECL dot_41_sse(MAT_KERNEL(float) const *transpose,
|
||||||
__m128 const *vector, __m128 *ans);
|
__m128 const *vector, __m128 *ans);
|
||||||
INTERNAL void SN_DECL dot_41_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
INTERNAL void NIF_DECL dot_41_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
||||||
__m128 *ans);
|
__m128 *ans);
|
||||||
INTERNAL void SN_DECL dot_42_sse(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
INTERNAL void NIF_DECL dot_42_sse(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
||||||
__m128 *ans);
|
__m128 *ans);
|
||||||
INTERNAL void SN_DECL dot_42_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
INTERNAL void NIF_DECL dot_42_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
||||||
__m128 *ans);
|
__m128 *ans);
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
#pragma region string
|
#pragma region string
|
||||||
|
|
||||||
INTERNAL int SN_DECL city_hash_simplify_sse(byte const *str, int length);
|
INTERNAL int NIF_DECL city_hash_simplify_sse(byte const *str, int length);
|
||||||
INTERNAL int SN_DECL index_pair_sse(short const *stram, uint32_t target, int length);
|
INTERNAL int NIF_DECL index_pair_sse(short const *stram, uint32_t target, int length);
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
+25
-25
@@ -3,12 +3,12 @@
|
|||||||
|
|
||||||
#define SSC_INTRIN_HEAD
|
#define SSC_INTRIN_HEAD
|
||||||
|
|
||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
#include <xmmintrin.h>
|
#include <xmmintrin.h>
|
||||||
#include <immintrin.h>
|
#include <immintrin.h>
|
||||||
#include <smmintrin.h>
|
#include <smmintrin.h>
|
||||||
#include "sn_intrinsic.matkernel.h"
|
#include "nif_intrinsic.matkernel.h"
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
@@ -28,7 +28,7 @@
|
|||||||
((LASTTWO(s3) << 6) | (LASTTWO(s2) << 4) | (LASTTWO(s1) << 2) | (LASTTWO(s0)))
|
((LASTTWO(s3) << 6) | (LASTTWO(s2) << 4) | (LASTTWO(s1) << 2) | (LASTTWO(s0)))
|
||||||
#define BIT_CVRT(pack, index, T) *(T *)(pack->data + index)
|
#define BIT_CVRT(pack, index, T) *(T *)(pack->data + index)
|
||||||
|
|
||||||
#if SN_IS_ARCH(x86_64)
|
#if NIF_IS_ARCH(x86_64)
|
||||||
|
|
||||||
#define vec_128 __m128
|
#define vec_128 __m128
|
||||||
#define vec_256 __m256
|
#define vec_256 __m256
|
||||||
@@ -66,7 +66,7 @@ typedef union uint64_u {
|
|||||||
typedef struct mat_kernel mat_kernel;
|
typedef struct mat_kernel mat_kernel;
|
||||||
|
|
||||||
typedef union M128{
|
typedef union M128{
|
||||||
#if SN_IS_ARCH(x86_64)
|
#if NIF_IS_ARCH(x86_64)
|
||||||
__m128 m128;
|
__m128 m128;
|
||||||
#endif
|
#endif
|
||||||
float f32[4];
|
float f32[4];
|
||||||
@@ -76,7 +76,7 @@ typedef union M128{
|
|||||||
}M128;
|
}M128;
|
||||||
|
|
||||||
typedef union M256{
|
typedef union M256{
|
||||||
#if SN_IS_ARCH(x86_64)
|
#if NIF_IS_ARCH(x86_64)
|
||||||
__m256 m256;
|
__m256 m256;
|
||||||
#endif
|
#endif
|
||||||
float f32[8];
|
float f32[8];
|
||||||
@@ -86,7 +86,7 @@ typedef union M256{
|
|||||||
}M256;
|
}M256;
|
||||||
|
|
||||||
typedef union M512{
|
typedef union M512{
|
||||||
#if SN_IS_ARCH(x86_64)
|
#if NIF_IS_ARCH(x86_64)
|
||||||
__m512 m512;
|
__m512 m512;
|
||||||
#endif
|
#endif
|
||||||
uint64_t u64[8];
|
uint64_t u64[8];
|
||||||
@@ -97,24 +97,24 @@ typedef union M512{
|
|||||||
int64_t i64[8];
|
int64_t i64[8];
|
||||||
}M512;
|
}M512;
|
||||||
|
|
||||||
typedef struct sn_L4_cache_head {
|
typedef struct nif_L4_cache_head {
|
||||||
uint64_t reverse_mask_0;
|
uint64_t reverse_mask_0;
|
||||||
uint32_t position_mask;
|
uint32_t position_mask;
|
||||||
uint32_t size;
|
uint32_t size;
|
||||||
uint64_t reverse_mask_1;
|
uint64_t reverse_mask_1;
|
||||||
uint64_t reverse_mask_2;
|
uint64_t reverse_mask_2;
|
||||||
} sn_L4_cache_head;
|
} nif_L4_cache_head;
|
||||||
|
|
||||||
typedef struct sn_L4_handle {
|
typedef struct nif_L4_handle {
|
||||||
void *ptr;
|
void *ptr;
|
||||||
sn_L4_cache_head* head;
|
nif_L4_cache_head* head;
|
||||||
} sn_L4_handle;
|
} nif_L4_handle;
|
||||||
|
|
||||||
typedef struct matrix_task {
|
typedef struct matrix_task {
|
||||||
sn_L4_handle buffer_0;
|
nif_L4_handle buffer_0;
|
||||||
sn_L4_handle buffer_1;
|
nif_L4_handle buffer_1;
|
||||||
sn_L4_handle buffer_2;
|
nif_L4_handle buffer_2;
|
||||||
sn_L4_handle buffer_3;
|
nif_L4_handle buffer_3;
|
||||||
union {
|
union {
|
||||||
struct {
|
struct {
|
||||||
int32_t reverse_0;
|
int32_t reverse_0;
|
||||||
@@ -144,18 +144,18 @@ static_assert(sizeof(matrix_task) == 128, "matrix_parallel_task_package size mis
|
|||||||
static_assert(sizeof(matrix_task) == 128, "matrix_parallel_task_package size mismatch");
|
static_assert(sizeof(matrix_task) == 128, "matrix_parallel_task_package size mismatch");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
typedef void(SN_DECL *UNI_MK_PROC)(matrix_task *task);
|
typedef void(NIF_DECL *UNI_MK_PROC)(matrix_task *task);
|
||||||
typedef void(SN_DECL *UNI_SK_PROC)(mat_kernel const *left, mat_kernel const *right,
|
typedef void(NIF_DECL *UNI_SK_PROC)(mat_kernel const *left, mat_kernel const *right,
|
||||||
mat_kernel *restrict ans, uint64_t scalar);
|
mat_kernel *restrict ans, uint64_t scalar);
|
||||||
|
|
||||||
typedef void(SN_DECL *VECTORNORMALIZEPROC)(VEC_SEGMENT(float) *source, VEC_SEGMENT(float) *target);
|
typedef void(NIF_DECL *VECTORNORMALIZEPROC)(VEC_SEGMENT(float) *source, VEC_SEGMENT(float) *target);
|
||||||
typedef void(SN_DECL *DOTPROC)(void *transpose, __m128 *vector, __m128 *ans);
|
typedef void(NIF_DECL *DOTPROC)(void *transpose, __m128 *vector, __m128 *ans);
|
||||||
typedef uint64_t(SN_DECL *FACTORIALROC)(int n);
|
typedef uint64_t(NIF_DECL *FACTORIALROC)(int n);
|
||||||
|
|
||||||
#pragma region string
|
#pragma region string
|
||||||
|
|
||||||
typedef int(SN_DECL *HASH)(byte const *str, int length);
|
typedef int(NIF_DECL *HASH)(byte const *str, int length);
|
||||||
typedef int(SN_DECL *INDEX_PAIR)(short const *stram, uint32_t target, int length);
|
typedef int(NIF_DECL *INDEX_PAIR)(short const *stram, uint32_t target, int length);
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
@@ -168,13 +168,13 @@ typedef struct mat_sk_intrinsic {
|
|||||||
} mat_sk_intrinsic;
|
} mat_sk_intrinsic;
|
||||||
|
|
||||||
// Mirrors C# IntrinsicContext field order so managed/unmanaged layouts stay in sync.
|
// Mirrors C# IntrinsicContext field order so managed/unmanaged layouts stay in sync.
|
||||||
typedef struct sn_intrinsic {
|
typedef struct nif_intrinsic {
|
||||||
HASH city_hash_simplify;
|
HASH city_hash_simplify;
|
||||||
FACTORIALROC factorial_simd;
|
FACTORIALROC factorial_simd;
|
||||||
VECTORNORMALIZEPROC vec_f32_normalize_3;
|
VECTORNORMALIZEPROC vec_f32_normalize_3;
|
||||||
mat_mk_intrinsic mat_mk[0x0a];
|
mat_mk_intrinsic mat_mk[0x0a];
|
||||||
mat_sk_intrinsic mat_sk[0x0a];
|
mat_sk_intrinsic mat_sk[0x0a];
|
||||||
} sn_intrinsic;
|
} nif_intrinsic;
|
||||||
|
|
||||||
|
|
||||||
typedef enum mat_proc_index {
|
typedef enum mat_proc_index {
|
||||||
@@ -0,0 +1,54 @@
|
|||||||
|
#ifndef NIF_MATKERNEL
|
||||||
|
#define NIF_MATKERNEL
|
||||||
|
|
||||||
|
#include <immintrin.h>
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
#include "nif_internal.h"
|
||||||
|
|
||||||
|
/* Kernel storage unions for a fixed 4x4 block. */
|
||||||
|
#define ELEMENTSIZE(T) sizeof(T)
|
||||||
|
#define XMMCOUNT(T) (sizeof(T))
|
||||||
|
#define YMMCOUNT(T) (sizeof(T) / 2)
|
||||||
|
#define ZMMCOUNT(T) (sizeof(T) / 4)
|
||||||
|
|
||||||
|
#define NIF_MAT_KERNEL_MEMBER(T) \
|
||||||
|
{ \
|
||||||
|
__m128 x[XMMCOUNT(T)]; \
|
||||||
|
__m256 y[YMMCOUNT(T)]; \
|
||||||
|
__m512 z[ZMMCOUNT(T)]; \
|
||||||
|
T m[4][4]; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define NIF_MAT_KERNEL_DEFINE(T) \
|
||||||
|
typedef union NIF_MAT_KERNEL_TYPE_##T NIF_MAT_KERNEL_MEMBER(T) NIF_MAT_KERNEL_TYPE_##T
|
||||||
|
|
||||||
|
#define MAT_KERNEL(T) NIF_MAT_KERNEL_TYPE(T)
|
||||||
|
#define NIF_MAT_KERNEL_TYPE(T) NIF_MAT_KERNEL_TYPE_##T
|
||||||
|
|
||||||
|
NIF_MAT_KERNEL_DEFINE(float);
|
||||||
|
NIF_MAT_KERNEL_DEFINE(double);
|
||||||
|
NIF_MAT_KERNEL_DEFINE(uint64_t);
|
||||||
|
|
||||||
|
|
||||||
|
#define NIF_VEC_SEGMENT_MEMBER(T) \
|
||||||
|
{ \
|
||||||
|
__m128 f32_x[XMMCOUNT(T) / 4]; \
|
||||||
|
__m256 f32_y[YMMCOUNT(T) / 4]; \
|
||||||
|
__m512 f32_z[ZMMCOUNT(T) / 4]; \
|
||||||
|
T v[4]; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define NIF_VEC_SEGMENT_DEFINE(T) \
|
||||||
|
typedef union NIF_VEC_SEGMENT_TYPE_##T NIF_VEC_SEGMENT_MEMBER(T) NIF_VEC_SEGMENT_TYPE_##T
|
||||||
|
|
||||||
|
#define VEC_SEGMENT(T) NIF_VEC_SEGMENT_TYPE(T)
|
||||||
|
#define NIF_VEC_SEGMENT_TYPE(T) NIF_VEC_SEGMENT_TYPE_##T
|
||||||
|
|
||||||
|
NIF_VEC_SEGMENT_DEFINE(float);
|
||||||
|
NIF_VEC_SEGMENT_DEFINE(double);
|
||||||
|
|
||||||
|
/* Global zero kernel declaration (defined in dllmain.c), aligned to 64 bytes */
|
||||||
|
extern __declspec(align(64)) MAT_KERNEL(u64) NIF_ZERO_KERNEL;
|
||||||
|
|
||||||
|
#endif /* NIF_MATKERNEL */
|
||||||
+26
-26
@@ -1,23 +1,23 @@
|
|||||||
#ifndef SN_INTRINSIC_CALLCONV_STD
|
#ifndef NIF_INTRINSIC_CALLCONV_STD
|
||||||
#define SN_INTRINSIC_CALLCONV_STD
|
#define NIF_INTRINSIC_CALLCONV_STD
|
||||||
|
|
||||||
#include "sn_internal.h"
|
#include "nif_internal.h"
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
|
|
||||||
#ifndef static_assert
|
#ifndef static_assert
|
||||||
#define static_assert _Static_assert
|
#define static_assert _Static_assert
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define SN_STD_TARGET_ATTR(T_arch, T_feature) SN_STD_TARGET_ATTR_IMPL(T_arch, T_feature)
|
#define NIF_STD_TARGET_ATTR(T_arch, T_feature) NIF_STD_TARGET_ATTR_IMPL(T_arch, T_feature)
|
||||||
|
|
||||||
#pragma region mk_proc attributes
|
#pragma region mk_proc attributes
|
||||||
#define MK_PROC_NAME_STD(T_type, T_arch, T_feature, T_op) \
|
#define MK_PROC_NAME_STD(T_type, T_arch, T_feature, T_op) \
|
||||||
T_type##_multi_kernel_proc_##T_op##_##T_arch##_##T_feature
|
T_type##_multi_kernel_proc_##T_op##_##T_arch##_##T_feature
|
||||||
#define GET_MK_PROC_STD(T_type, T_arch, T_feature, T_op) \
|
#define GET_MK_PROC_STD(T_type, T_arch, T_feature, T_op) \
|
||||||
((UNI_MK_PROC)MK_PROC_NAME_STD(T_type, T_arch, T_feature, T_op))
|
((UNI_MK_PROC)MK_PROC_NAME_STD(T_type, T_arch, T_feature, T_op))
|
||||||
#define SN_MK_PROC_DECL(T_type, P_name) INTERNAL void SN_DECL P_name(MAT_TASK(T_type) const *task)
|
#define NIF_MK_PROC_DECL(T_type, P_name) INTERNAL void NIF_DECL P_name(MAT_TASK(T_type) const *task)
|
||||||
#define SN_MK_PROC_DECL_STD(T_type, T_arch, T_feature, T_op) \
|
#define NIF_MK_PROC_DECL_STD(T_type, T_arch, T_feature, T_op) \
|
||||||
INTERNAL NOINLINE SN_STD_TARGET_ATTR(T_arch, T_feature) void SN_DECL MK_PROC_NAME_STD( \
|
INTERNAL NOINLINE NIF_STD_TARGET_ATTR(T_arch, T_feature) void NIF_DECL MK_PROC_NAME_STD( \
|
||||||
T_type, T_arch, T_feature, T_op)(MAT_TASK(T_type) const *task)
|
T_type, T_arch, T_feature, T_op)(MAT_TASK(T_type) const *task)
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
@@ -26,8 +26,8 @@
|
|||||||
T_type##_single_kernel_proc_##T_op##_##T_arch##_##T_feature
|
T_type##_single_kernel_proc_##T_op##_##T_arch##_##T_feature
|
||||||
#define GET_SK_PROC_STD(T_type, T_arch, T_feature, T_op) \
|
#define GET_SK_PROC_STD(T_type, T_arch, T_feature, T_op) \
|
||||||
((UNI_SK_PROC)SK_PROC_NAME_STD(T_type, T_arch, T_feature, T_op))
|
((UNI_SK_PROC)SK_PROC_NAME_STD(T_type, T_arch, T_feature, T_op))
|
||||||
#define SN_SK_PROC_DECL_STD(T_type, T_arch, T_feature, T_op) \
|
#define NIF_SK_PROC_DECL_STD(T_type, T_arch, T_feature, T_op) \
|
||||||
INTERNAL NOINLINE SN_STD_TARGET_ATTR(T_arch, T_feature) void SN_DECL SK_PROC_NAME_STD( \
|
INTERNAL NOINLINE NIF_STD_TARGET_ATTR(T_arch, T_feature) void NIF_DECL SK_PROC_NAME_STD( \
|
||||||
T_type, T_arch, T_feature, \
|
T_type, T_arch, T_feature, \
|
||||||
T_op)(MAT_KERNEL(T_type) const *left, MAT_KERNEL(T_type) const *right, \
|
T_op)(MAT_KERNEL(T_type) const *left, MAT_KERNEL(T_type) const *right, \
|
||||||
MAT_KERNEL(T_type) *restrict ans, uint64_t scalar)
|
MAT_KERNEL(T_type) *restrict ans, uint64_t scalar)
|
||||||
@@ -35,8 +35,8 @@
|
|||||||
|
|
||||||
#define _SN_STD__PROBE_0 0
|
#define _SN_STD__PROBE_0 0
|
||||||
#define _SN_STD__PROBE_1 1
|
#define _SN_STD__PROBE_1 1
|
||||||
#define SN_STD__PROBE_PRINT(x) _SN_STD__PROBE_##x
|
#define NIF_STD__PROBE_PRINT(x) _SN_STD__PROBE_##x
|
||||||
#define SN_STD__PROBE(x) SN_STD__PROBE_PRINT(x)
|
#define NIF_STD__PROBE(x) NIF_STD__PROBE_PRINT(x)
|
||||||
|
|
||||||
#pragma region param styles
|
#pragma region param styles
|
||||||
|
|
||||||
@@ -51,37 +51,37 @@
|
|||||||
int count_##i = task->count_##i;\
|
int count_##i = task->count_##i;\
|
||||||
|
|
||||||
#define _SN_MK_EXPAND_RIGHT_ANS \
|
#define _SN_MK_EXPAND_RIGHT_ANS \
|
||||||
SN_MAT_KERNEL_LOCAL const *right = (SN_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
NIF_MAT_KERNEL_LOCAL const *right = (NIF_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans = (SN_MAT_KERNEL_LOCAL *)task->buffer_2.ptr;\
|
NIF_MAT_KERNEL_LOCAL *restrict ans = (NIF_MAT_KERNEL_LOCAL *)task->buffer_2.ptr;\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(1); \
|
_SN_MK_EXPAND_BUFFER_SIZE(1); \
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
||||||
|
|
||||||
#define _SN_MK_EXPAND_LEFT_RIGHT_ANS \
|
#define _SN_MK_EXPAND_LEFT_RIGHT_ANS \
|
||||||
SN_MAT_KERNEL_LOCAL const *left = (SN_MAT_KERNEL_LOCAL const *)task->buffer_0.ptr; \
|
NIF_MAT_KERNEL_LOCAL const *left = (NIF_MAT_KERNEL_LOCAL const *)task->buffer_0.ptr; \
|
||||||
SN_MAT_KERNEL_LOCAL const *right = (SN_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
NIF_MAT_KERNEL_LOCAL const *right = (NIF_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans = (SN_MAT_KERNEL_LOCAL *)task->buffer_2.ptr;\
|
NIF_MAT_KERNEL_LOCAL *restrict ans = (NIF_MAT_KERNEL_LOCAL *)task->buffer_2.ptr;\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(0); \
|
_SN_MK_EXPAND_BUFFER_SIZE(0); \
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(1);\
|
_SN_MK_EXPAND_BUFFER_SIZE(1);\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
||||||
|
|
||||||
#define _SN_MK_EXPAND_RIGHT_ANS_SCALAR \
|
#define _SN_MK_EXPAND_RIGHT_ANS_SCALAR \
|
||||||
SN_MAT_KERNEL_LOCAL const *right = (SN_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
NIF_MAT_KERNEL_LOCAL const *right = (NIF_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans = (SN_MAT_KERNEL_LOCAL *)task->buffer_2.ptr; \
|
NIF_MAT_KERNEL_LOCAL *restrict ans = (NIF_MAT_KERNEL_LOCAL *)task->buffer_2.ptr; \
|
||||||
M128 scalar = task->scalar_pack;\
|
M128 scalar = task->scalar_pack;\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(1);\
|
_SN_MK_EXPAND_BUFFER_SIZE(1);\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
||||||
|
|
||||||
#define _SN_MK_EXPAND_LEFT_RIGHT_ANS_SCALAR \
|
#define _SN_MK_EXPAND_LEFT_RIGHT_ANS_SCALAR \
|
||||||
SN_MAT_KERNEL_LOCAL const *left = (SN_MAT_KERNEL_LOCAL const *)task->buffer_0.ptr; \
|
NIF_MAT_KERNEL_LOCAL const *left = (NIF_MAT_KERNEL_LOCAL const *)task->buffer_0.ptr; \
|
||||||
SN_MAT_KERNEL_LOCAL const *right = (SN_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
NIF_MAT_KERNEL_LOCAL const *right = (NIF_MAT_KERNEL_LOCAL const *)task->buffer_1.ptr; \
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans = (SN_MAT_KERNEL_LOCAL *)task->buffer_2.ptr; \
|
NIF_MAT_KERNEL_LOCAL *restrict ans = (NIF_MAT_KERNEL_LOCAL *)task->buffer_2.ptr; \
|
||||||
M128 scalar = task->scalar_pack;\
|
M128 scalar = task->scalar_pack;\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(0);\
|
_SN_MK_EXPAND_BUFFER_SIZE(0);\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(1);\
|
_SN_MK_EXPAND_BUFFER_SIZE(1);\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
||||||
|
|
||||||
#define _SN_MK_EXPAND_ANS_SCALAR \
|
#define _SN_MK_EXPAND_ANS_SCALAR \
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans = (SN_MAT_KERNEL_LOCAL *)task->buffer_2.ptr; \
|
NIF_MAT_KERNEL_LOCAL *restrict ans = (NIF_MAT_KERNEL_LOCAL *)task->buffer_2.ptr; \
|
||||||
M128 scalar = task->scalar_pack;\
|
M128 scalar = task->scalar_pack;\
|
||||||
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
_SN_MK_EXPAND_BUFFER_SIZE(2);
|
||||||
|
|
||||||
@@ -91,11 +91,11 @@
|
|||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
|
||||||
#define __mk_param_std(param, T) \
|
#define __mk_param_std(param, T) \
|
||||||
typedef MAT_KERNEL(T) SN_MAT_KERNEL_LOCAL; \
|
typedef MAT_KERNEL(T) NIF_MAT_KERNEL_LOCAL; \
|
||||||
matrix_task const *_ = (_SN_PARAM_STYLE(param), task); \
|
matrix_task const *_ = (_SN_PARAM_STYLE(param), task); \
|
||||||
_SN_MK_EXPAND_PARAM(param)
|
_SN_MK_EXPAND_PARAM(param)
|
||||||
|
|
||||||
#define __sk_param_std(T) \
|
#define __sk_param_std(T) \
|
||||||
typedef MAT_KERNEL(T) SN_MAT_KERNEL_LOCAL; \
|
typedef MAT_KERNEL(T) NIF_MAT_KERNEL_LOCAL; \
|
||||||
(void)scalar
|
(void)scalar
|
||||||
#endif // !SN_INTRINSIC_PARAM_EXPAND
|
#endif // !NIF_INTRINSIC_PARAM_EXPAND
|
||||||
@@ -0,0 +1,94 @@
|
|||||||
|
#ifndef NIF_TARGET
|
||||||
|
#define NIF_TARGET
|
||||||
|
|
||||||
|
#include "nif_internal.h"
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
#define NIF_OS_WINDOWS 0
|
||||||
|
#define NIF_OS_LINUX 1
|
||||||
|
#define NIF_OS_MACOS 2
|
||||||
|
#define NIF_OS_IOS 3
|
||||||
|
#define NIF_OS_ANDROID 4
|
||||||
|
#define NIF_OS_UNKNOWN 5
|
||||||
|
|
||||||
|
#define NIF_ARCH_X86_64 0
|
||||||
|
#define NIF_ARCH_ARM64 1
|
||||||
|
#define NIF_ARCH_RISCV64 2
|
||||||
|
#define NIF_ARCH_PPC64le 3
|
||||||
|
|
||||||
|
#if defined(_M_X64) || defined(_M_AMD64) || defined(__x86_64__) || defined(__amd64__)
|
||||||
|
#define NIF_CURRENT_ARCH NIF_ARCH_X86_64
|
||||||
|
|
||||||
|
#elif defined(_M_ARM64) || defined(__aarch64__)
|
||||||
|
#define NIF_CURRENT_ARCH NIF_ARCH_ARM64
|
||||||
|
|
||||||
|
#elif defined(_M_ARM) || defined(__arm__)
|
||||||
|
#define NIF_CURRENT_ARCH NIF_ARCH_ARM32
|
||||||
|
|
||||||
|
#elif defined(_M_IX86) || defined(__i386__)
|
||||||
|
#define NIF_CURRENT_ARCH NIF_ARCH_X86_32
|
||||||
|
|
||||||
|
#elif defined(__powerpc64__) && defined(__LITTLE_ENDIAN__)
|
||||||
|
#define NIF_CURRENT_ARCH NIF_ARCH_PPC64LE
|
||||||
|
|
||||||
|
#elif defined(__riscv) && (__riscv_xlen == 64)
|
||||||
|
#define NIF_CURRENT_ARCH NIF_ARCH_RISCV64
|
||||||
|
|
||||||
|
#else
|
||||||
|
#error "SN: Unsupported target architecture"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Target selection policy:
|
||||||
|
* - Default (no NIF_EXTERN_TARGET): fixed Windows + x86_64.
|
||||||
|
* - External (NIF_EXTERN_TARGET): build system must provide NIF_OS and NIF_ARCH.
|
||||||
|
*/
|
||||||
|
#ifndef NIF_EXTERN_TARGET
|
||||||
|
|
||||||
|
#define NIF_OS_TARGET NIF_OS_WINDOWS
|
||||||
|
#define NIF_ARCH_TARGET NIF_ARCH_X86_64
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
#ifndef NIF_OS_TARGET
|
||||||
|
#error "NIF_EXTERN_TARGET is defined but NIF_OS is not provided."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef NIF_ARCH_TARGET
|
||||||
|
#error "NIF_EXTERN_TARGET is defined but NIF_ARCH is not provided."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Validate externally supplied values are within known enum constants. */
|
||||||
|
#if (NIF_OS_TARGET != NIF_OS_WINDOWS) && (NIF_OS_TARGET != NIF_OS_LINUX) && \
|
||||||
|
(NIF_OS_TARGET != NIF_OS_MACOS) && (NIF_OS_TARGET != NIF_OS_IOS) && \
|
||||||
|
(NIF_OS_TARGET != NIF_OS_ANDROID) && (NIF_OS_TARGET != NIF_OS_UNKNOWN)
|
||||||
|
#error "NIF_OS has an invalid value. Use NIF_OS_<...> enum constants."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if (NIF_ARCH_TARGET != NIF_ARCH_X86_64) && (NIF_ARCH_TARGET != NIF_ARCH_ARM64) && \
|
||||||
|
(NIF_ARCH_TARGET != NIF_ARCH_RISCV64) && (NIF_ARCH_TARGET != NIF_ARCH_PPC64le)
|
||||||
|
#error "NIF_ARCH has an invalid value. Use NIF_ARCH_<...> enum constants."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define NIF_IS_OS(os) ((NIF_OS_TARGET) == (os))
|
||||||
|
|
||||||
|
#define NIF_IS_ARCH(arch) ((NIF_ARCH_TARGET) == (arch))
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Per-function ISA selection is required for runtime-dispatched kernels that
|
||||||
|
* mix multiple x86 feature levels in one build target.
|
||||||
|
*/
|
||||||
|
#if defined(__clang__) && ((NIF_ARCH_TARGET) == NIF_ARCH_X86_64)
|
||||||
|
#define NIF_CLANG_TARGET_ATTR(options) __attribute__((target(options)))
|
||||||
|
#else
|
||||||
|
#define NIF_CLANG_TARGET_ATTR(options)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
typedef union SIMDID {
|
||||||
|
uint64_t mask;
|
||||||
|
char make_byte[8];
|
||||||
|
} SIMDID;
|
||||||
|
|
||||||
|
#endif // NIF_TARGET
|
||||||
@@ -1,18 +1,18 @@
|
|||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
#include "sn_intrinsic.matkernel.h"
|
#include "nif_intrinsic.matkernel.h"
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
|
|
||||||
/* Define and initialize a global zero kernel aligned to 64 bytes for universal ISA usage */
|
/* Define and initialize a global zero kernel aligned to 64 bytes for universal ISA usage */
|
||||||
|
|
||||||
__declspec(align(64)) MAT_KERNEL(u64) SN_ZERO_KERNEL;
|
__declspec(align(64)) MAT_KERNEL(u64) NIF_ZERO_KERNEL;
|
||||||
|
|
||||||
static void init_zero_kernel(void)
|
static void init_zero_kernel(void)
|
||||||
{
|
{
|
||||||
for (int c = 0; c < 4; ++c) {
|
for (int c = 0; c < 4; ++c) {
|
||||||
for (int r = 0; r < 4; ++r) {
|
for (int r = 0; r < 4; ++r) {
|
||||||
SN_ZERO_KERNEL.m[r][c] = 0;
|
NIF_ZERO_KERNEL.m[r][c] = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
|
|
||||||
SN_API void SN_DECL load_glfw_functions(GLFWFunctionTable *table)
|
NIF_API void NIF_DECL nif_load_glfw_functions(GLFWFunctionTable *table)
|
||||||
{
|
{
|
||||||
table->glfwCreateCursor = glfwCreateCursor;
|
table->glfwCreateCursor = glfwCreateCursor;
|
||||||
table->glfwCreateStandardCursor = glfwCreateStandardCursor;
|
table->glfwCreateStandardCursor = glfwCreateStandardCursor;
|
||||||
+16
-16
@@ -1,28 +1,28 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
PRIVATE void load_intrinsic_sse(sn_intrinsic *context, SIMDID id);
|
PRIVATE void load_intrinsic_sse(nif_intrinsic *context, SIMDID id);
|
||||||
PRIVATE void load_intrinsic_avx(sn_intrinsic *context, SIMDID id);
|
PRIVATE void load_intrinsic_avx(nif_intrinsic *context, SIMDID id);
|
||||||
PRIVATE void load_intrinsic_512(sn_intrinsic *context, SIMDID id);
|
PRIVATE void load_intrinsic_512(nif_intrinsic *context, SIMDID id);
|
||||||
|
|
||||||
SN_API void SN_DECL load_intrinsic_function(void *intrinsic_context, uint64_t id)
|
NIF_API void NIF_DECL nif_load_intrinsic_function(void *intrinsic_context, uint64_t id)
|
||||||
{
|
{
|
||||||
sn_null_assert(intrinsic_context);
|
nif_null_assert(intrinsic_context);
|
||||||
|
|
||||||
SIMDID simdid;
|
SIMDID simdid;
|
||||||
if (id) {
|
if (id) {
|
||||||
simdid.mask = id;
|
simdid.mask = id;
|
||||||
} else {
|
} else {
|
||||||
simdid = sn_get_simd_level_global();
|
simdid = nif_get_simd_level_global();
|
||||||
}
|
}
|
||||||
|
|
||||||
sn_intrinsic *context = (sn_intrinsic *)intrinsic_context;
|
nif_intrinsic *context = (nif_intrinsic *)intrinsic_context;
|
||||||
|
|
||||||
switch (simdid.make_byte[1]) {
|
switch (simdid.make_byte[1]) {
|
||||||
case SIMDID_MAIN_LVL_SSE:
|
case SIMDID_MAIN_LVL_SSE:
|
||||||
@@ -38,7 +38,7 @@ SN_API void SN_DECL load_intrinsic_function(void *intrinsic_context, uint64_t id
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void load_intrinsic_sse(sn_intrinsic *context, SIMDID id)
|
void load_intrinsic_sse(nif_intrinsic *context, SIMDID id)
|
||||||
{
|
{
|
||||||
context->city_hash_simplify = city_hash_simplify_sse;
|
context->city_hash_simplify = city_hash_simplify_sse;
|
||||||
context->factorial_simd = factorial_simd_sse;
|
context->factorial_simd = factorial_simd_sse;
|
||||||
@@ -62,7 +62,7 @@ void load_intrinsic_sse(sn_intrinsic *context, SIMDID id)
|
|||||||
context->vec_f32_normalize_3 = f32_normalize;
|
context->vec_f32_normalize_3 = f32_normalize;
|
||||||
}
|
}
|
||||||
|
|
||||||
void load_intrinsic_avx(sn_intrinsic *context, SIMDID id)
|
void load_intrinsic_avx(nif_intrinsic *context, SIMDID id)
|
||||||
{
|
{
|
||||||
char avx_seg = id.make_byte[4];
|
char avx_seg = id.make_byte[4];
|
||||||
char is_fma = (avx_seg & SIMDID_AVX_FMA) != 0;
|
char is_fma = (avx_seg & SIMDID_AVX_FMA) != 0;
|
||||||
@@ -91,7 +91,7 @@ void load_intrinsic_avx(sn_intrinsic *context, SIMDID id)
|
|||||||
context->vec_f32_normalize_3 = f32_normalize;
|
context->vec_f32_normalize_3 = f32_normalize;
|
||||||
}
|
}
|
||||||
|
|
||||||
void load_intrinsic_512(sn_intrinsic *context, SIMDID id)
|
void load_intrinsic_512(nif_intrinsic *context, SIMDID id)
|
||||||
{
|
{
|
||||||
context->city_hash_simplify = city_hash_simplify_sse;
|
context->city_hash_simplify = city_hash_simplify_sse;
|
||||||
context->factorial_simd = factorial_simd_sse;
|
context->factorial_simd = factorial_simd_sse;
|
||||||
+29
-29
@@ -1,13 +1,13 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include <immintrin.h>
|
#include <immintrin.h>
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fill)
|
NIF_MK_PROC_DECL_STD(float, sse, , fill)
|
||||||
{
|
{
|
||||||
__mk_param_std(ANS_SCALAR, float);
|
__mk_param_std(ANS_SCALAR, float);
|
||||||
register __m128 vec = _mm_set_ps1(scalar.f32[0]);
|
register __m128 vec = _mm_set_ps1(scalar.f32[0]);
|
||||||
@@ -19,7 +19,7 @@ SN_MK_PROC_DECL_STD(float, sse, , fill)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fill)
|
NIF_MK_PROC_DECL_STD(float, avx, , fill)
|
||||||
{
|
{
|
||||||
__mk_param_std(ANS_SCALAR, float);
|
__mk_param_std(ANS_SCALAR, float);
|
||||||
register __m256 vec = _mm256_broadcast_ss(&scalar.f32[0]);
|
register __m256 vec = _mm256_broadcast_ss(&scalar.f32[0]);
|
||||||
@@ -29,7 +29,7 @@ SN_MK_PROC_DECL_STD(float, avx, , fill)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fill)
|
NIF_MK_PROC_DECL_STD(float, 512, , fill)
|
||||||
{
|
{
|
||||||
__mk_param_std(ANS_SCALAR, float);
|
__mk_param_std(ANS_SCALAR, float);
|
||||||
register __m512 vec = _mm512_broadcastss_ps(scalar.m128);
|
register __m512 vec = _mm512_broadcastss_ps(scalar.m128);
|
||||||
@@ -38,7 +38,7 @@ SN_MK_PROC_DECL_STD(float, 512, , fill)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , fill)
|
NIF_MK_PROC_DECL_STD(double, sse, , fill)
|
||||||
{
|
{
|
||||||
__mk_param_std(ANS_SCALAR, double);
|
__mk_param_std(ANS_SCALAR, double);
|
||||||
register __m128d vec_d = _mm_set1_pd(scalar.f64[0]);
|
register __m128d vec_d = _mm_set1_pd(scalar.f64[0]);
|
||||||
@@ -55,7 +55,7 @@ SN_MK_PROC_DECL_STD(double, sse, , fill)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , fill)
|
NIF_MK_PROC_DECL_STD(double, avx, , fill)
|
||||||
{
|
{
|
||||||
__mk_param_std(ANS_SCALAR, double);
|
__mk_param_std(ANS_SCALAR, double);
|
||||||
register __m256d vec = _mm256_broadcast_sd(&scalar.f64[0]);
|
register __m256d vec = _mm256_broadcast_sd(&scalar.f64[0]);
|
||||||
@@ -67,7 +67,7 @@ SN_MK_PROC_DECL_STD(double, avx, , fill)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , fill)
|
NIF_MK_PROC_DECL_STD(double, 512, , fill)
|
||||||
{
|
{
|
||||||
__mk_param_std(ANS_SCALAR, double);
|
__mk_param_std(ANS_SCALAR, double);
|
||||||
register __m512d vec = _mm512_set1_pd(scalar.f64[0]);
|
register __m512d vec = _mm512_set1_pd(scalar.f64[0]);
|
||||||
@@ -77,7 +77,7 @@ SN_MK_PROC_DECL_STD(double, 512, , fill)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , add)
|
NIF_MK_PROC_DECL_STD(float, sse, , add)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -94,7 +94,7 @@ SN_MK_PROC_DECL_STD(float, sse, , add)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , add)
|
NIF_MK_PROC_DECL_STD(float, avx, , add)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -107,7 +107,7 @@ SN_MK_PROC_DECL_STD(float, avx, , add)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , add)
|
NIF_MK_PROC_DECL_STD(float, 512, , add)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -116,7 +116,7 @@ SN_MK_PROC_DECL_STD(float, 512, , add)
|
|||||||
ans[i].z[0] = c0;
|
ans[i].z[0] = c0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , add)
|
NIF_MK_PROC_DECL_STD(double, sse, , add)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, double);
|
__mk_param_std( LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
@@ -149,7 +149,7 @@ SN_MK_PROC_DECL_STD(double, sse, , add)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , add)
|
NIF_MK_PROC_DECL_STD(double, avx, , add)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, double);
|
__mk_param_std( LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
@@ -166,7 +166,7 @@ SN_MK_PROC_DECL_STD(double, avx, , add)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , add)
|
NIF_MK_PROC_DECL_STD(double, 512, , add)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, double);
|
__mk_param_std( LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
@@ -178,7 +178,7 @@ SN_MK_PROC_DECL_STD(double, 512, , add)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , sub)
|
NIF_MK_PROC_DECL_STD(float, sse, , sub)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, float);
|
__mk_param_std( LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -195,7 +195,7 @@ SN_MK_PROC_DECL_STD(float, sse, , sub)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , sub)
|
NIF_MK_PROC_DECL_STD(float, avx, , sub)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, float);
|
__mk_param_std( LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -207,7 +207,7 @@ SN_MK_PROC_DECL_STD(float, avx, , sub)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , sub)
|
NIF_MK_PROC_DECL_STD(float, 512, , sub)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, float);
|
__mk_param_std( LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -217,7 +217,7 @@ SN_MK_PROC_DECL_STD(float, 512, , sub)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , sub)
|
NIF_MK_PROC_DECL_STD(double, sse, , sub)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, double);
|
__mk_param_std( LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
@@ -242,7 +242,7 @@ SN_MK_PROC_DECL_STD(double, sse, , sub)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , sub)
|
NIF_MK_PROC_DECL_STD(double, avx, , sub)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, double);
|
__mk_param_std( LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
@@ -254,7 +254,7 @@ SN_MK_PROC_DECL_STD(double, avx, , sub)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , sub)
|
NIF_MK_PROC_DECL_STD(double, 512, , sub)
|
||||||
{
|
{
|
||||||
__mk_param_std( LEFT_RIGHT_ANS, double);
|
__mk_param_std( LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
@@ -264,7 +264,7 @@ SN_MK_PROC_DECL_STD(double, 512, , sub)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , scalar_mul)
|
NIF_MK_PROC_DECL_STD(float, sse, , scalar_mul)
|
||||||
{
|
{
|
||||||
__mk_param_std( RIGHT_ANS_SCALAR, float);
|
__mk_param_std( RIGHT_ANS_SCALAR, float);
|
||||||
|
|
||||||
@@ -282,7 +282,7 @@ SN_MK_PROC_DECL_STD(float, sse, , scalar_mul)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , scalar_mul)
|
NIF_MK_PROC_DECL_STD(float, avx, , scalar_mul)
|
||||||
{
|
{
|
||||||
__mk_param_std( RIGHT_ANS_SCALAR, float);
|
__mk_param_std( RIGHT_ANS_SCALAR, float);
|
||||||
|
|
||||||
@@ -296,7 +296,7 @@ SN_MK_PROC_DECL_STD(float, avx, , scalar_mul)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , scalar_mul)
|
NIF_MK_PROC_DECL_STD(float, 512, , scalar_mul)
|
||||||
{
|
{
|
||||||
__mk_param_std( RIGHT_ANS_SCALAR, float);
|
__mk_param_std( RIGHT_ANS_SCALAR, float);
|
||||||
|
|
||||||
@@ -308,7 +308,7 @@ SN_MK_PROC_DECL_STD(float, 512, , scalar_mul)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , scalar_mul)
|
NIF_MK_PROC_DECL_STD(double, sse, , scalar_mul)
|
||||||
{
|
{
|
||||||
__mk_param_std( RIGHT_ANS_SCALAR, double);
|
__mk_param_std( RIGHT_ANS_SCALAR, double);
|
||||||
|
|
||||||
@@ -334,7 +334,7 @@ SN_MK_PROC_DECL_STD(double, sse, , scalar_mul)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , scalar_mul)
|
NIF_MK_PROC_DECL_STD(double, avx, , scalar_mul)
|
||||||
{
|
{
|
||||||
__mk_param_std( RIGHT_ANS_SCALAR, double);
|
__mk_param_std( RIGHT_ANS_SCALAR, double);
|
||||||
|
|
||||||
@@ -352,7 +352,7 @@ SN_MK_PROC_DECL_STD(double, avx, , scalar_mul)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , scalar_mul)
|
NIF_MK_PROC_DECL_STD(double, 512, , scalar_mul)
|
||||||
{
|
{
|
||||||
__mk_param_std( RIGHT_ANS_SCALAR, double);
|
__mk_param_std( RIGHT_ANS_SCALAR, double);
|
||||||
|
|
||||||
@@ -1,15 +1,15 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
|
|
||||||
static const float quality_threshold = 1e-6f;
|
static const float quality_threshold = 1e-6f;
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , try_plu)
|
NIF_MK_PROC_DECL_STD(float, sse, , try_plu)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS_SCALAR, float);
|
__mk_param_std(LEFT_RIGHT_ANS_SCALAR, float);
|
||||||
|
|
||||||
@@ -115,7 +115,7 @@ SN_MK_PROC_DECL_STD(float, sse, , try_plu)
|
|||||||
* layout of scalarpack:
|
* layout of scalarpack:
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , quality)
|
NIF_MK_PROC_DECL_STD(float, sse, , quality)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS, float);
|
__mk_param_std(RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -126,7 +126,7 @@ SN_MK_PROC_DECL_STD(float, sse, , quality)
|
|||||||
register __m128 col2 = _mm_load_ps((float *)&right->x[2]);
|
register __m128 col2 = _mm_load_ps((float *)&right->x[2]);
|
||||||
register __m128 col3 = _mm_load_ps((float *)&right->x[3]);
|
register __m128 col3 = _mm_load_ps((float *)&right->x[3]);
|
||||||
|
|
||||||
SN_ALIGNAS(16) float self_dot_src[4] = { 0.0f, 0.0f, 0.0f, 0.0f };
|
NIF_ALIGNAS(16) float self_dot_src[4] = { 0.0f, 0.0f, 0.0f, 0.0f };
|
||||||
// try in reigister mix later
|
// try in reigister mix later
|
||||||
DOT_F32_SSE(col0, col0, self_dot_src[0]);
|
DOT_F32_SSE(col0, col0, self_dot_src[0]);
|
||||||
DOT_F32_SSE(col1, col1, self_dot_src[1]);
|
DOT_F32_SSE(col1, col1, self_dot_src[1]);
|
||||||
@@ -153,7 +153,7 @@ SN_MK_PROC_DECL_STD(float, sse, , quality)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_ALIGNAS(16) float cross_dot_src[2][4] = { 0 };
|
NIF_ALIGNAS(16) float cross_dot_src[2][4] = { 0 };
|
||||||
DOT_F32_SSE(col0, col1, cross_dot_src[0][0]);
|
DOT_F32_SSE(col0, col1, cross_dot_src[0][0]);
|
||||||
DOT_F32_SSE(col0, col2, cross_dot_src[0][1]);
|
DOT_F32_SSE(col0, col2, cross_dot_src[0][1]);
|
||||||
DOT_F32_SSE(col0, col3, cross_dot_src[0][2]);
|
DOT_F32_SSE(col0, col3, cross_dot_src[0][2]);
|
||||||
+8
-8
@@ -1,13 +1,13 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
|
|
||||||
// Matrix transpose implementations
|
// Matrix transpose implementations
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , transpose)
|
NIF_MK_PROC_DECL_STD(float, sse, , transpose)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS, float);
|
__mk_param_std(RIGHT_ANS, float);
|
||||||
|
|
||||||
@@ -26,7 +26,7 @@ SN_MK_PROC_DECL_STD(float, sse, , transpose)
|
|||||||
ans->x[3] = _mm_movehl_ps(tmp3, tmp1);
|
ans->x[3] = _mm_movehl_ps(tmp3, tmp1);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , transpose)
|
NIF_MK_PROC_DECL_STD(float, avx, , transpose)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS, float);
|
__mk_param_std(RIGHT_ANS, float);
|
||||||
register __m256 col_low = right->y[0];
|
register __m256 col_low = right->y[0];
|
||||||
@@ -42,7 +42,7 @@ SN_MK_PROC_DECL_STD(float, avx, , transpose)
|
|||||||
ans->y[1] = _mm256_shuffle_ps(col_high, col_low, _MM_SHUFFLE(3, 1, 3, 1));
|
ans->y[1] = _mm256_shuffle_ps(col_high, col_low, _MM_SHUFFLE(3, 1, 3, 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , transpose)
|
NIF_MK_PROC_DECL_STD(float, 512, , transpose)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS, float);
|
__mk_param_std(RIGHT_ANS, float);
|
||||||
register __m512 matrix = right->z[0];
|
register __m512 matrix = right->z[0];
|
||||||
@@ -1,8 +1,8 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* pack left matrix data to L4 buffer
|
* pack left matrix data to L4 buffer
|
||||||
@@ -19,14 +19,14 @@
|
|||||||
* scalar pack carries column length and offset data:
|
* scalar pack carries column length and offset data:
|
||||||
* [column length, empty, empty, empty]
|
* [column length, empty, empty, empty]
|
||||||
*/
|
*/
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma_pack_left)
|
NIF_MK_PROC_DECL_STD(float, sse, , fma_pack_left)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
// for SSE branch, no need for rounding, a direct copy is sufficient as long as the buffer is large enough to hold the packed data
|
// for SSE branch, no need for rounding, a direct copy is sufficient as long as the buffer is large enough to hold the packed data
|
||||||
memcpy(ans, right + offset_1, sizeof(MAT_KERNEL(float)) * count_2);
|
memcpy(ans, right + offset_1, sizeof(MAT_KERNEL(float)) * count_2);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma_pack_left)
|
NIF_MK_PROC_DECL_STD(float, avx, , fma_pack_left)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
size_t i = 0;
|
size_t i = 0;
|
||||||
@@ -61,7 +61,7 @@ SN_MK_PROC_DECL_STD(float, avx, , fma_pack_left)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma_pack_left)
|
NIF_MK_PROC_DECL_STD(float, 512, , fma_pack_left)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
size_t i = 0;
|
size_t i = 0;
|
||||||
@@ -154,7 +154,7 @@ SN_MK_PROC_DECL_STD(float, 512, , fma_pack_left)
|
|||||||
* scalar pack carries column length and offset data:
|
* scalar pack carries column length and offset data:
|
||||||
* [column length, empty, empty, empty]
|
* [column length, empty, empty, empty]
|
||||||
*/
|
*/
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma_pack_right)
|
NIF_MK_PROC_DECL_STD(float, sse, , fma_pack_right)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
int col_length = scalar.i32[0];
|
int col_length = scalar.i32[0];
|
||||||
@@ -163,7 +163,7 @@ SN_MK_PROC_DECL_STD(float, sse, , fma_pack_right)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma_pack_right)
|
NIF_MK_PROC_DECL_STD(float, avx, , fma_pack_right)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
int col_length = scalar.i32[0];
|
int col_length = scalar.i32[0];
|
||||||
@@ -205,7 +205,7 @@ SN_MK_PROC_DECL_STD(float, avx, , fma_pack_right)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma_pack_right)
|
NIF_MK_PROC_DECL_STD(float, 512, , fma_pack_right)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
int col_length = scalar.i32[0];
|
int col_length = scalar.i32[0];
|
||||||
@@ -1,22 +1,22 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
#include <immintrin.h>
|
#include <immintrin.h>
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
// #include "sn_intrinsic.h"
|
// #include "nif_intrinsic.h"
|
||||||
#include "sn_template.fma.x86.h"
|
#include "nif_template.fma.x86.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
#define _FMA_SELECT(i) _MM_SHUFFLE(i, i, i, i)
|
#define _FMA_SELECT(i) _MM_SHUFFLE(i, i, i, i)
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , fma)
|
NIF_MK_PROC_DECL_STD(float, sse, , fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
|
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
|
|
||||||
register __m128 c0 = _mm_load_ps((float *)&ans_cur->x[0]);
|
register __m128 c0 = _mm_load_ps((float *)&ans_cur->x[0]);
|
||||||
register __m128 c1 = _mm_load_ps((float *)&ans_cur->x[1]);
|
register __m128 c1 = _mm_load_ps((float *)&ans_cur->x[1]);
|
||||||
@@ -25,8 +25,8 @@ SN_MK_PROC_DECL_STD(float, sse, , fma)
|
|||||||
register __m128 bcol;
|
register __m128 bcol;
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z++) {
|
for (size_t z = 0; z < count_0; z++) {
|
||||||
SN_MAT_KERNEL_LOCAL const *right_base = right;
|
NIF_MAT_KERNEL_LOCAL const *right_base = right;
|
||||||
SN_MAT_KERNEL_LOCAL const *left_base = left;
|
NIF_MAT_KERNEL_LOCAL const *left_base = left;
|
||||||
|
|
||||||
const __m128 a0 = _mm_load_ps((float *)&left_base->x[0]);
|
const __m128 a0 = _mm_load_ps((float *)&left_base->x[0]);
|
||||||
const __m128 a1 = _mm_load_ps((float *)&left_base->x[1]);
|
const __m128 a1 = _mm_load_ps((float *)&left_base->x[1]);
|
||||||
@@ -68,18 +68,18 @@ SN_MK_PROC_DECL_STD(float, sse, , fma)
|
|||||||
_mm_store_ps((float *)&ans_cur->x[3], c3);
|
_mm_store_ps((float *)&ans_cur->x[3], c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, , fma)
|
NIF_MK_PROC_DECL_STD(float, avx, , fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
register __m256 c0 = _mm256_load_ps((float *)&ans_cur->y[0]);
|
register __m256 c0 = _mm256_load_ps((float *)&ans_cur->y[0]);
|
||||||
register __m256 c1 = _mm256_load_ps((float *)&ans_cur->y[1]);
|
register __m256 c1 = _mm256_load_ps((float *)&ans_cur->y[1]);
|
||||||
register __m256 c2 = _mm256_load_ps((float *)&ans_cur->y[2]);
|
register __m256 c2 = _mm256_load_ps((float *)&ans_cur->y[2]);
|
||||||
register __m256 c3 = _mm256_load_ps((float *)&ans_cur->y[3]);
|
register __m256 c3 = _mm256_load_ps((float *)&ans_cur->y[3]);
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z++) {
|
for (size_t z = 0; z < count_0; z++) {
|
||||||
SN_MAT_KERNEL_LOCAL const *b_base = right;
|
NIF_MAT_KERNEL_LOCAL const *b_base = right;
|
||||||
SN_MAT_KERNEL_LOCAL const *a_base = left;
|
NIF_MAT_KERNEL_LOCAL const *a_base = left;
|
||||||
|
|
||||||
register __m256 b0 = _mm256_load_ps((float *)&b_base->y[0]);
|
register __m256 b0 = _mm256_load_ps((float *)&b_base->y[0]);
|
||||||
register __m256 b1 = _mm256_load_ps((float *)&b_base->y[1]);
|
register __m256 b1 = _mm256_load_ps((float *)&b_base->y[1]);
|
||||||
@@ -91,10 +91,10 @@ SN_MK_PROC_DECL_STD(float, avx, , fma)
|
|||||||
register __m256 a2 = _mm256_load_ps((float *)&a_base->y[2]);
|
register __m256 a2 = _mm256_load_ps((float *)&a_base->y[2]);
|
||||||
register __m256 a3 = _mm256_load_ps((float *)&a_base->y[3]);
|
register __m256 a3 = _mm256_load_ps((float *)&a_base->y[3]);
|
||||||
|
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(0);
|
NIF_MK_FMA_F32_AVX2_CYCLE(0);
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(1);
|
NIF_MK_FMA_F32_AVX2_CYCLE(1);
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(2);
|
NIF_MK_FMA_F32_AVX2_CYCLE(2);
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(3);
|
NIF_MK_FMA_F32_AVX2_CYCLE(3);
|
||||||
}
|
}
|
||||||
_mm256_store_ps((float *)&(ans_cur->y[0]), c0);
|
_mm256_store_ps((float *)&(ans_cur->y[0]), c0);
|
||||||
_mm256_store_ps((float *)&(ans_cur->y[1]), c1);
|
_mm256_store_ps((float *)&(ans_cur->y[1]), c1);
|
||||||
@@ -102,18 +102,18 @@ SN_MK_PROC_DECL_STD(float, avx, , fma)
|
|||||||
_mm256_store_ps((float *)&(ans_cur->y[3]), c3);
|
_mm256_store_ps((float *)&(ans_cur->y[3]), c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, avx, _fma, fma)
|
NIF_MK_PROC_DECL_STD(float, avx, _fma, fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
register __m256 c0 = _mm256_load_ps((float *)&ans_cur->y[0]);
|
register __m256 c0 = _mm256_load_ps((float *)&ans_cur->y[0]);
|
||||||
register __m256 c1 = _mm256_load_ps((float *)&ans_cur->y[1]);
|
register __m256 c1 = _mm256_load_ps((float *)&ans_cur->y[1]);
|
||||||
register __m256 c2 = _mm256_load_ps((float *)&ans_cur->y[2]);
|
register __m256 c2 = _mm256_load_ps((float *)&ans_cur->y[2]);
|
||||||
register __m256 c3 = _mm256_load_ps((float *)&ans_cur->y[3]);
|
register __m256 c3 = _mm256_load_ps((float *)&ans_cur->y[3]);
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z += 2) {
|
for (size_t z = 0; z < count_0; z += 2) {
|
||||||
const SN_MAT_KERNEL_LOCAL *a_base = left + z;
|
const NIF_MAT_KERNEL_LOCAL *a_base = left + z;
|
||||||
const SN_MAT_KERNEL_LOCAL *b_base = right + z;
|
const NIF_MAT_KERNEL_LOCAL *b_base = right + z;
|
||||||
|
|
||||||
register __m256 b0 = _mm256_load_ps((float *)&b_base->y[0]);
|
register __m256 b0 = _mm256_load_ps((float *)&b_base->y[0]);
|
||||||
register __m256 b1 = _mm256_load_ps((float *)&b_base->y[1]);
|
register __m256 b1 = _mm256_load_ps((float *)&b_base->y[1]);
|
||||||
@@ -125,10 +125,10 @@ SN_MK_PROC_DECL_STD(float, avx, _fma, fma)
|
|||||||
register __m256 a2 = _mm256_load_ps((float *)&a_base->y[2]);
|
register __m256 a2 = _mm256_load_ps((float *)&a_base->y[2]);
|
||||||
register __m256 a3 = _mm256_load_ps((float *)&a_base->y[3]);
|
register __m256 a3 = _mm256_load_ps((float *)&a_base->y[3]);
|
||||||
|
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(0);
|
NIF_MK_FMA_F32_AVX2_CYCLE(0);
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(1);
|
NIF_MK_FMA_F32_AVX2_CYCLE(1);
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(2);
|
NIF_MK_FMA_F32_AVX2_CYCLE(2);
|
||||||
SN_MK_FMA_F32_AVX2_CYCLE(3);
|
NIF_MK_FMA_F32_AVX2_CYCLE(3);
|
||||||
}
|
}
|
||||||
_mm256_store_ps((float *)&(ans_cur->y[0]), c0);
|
_mm256_store_ps((float *)&(ans_cur->y[0]), c0);
|
||||||
_mm256_store_ps((float *)&(ans_cur->y[1]), c1);
|
_mm256_store_ps((float *)&(ans_cur->y[1]), c1);
|
||||||
@@ -136,18 +136,18 @@ SN_MK_PROC_DECL_STD(float, avx, _fma, fma)
|
|||||||
_mm256_store_ps((float *)&(ans_cur->y[3]), c3);
|
_mm256_store_ps((float *)&(ans_cur->y[3]), c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, 512, , fma)
|
NIF_MK_PROC_DECL_STD(float, 512, , fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, float);
|
__mk_param_std(LEFT_RIGHT_ANS, float);
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
register __m512 c0 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
register __m512 c0 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
||||||
register __m512 c1 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
register __m512 c1 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
||||||
register __m512 c2 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
register __m512 c2 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
||||||
register __m512 c3 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
register __m512 c3 = _mm512_load_ps((float *)&ans_cur->z[0]);
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z += 4) {
|
for (size_t z = 0; z < count_0; z += 4) {
|
||||||
const SN_MAT_KERNEL_LOCAL *a_base = left + z;
|
const NIF_MAT_KERNEL_LOCAL *a_base = left + z;
|
||||||
const SN_MAT_KERNEL_LOCAL *b_base = right + z;
|
const NIF_MAT_KERNEL_LOCAL *b_base = right + z;
|
||||||
|
|
||||||
register __m512 b0 = _mm512_load_ps((float *)&b_base->z[0]);
|
register __m512 b0 = _mm512_load_ps((float *)&b_base->z[0]);
|
||||||
register __m512 b1 = _mm512_load_ps((float *)&b_base->z[1]);
|
register __m512 b1 = _mm512_load_ps((float *)&b_base->z[1]);
|
||||||
@@ -159,10 +159,10 @@ SN_MK_PROC_DECL_STD(float, 512, , fma)
|
|||||||
register __m512 a2 = _mm512_load_ps((float *)&a_base->z[2]);
|
register __m512 a2 = _mm512_load_ps((float *)&a_base->z[2]);
|
||||||
register __m512 a3 = _mm512_load_ps((float *)&a_base->z[3]);
|
register __m512 a3 = _mm512_load_ps((float *)&a_base->z[3]);
|
||||||
|
|
||||||
SN_MK_FMA_F32_512_CYCLE(0);
|
NIF_MK_FMA_F32_512_CYCLE(0);
|
||||||
SN_MK_FMA_F32_512_CYCLE(1);
|
NIF_MK_FMA_F32_512_CYCLE(1);
|
||||||
SN_MK_FMA_F32_512_CYCLE(2);
|
NIF_MK_FMA_F32_512_CYCLE(2);
|
||||||
SN_MK_FMA_F32_512_CYCLE(3);
|
NIF_MK_FMA_F32_512_CYCLE(3);
|
||||||
}
|
}
|
||||||
_mm512_store_ps((float *)&ans_cur->z[0], c0);
|
_mm512_store_ps((float *)&ans_cur->z[0], c0);
|
||||||
_mm512_store_ps((float *)&ans_cur->z[1], c1);
|
_mm512_store_ps((float *)&ans_cur->z[1], c1);
|
||||||
@@ -170,11 +170,11 @@ SN_MK_PROC_DECL_STD(float, 512, , fma)
|
|||||||
_mm512_store_ps((float *)&ans_cur->z[3], c3);
|
_mm512_store_ps((float *)&ans_cur->z[3], c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, sse, , fma)
|
NIF_MK_PROC_DECL_STD(double, sse, , fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, double);
|
__mk_param_std(LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
|
|
||||||
register __m128d c0_lo = ans_cur->x[0];
|
register __m128d c0_lo = ans_cur->x[0];
|
||||||
register __m128d c0_hi = ans_cur->x[1];
|
register __m128d c0_hi = ans_cur->x[1];
|
||||||
@@ -186,18 +186,18 @@ SN_MK_PROC_DECL_STD(double, sse, , fma)
|
|||||||
register __m128d c3_hi = ans_cur->x[7];
|
register __m128d c3_hi = ans_cur->x[7];
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z++) {
|
for (size_t z = 0; z < count_0; z++) {
|
||||||
SN_MAT_KERNEL_LOCAL const *right_base = right;
|
NIF_MAT_KERNEL_LOCAL const *right_base = right;
|
||||||
SN_MAT_KERNEL_LOCAL const *left_base = left;
|
NIF_MAT_KERNEL_LOCAL const *left_base = left;
|
||||||
const double *right_values = &right_base->m[0][0];
|
const double *right_values = &right_base->m[0][0];
|
||||||
const double *left_values = &left_base->m[0][0];
|
const double *left_values = &left_base->m[0][0];
|
||||||
|
|
||||||
SN_MK_FMA_F64_SSE_PHASE(0);
|
NIF_MK_FMA_F64_SSE_PHASE(0);
|
||||||
|
|
||||||
SN_MK_FMA_F64_SSE_PHASE(1);
|
NIF_MK_FMA_F64_SSE_PHASE(1);
|
||||||
|
|
||||||
SN_MK_FMA_F64_SSE_PHASE(2);
|
NIF_MK_FMA_F64_SSE_PHASE(2);
|
||||||
|
|
||||||
SN_MK_FMA_F64_SSE_PHASE(3);
|
NIF_MK_FMA_F64_SSE_PHASE(3);
|
||||||
}
|
}
|
||||||
|
|
||||||
ans_cur->x[0] = c0_lo;
|
ans_cur->x[0] = c0_lo;
|
||||||
@@ -210,11 +210,11 @@ SN_MK_PROC_DECL_STD(double, sse, , fma)
|
|||||||
ans_cur->x[7] = c3_hi;
|
ans_cur->x[7] = c3_hi;
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, avx, , fma)
|
NIF_MK_PROC_DECL_STD(double, avx, , fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, double);
|
__mk_param_std(LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
|
|
||||||
register __m256d c0 = _mm256_load_pd((double *)&ans_cur->y[0]);
|
register __m256d c0 = _mm256_load_pd((double *)&ans_cur->y[0]);
|
||||||
register __m256d c1 = _mm256_load_pd((double *)&ans_cur->y[1]);
|
register __m256d c1 = _mm256_load_pd((double *)&ans_cur->y[1]);
|
||||||
@@ -223,8 +223,8 @@ SN_MK_PROC_DECL_STD(double, avx, , fma)
|
|||||||
register __m256d bcol;
|
register __m256d bcol;
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z++) {
|
for (size_t z = 0; z < count_0; z++) {
|
||||||
SN_MAT_KERNEL_LOCAL const *right_base = right;
|
NIF_MAT_KERNEL_LOCAL const *right_base = right;
|
||||||
SN_MAT_KERNEL_LOCAL const *left_base = left;
|
NIF_MAT_KERNEL_LOCAL const *left_base = left;
|
||||||
|
|
||||||
const __m256d a0 = _mm256_load_pd((double *)&left_base->y[0]);
|
const __m256d a0 = _mm256_load_pd((double *)&left_base->y[0]);
|
||||||
const __m256d a1 = _mm256_load_pd((double *)&left_base->y[1]);
|
const __m256d a1 = _mm256_load_pd((double *)&left_base->y[1]);
|
||||||
@@ -282,11 +282,11 @@ SN_MK_PROC_DECL_STD(double, avx, , fma)
|
|||||||
_mm256_store_pd((double *)&ans_cur->y[3], c3);
|
_mm256_store_pd((double *)&ans_cur->y[3], c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, avx, _fma, fma)
|
NIF_MK_PROC_DECL_STD(double, avx, _fma, fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, double);
|
__mk_param_std(LEFT_RIGHT_ANS, double);
|
||||||
|
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
|
|
||||||
register __m256d c0 = _mm256_load_pd((double *)&ans_cur->y[0]);
|
register __m256d c0 = _mm256_load_pd((double *)&ans_cur->y[0]);
|
||||||
register __m256d c1 = _mm256_load_pd((double *)&ans_cur->y[1]);
|
register __m256d c1 = _mm256_load_pd((double *)&ans_cur->y[1]);
|
||||||
@@ -295,8 +295,8 @@ SN_MK_PROC_DECL_STD(double, avx, _fma, fma)
|
|||||||
register __m256d bcol;
|
register __m256d bcol;
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z++) {
|
for (size_t z = 0; z < count_0; z++) {
|
||||||
SN_MAT_KERNEL_LOCAL const *right_base = right;
|
NIF_MAT_KERNEL_LOCAL const *right_base = right;
|
||||||
SN_MAT_KERNEL_LOCAL const *left_base = left;
|
NIF_MAT_KERNEL_LOCAL const *left_base = left;
|
||||||
|
|
||||||
const __m256d a0 = _mm256_load_pd((double *)&left_base->y[0]);
|
const __m256d a0 = _mm256_load_pd((double *)&left_base->y[0]);
|
||||||
const __m256d a1 = _mm256_load_pd((double *)&left_base->y[1]);
|
const __m256d a1 = _mm256_load_pd((double *)&left_base->y[1]);
|
||||||
@@ -338,10 +338,10 @@ SN_MK_PROC_DECL_STD(double, avx, _fma, fma)
|
|||||||
_mm256_store_pd((double *)&ans_cur->y[3], c3);
|
_mm256_store_pd((double *)&ans_cur->y[3], c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(double, 512, , fma)
|
NIF_MK_PROC_DECL_STD(double, 512, , fma)
|
||||||
{
|
{
|
||||||
__mk_param_std(LEFT_RIGHT_ANS, double);
|
__mk_param_std(LEFT_RIGHT_ANS, double);
|
||||||
SN_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
NIF_MAT_KERNEL_LOCAL *restrict ans_cur = ans + offset_2;
|
||||||
|
|
||||||
register __m512d c0 = _mm512_load_pd((double *)&ans_cur->z[0]);
|
register __m512d c0 = _mm512_load_pd((double *)&ans_cur->z[0]);
|
||||||
register __m512d c1 = _mm512_load_pd((double *)&ans_cur->z[1]);
|
register __m512d c1 = _mm512_load_pd((double *)&ans_cur->z[1]);
|
||||||
@@ -349,8 +349,8 @@ SN_MK_PROC_DECL_STD(double, 512, , fma)
|
|||||||
register __m512d c3 = _mm512_load_pd((double *)&ans_cur->z[3]);
|
register __m512d c3 = _mm512_load_pd((double *)&ans_cur->z[3]);
|
||||||
|
|
||||||
for (size_t z = 0; z < count_0; z += 2) {
|
for (size_t z = 0; z < count_0; z += 2) {
|
||||||
SN_MAT_KERNEL_LOCAL const *right_base = right + z;
|
NIF_MAT_KERNEL_LOCAL const *right_base = right + z;
|
||||||
SN_MAT_KERNEL_LOCAL const *left_base = left + z;
|
NIF_MAT_KERNEL_LOCAL const *left_base = left + z;
|
||||||
|
|
||||||
register __m512d a0 = _mm512_load_pd((double *)&left_base->z[0]);
|
register __m512d a0 = _mm512_load_pd((double *)&left_base->z[0]);
|
||||||
register __m512d a1 = _mm512_load_pd((double *)&left_base->z[1]);
|
register __m512d a1 = _mm512_load_pd((double *)&left_base->z[1]);
|
||||||
@@ -362,10 +362,10 @@ SN_MK_PROC_DECL_STD(double, 512, , fma)
|
|||||||
register __m512d b2 = _mm512_load_pd((double *)&right_base->z[2]);
|
register __m512d b2 = _mm512_load_pd((double *)&right_base->z[2]);
|
||||||
register __m512d b3 = _mm512_load_pd((double *)&right_base->z[3]);
|
register __m512d b3 = _mm512_load_pd((double *)&right_base->z[3]);
|
||||||
|
|
||||||
SN_MK_FMA_F64_AVX2_CYCLE(0);
|
NIF_MK_FMA_F64_AVX2_CYCLE(0);
|
||||||
SN_MK_FMA_F64_AVX2_CYCLE(1);
|
NIF_MK_FMA_F64_AVX2_CYCLE(1);
|
||||||
SN_MK_FMA_F64_AVX2_CYCLE(2);
|
NIF_MK_FMA_F64_AVX2_CYCLE(2);
|
||||||
SN_MK_FMA_F64_AVX2_CYCLE(3);
|
NIF_MK_FMA_F64_AVX2_CYCLE(3);
|
||||||
}
|
}
|
||||||
_mm512_store_pd((double *)&ans_cur->z[0], c0);
|
_mm512_store_pd((double *)&ans_cur->z[0], c0);
|
||||||
_mm512_store_pd((double *)&ans_cur->z[1], c1);
|
_mm512_store_pd((double *)&ans_cur->z[1], c1);
|
||||||
+10
-10
@@ -1,25 +1,25 @@
|
|||||||
|
|
||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_internal.h"
|
#include "nif_internal.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.matkernel.h"
|
#include "nif_intrinsic.matkernel.h"
|
||||||
#include <emmintrin.h>
|
#include <emmintrin.h>
|
||||||
#include <immintrin.h>
|
#include <immintrin.h>
|
||||||
#include <pmmintrin.h>
|
#include <pmmintrin.h>
|
||||||
|
|
||||||
SN_MK_PROC_DECL_STD(float, sse, , k_quality)
|
NIF_MK_PROC_DECL_STD(float, sse, , k_quality)
|
||||||
{
|
{
|
||||||
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
__mk_param_std(RIGHT_ANS_SCALAR, float);
|
||||||
}
|
}
|
||||||
|
|
||||||
INTERNAL SN_STD_TARGET_ATTR(sse, ) void kp_check_f32(mat_kernel *kernel)
|
INTERNAL NIF_STD_TARGET_ATTR(sse, ) void kp_check_f32(mat_kernel *kernel)
|
||||||
{
|
{
|
||||||
typedef MAT_KERNEL(float) SN_MAT;
|
typedef MAT_KERNEL(float) NIF_MAT;
|
||||||
SN_MAT const *k = (SN_MAT const *)kernel;
|
NIF_MAT const *k = (NIF_MAT const *)kernel;
|
||||||
float cross[4];
|
float cross[4];
|
||||||
cross[0] = k->m[0][0];
|
cross[0] = k->m[0][0];
|
||||||
cross[1] = k->m[1][1];
|
cross[1] = k->m[1][1];
|
||||||
+6
-6
@@ -1,14 +1,14 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_internal.h"
|
#include "nif_internal.h"
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
|
|
||||||
static __m128i facIncrement;
|
static __m128i facIncrement;
|
||||||
static __m128i facBase;
|
static __m128i facBase;
|
||||||
|
|
||||||
INTERNAL uint64_t SN_DECL factorial_simd_sse(int n)
|
INTERNAL uint64_t NIF_DECL factorial_simd_sse(int n)
|
||||||
{
|
{
|
||||||
facIncrement = _mm_set1_epi32(4);
|
facIncrement = _mm_set1_epi32(4);
|
||||||
facBase = _mm_setr_epi32(1, 2, 3, 4);
|
facBase = _mm_setr_epi32(1, 2, 3, 4);
|
||||||
@@ -20,7 +20,7 @@ INTERNAL uint64_t SN_DECL factorial_simd_sse(int n)
|
|||||||
facBaseLocal = _mm_add_epi32(facBaseLocal, facIncrement);
|
facBaseLocal = _mm_add_epi32(facBaseLocal, facIncrement);
|
||||||
baseResult = _mm_mullo_epi32(baseResult, facBaseLocal);
|
baseResult = _mm_mullo_epi32(baseResult, facBaseLocal);
|
||||||
}
|
}
|
||||||
SN_ALIGNAS(16) int32_t lanes[4];
|
NIF_ALIGNAS(16) int32_t lanes[4];
|
||||||
_mm_store_si128((__m128i *)lanes, baseResult);
|
_mm_store_si128((__m128i *)lanes, baseResult);
|
||||||
uint64_t result = (uint64_t)lanes[0] * (uint64_t)lanes[1] * (uint64_t)lanes[2] *
|
uint64_t result = (uint64_t)lanes[0] * (uint64_t)lanes[1] * (uint64_t)lanes[2] *
|
||||||
(uint64_t)lanes[3];
|
(uint64_t)lanes[3];
|
||||||
@@ -1,10 +1,10 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
|
|
||||||
INTERNAL int SN_DECL city_hash_simplify_sse(byte const *str, int const length)
|
INTERNAL int NIF_DECL city_hash_simplify_sse(byte const *str, int const length)
|
||||||
{
|
{
|
||||||
uint32_t hash = length, size = length << 1;
|
uint32_t hash = length, size = length << 1;
|
||||||
byte const *end = str + size;
|
byte const *end = str + size;
|
||||||
@@ -1,13 +1,13 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
/* clang-format off */
|
/* clang-format off */
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
static SIMDID global_simdid = { 0 };
|
static SIMDID global_simdid = { 0 };
|
||||||
|
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
#include <immintrin.h>
|
#include <immintrin.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
@@ -126,7 +126,7 @@ static int is_amd_glue_ymm(const char *vendor, int cpuid1_eax)
|
|||||||
return (family == 0x17) && (model < 0x30);
|
return (family == 0x17) && (model < 0x30);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API SIMDID SN_DECL sn_get_simd_level_local()
|
NIF_API SIMDID NIF_DECL nif_get_simd_level_local()
|
||||||
{
|
{
|
||||||
SIMDID simdid = { 0 };
|
SIMDID simdid = { 0 };
|
||||||
|
|
||||||
@@ -314,13 +314,13 @@ SN_API SIMDID SN_DECL sn_get_simd_level_local()
|
|||||||
return simdid;
|
return simdid;
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API SIMDID SN_DECL sn_get_simd_level_global()
|
NIF_API SIMDID NIF_DECL nif_get_simd_level_global()
|
||||||
{
|
{
|
||||||
if (global_simdid.mask) {
|
if (global_simdid.mask) {
|
||||||
return global_simdid;
|
return global_simdid;
|
||||||
}
|
}
|
||||||
|
|
||||||
global_simdid = sn_get_simd_level_local();
|
global_simdid = nif_get_simd_level_local();
|
||||||
return global_simdid;
|
return global_simdid;
|
||||||
}
|
}
|
||||||
|
|
||||||
+8
-8
@@ -1,9 +1,9 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
/* -----------------------------------------------------------------------
|
/* -----------------------------------------------------------------------
|
||||||
* Field extraction helpers.
|
* Field extraction helpers.
|
||||||
@@ -49,7 +49,7 @@ static int impl_strength(uint16_t avx512)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* -----------------------------------------------------------------------
|
/* -----------------------------------------------------------------------
|
||||||
* sn_get_unite_simd
|
* nif_get_unite_simd
|
||||||
*
|
*
|
||||||
* Produce the conservative intersection of two SIMDIDs — the strongest
|
* Produce the conservative intersection of two SIMDIDs — the strongest
|
||||||
* capability set that is safe to use on BOTH cores:
|
* capability set that is safe to use on BOTH cores:
|
||||||
@@ -60,7 +60,7 @@ static int impl_strength(uint16_t avx512)
|
|||||||
* - Root / Manu : keep left (must be same arch in practice)
|
* - Root / Manu : keep left (must be same arch in practice)
|
||||||
* - uArchHi : bitwise OR (HYBRID_P/E union; SIMD_DUAL set if either core is dual)
|
* - uArchHi : bitwise OR (HYBRID_P/E union; SIMD_DUAL set if either core is dual)
|
||||||
* ----------------------------------------------------------------------- */
|
* ----------------------------------------------------------------------- */
|
||||||
SN_API SIMDID SN_DECL sn_get_unite_simd(SIMDID left, SIMDID right)
|
NIF_API SIMDID NIF_DECL nif_get_unite_simd(SIMDID left, SIMDID right)
|
||||||
{
|
{
|
||||||
SIMDID out;
|
SIMDID out;
|
||||||
out.mask = 0;
|
out.mask = 0;
|
||||||
@@ -117,7 +117,7 @@ SN_API SIMDID SN_DECL sn_get_unite_simd(SIMDID left, SIMDID right)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* -----------------------------------------------------------------------
|
/* -----------------------------------------------------------------------
|
||||||
* sn_compare_simd
|
* nif_compare_simd
|
||||||
*
|
*
|
||||||
* Compare two SIMDIDs by ISA strength. Returns:
|
* Compare two SIMDIDs by ISA strength. Returns:
|
||||||
* +1 if left is strictly stronger than right
|
* +1 if left is strictly stronger than right
|
||||||
@@ -154,7 +154,7 @@ SN_API SIMDID SN_DECL sn_get_unite_simd(SIMDID left, SIMDID right)
|
|||||||
* 7. uArchHi SIMD_DUAL (final tie-break)
|
* 7. uArchHi SIMD_DUAL (final tie-break)
|
||||||
* Non-dual (SIMD_DUAL=0) > dual (SIMD_DUAL=1).
|
* Non-dual (SIMD_DUAL=0) > dual (SIMD_DUAL=1).
|
||||||
* ----------------------------------------------------------------------- */
|
* ----------------------------------------------------------------------- */
|
||||||
SN_API int SN_DECL sn_compare_simd(SIMDID left, SIMDID right)
|
NIF_API int NIF_DECL nif_compare_simd(SIMDID left, SIMDID right)
|
||||||
{
|
{
|
||||||
/* 1. MainLevel */
|
/* 1. MainLevel */
|
||||||
unsigned lm = FIELD_MAIN(left);
|
unsigned lm = FIELD_MAIN(left);
|
||||||
@@ -1,10 +1,10 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_intrinsic.std.h"
|
#include "nif_intrinsic.std.h"
|
||||||
#include "sn_intrinsic.context.x86.h"
|
#include "nif_intrinsic.context.x86.h"
|
||||||
|
|
||||||
#define _FMA_SELECT(i) _MM_SHUFFLE(i, i, i, i)
|
#define _FMA_SELECT(i) _MM_SHUFFLE(i, i, i, i)
|
||||||
|
|
||||||
@@ -12,7 +12,7 @@
|
|||||||
|
|
||||||
// float
|
// float
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, sse, , fma)
|
NIF_SK_PROC_DECL_STD(float, sse, , fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(float);
|
__sk_param_std(float);
|
||||||
register __m128 c0 = _mm_load_ps((float *)&ans->x[0]);
|
register __m128 c0 = _mm_load_ps((float *)&ans->x[0]);
|
||||||
@@ -60,7 +60,7 @@ SN_SK_PROC_DECL_STD(float, sse, , fma)
|
|||||||
_mm_store_ps((float *)&ans->x[3], c3);
|
_mm_store_ps((float *)&ans->x[3], c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, avx, , fma)
|
NIF_SK_PROC_DECL_STD(float, avx, , fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(float);
|
__sk_param_std(float);
|
||||||
register __m256 c01 = _mm256_load_ps((float *)&ans->y[0]);
|
register __m256 c01 = _mm256_load_ps((float *)&ans->y[0]);
|
||||||
@@ -86,7 +86,7 @@ SN_SK_PROC_DECL_STD(float, avx, , fma)
|
|||||||
_mm256_store_ps((float *)&ans->y[1], c23);
|
_mm256_store_ps((float *)&ans->y[1], c23);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, avx, _fma, fma)
|
NIF_SK_PROC_DECL_STD(float, avx, _fma, fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(float);
|
__sk_param_std(float);
|
||||||
register __m256 c01 = _mm256_load_ps((float *)&ans->y[0]);
|
register __m256 c01 = _mm256_load_ps((float *)&ans->y[0]);
|
||||||
@@ -112,7 +112,7 @@ SN_SK_PROC_DECL_STD(float, avx, _fma, fma)
|
|||||||
_mm256_store_ps((float *)&ans->y[1], c23);
|
_mm256_store_ps((float *)&ans->y[1], c23);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(float, 512, , fma)
|
NIF_SK_PROC_DECL_STD(float, 512, , fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(float);
|
__sk_param_std(float);
|
||||||
register __m512 c = _mm512_load_ps((float *)ans);
|
register __m512 c = _mm512_load_ps((float *)ans);
|
||||||
@@ -173,7 +173,7 @@ SN_SK_PROC_DECL_STD(float, 512, , fma)
|
|||||||
|
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, sse, , fma)
|
NIF_SK_PROC_DECL_STD(double, sse, , fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(double);
|
__sk_param_std(double);
|
||||||
const double *left_values = &left->m[0][0];
|
const double *left_values = &left->m[0][0];
|
||||||
@@ -204,7 +204,7 @@ SN_SK_PROC_DECL_STD(double, sse, , fma)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// clang-format off
|
// clang-format off
|
||||||
SN_SK_PROC_DECL_STD(double, avx, , fma)
|
NIF_SK_PROC_DECL_STD(double, avx, , fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(double);
|
__sk_param_std(double);
|
||||||
register __m256d c0 = _mm256_load_pd((double *)&ans->y[0]);
|
register __m256d c0 = _mm256_load_pd((double *)&ans->y[0]);
|
||||||
@@ -253,7 +253,7 @@ SN_SK_PROC_DECL_STD(double, avx, , fma)
|
|||||||
}
|
}
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, avx, _fma, fma)
|
NIF_SK_PROC_DECL_STD(double, avx, _fma, fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(double);
|
__sk_param_std(double);
|
||||||
register __m256d c0 = _mm256_load_pd((double *)&ans->y[0]);
|
register __m256d c0 = _mm256_load_pd((double *)&ans->y[0]);
|
||||||
@@ -301,7 +301,7 @@ SN_SK_PROC_DECL_STD(double, avx, _fma, fma)
|
|||||||
_mm256_store_pd((double *)&ans->y[3], c3);
|
_mm256_store_pd((double *)&ans->y[3], c3);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_SK_PROC_DECL_STD(double, 512, , fma)
|
NIF_SK_PROC_DECL_STD(double, 512, , fma)
|
||||||
{
|
{
|
||||||
__sk_param_std(double);
|
__sk_param_std(double);
|
||||||
register __m512d c01 = _mm512_load_pd((double *)&ans->z[0]);
|
register __m512d c01 = _mm512_load_pd((double *)&ans->z[0]);
|
||||||
+51
-51
@@ -1,8 +1,8 @@
|
|||||||
#define _GNU_SOURCE
|
#define _GNU_SOURCE
|
||||||
|
|
||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_OS(SN_OS_LINUX)
|
#if NIF_IS_OS(NIF_OS_LINUX)
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <inttypes.h>
|
#include <inttypes.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
@@ -16,27 +16,27 @@
|
|||||||
#include <sys/syscall.h>
|
#include <sys/syscall.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|
||||||
typedef int (*sn_linux_id_visitor)(int value, void *context);
|
typedef int (*nif_linux_id_visitor)(int value, void *context);
|
||||||
|
|
||||||
typedef struct sn_linux_counter_context {
|
typedef struct nif_linux_counter_context {
|
||||||
int count;
|
int count;
|
||||||
} sn_linux_counter_context;
|
} nif_linux_counter_context;
|
||||||
|
|
||||||
typedef struct sn_linux_max_context {
|
typedef struct nif_linux_max_context {
|
||||||
int max_value;
|
int max_value;
|
||||||
} sn_linux_max_context;
|
} nif_linux_max_context;
|
||||||
|
|
||||||
typedef struct sn_linux_fill_cpu_context {
|
typedef struct nif_linux_fill_cpu_context {
|
||||||
uint64_t *internal;
|
uint64_t *internal;
|
||||||
uint32_t *global;
|
uint32_t *global;
|
||||||
int index;
|
int index;
|
||||||
} sn_linux_fill_cpu_context;
|
} nif_linux_fill_cpu_context;
|
||||||
|
|
||||||
typedef struct sn_linux_fill_node_count_context {
|
typedef struct nif_linux_fill_node_count_context {
|
||||||
int *count_of_each_numa;
|
int *count_of_each_numa;
|
||||||
} sn_linux_fill_node_count_context;
|
} nif_linux_fill_node_count_context;
|
||||||
|
|
||||||
static int sn_linux_read_first_line(char const *path, char *buffer, size_t buffer_size)
|
static int nif_linux_read_first_line(char const *path, char *buffer, size_t buffer_size)
|
||||||
{
|
{
|
||||||
FILE *file = fopen(path, "r");
|
FILE *file = fopen(path, "r");
|
||||||
if (file == NULL)
|
if (file == NULL)
|
||||||
@@ -47,7 +47,7 @@ static int sn_linux_read_first_line(char const *path, char *buffer, size_t buffe
|
|||||||
return line != NULL;
|
return line != NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_parse_nonnegative_int(char const **cursor, int *value)
|
static int nif_linux_parse_nonnegative_int(char const **cursor, int *value)
|
||||||
{
|
{
|
||||||
char *end = NULL;
|
char *end = NULL;
|
||||||
uintmax_t parsed_value = 0;
|
uintmax_t parsed_value = 0;
|
||||||
@@ -65,7 +65,7 @@ static int sn_linux_parse_nonnegative_int(char const **cursor, int *value)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_visit_id_list(char const *text, sn_linux_id_visitor visitor, void *context)
|
static int nif_linux_visit_id_list(char const *text, nif_linux_id_visitor visitor, void *context)
|
||||||
{
|
{
|
||||||
char const *cursor = text;
|
char const *cursor = text;
|
||||||
|
|
||||||
@@ -77,14 +77,14 @@ static int sn_linux_visit_id_list(char const *text, sn_linux_id_visitor visitor,
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
int begin = 0;
|
int begin = 0;
|
||||||
if (!sn_linux_parse_nonnegative_int(&cursor, &begin))
|
if (!nif_linux_parse_nonnegative_int(&cursor, &begin))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
int finish = begin;
|
int finish = begin;
|
||||||
|
|
||||||
if (*cursor == '-') {
|
if (*cursor == '-') {
|
||||||
cursor++;
|
cursor++;
|
||||||
if (!sn_linux_parse_nonnegative_int(&cursor, &finish))
|
if (!nif_linux_parse_nonnegative_int(&cursor, &finish))
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -103,24 +103,24 @@ static int sn_linux_visit_id_list(char const *text, sn_linux_id_visitor visitor,
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_count_id(int value, void *context)
|
static int nif_linux_count_id(int value, void *context)
|
||||||
{
|
{
|
||||||
(void)value;
|
(void)value;
|
||||||
((sn_linux_counter_context *)context)->count++;
|
((nif_linux_counter_context *)context)->count++;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_track_max_id(int value, void *context)
|
static int nif_linux_track_max_id(int value, void *context)
|
||||||
{
|
{
|
||||||
sn_linux_max_context *max_context = (sn_linux_max_context *)context;
|
nif_linux_max_context *max_context = (nif_linux_max_context *)context;
|
||||||
if (value > max_context->max_value)
|
if (value > max_context->max_value)
|
||||||
max_context->max_value = value;
|
max_context->max_value = value;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_fill_cpu_id(int value, void *context)
|
static int nif_linux_fill_cpu_id(int value, void *context)
|
||||||
{
|
{
|
||||||
sn_linux_fill_cpu_context *fill_context = (sn_linux_fill_cpu_context *)context;
|
nif_linux_fill_cpu_context *fill_context = (nif_linux_fill_cpu_context *)context;
|
||||||
|
|
||||||
if (fill_context->internal != NULL)
|
if (fill_context->internal != NULL)
|
||||||
fill_context->internal[fill_context->index] = (uint64_t)fill_context->index;
|
fill_context->internal[fill_context->index] = (uint64_t)fill_context->index;
|
||||||
@@ -131,37 +131,37 @@ static int sn_linux_fill_cpu_id(int value, void *context)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_count_cpu_list(char const *path)
|
static int nif_linux_count_cpu_list(char const *path)
|
||||||
{
|
{
|
||||||
char buffer[256];
|
char buffer[256];
|
||||||
if (!sn_linux_read_first_line(path, buffer, sizeof(buffer)))
|
if (!nif_linux_read_first_line(path, buffer, sizeof(buffer)))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
sn_linux_counter_context counter = { 0 };
|
nif_linux_counter_context counter = { 0 };
|
||||||
if (!sn_linux_visit_id_list(buffer, sn_linux_count_id, &counter))
|
if (!nif_linux_visit_id_list(buffer, nif_linux_count_id, &counter))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
return counter.count;
|
return counter.count;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_fill_node_cpu_count(int value, void *context)
|
static int nif_linux_fill_node_cpu_count(int value, void *context)
|
||||||
{
|
{
|
||||||
char path[128];
|
char path[128];
|
||||||
snprintf(path, sizeof(path), "/sys/devices/system/node/node%d/cpulist", value);
|
snprintf(path, sizeof(path), "/sys/devices/system/node/node%d/cpulist", value);
|
||||||
|
|
||||||
((sn_linux_fill_node_count_context *)context)->count_of_each_numa[value] =
|
((nif_linux_fill_node_count_context *)context)->count_of_each_numa[value] =
|
||||||
sn_linux_count_cpu_list(path);
|
nif_linux_count_cpu_list(path);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_node_exists(int numa_id)
|
static int nif_linux_node_exists(int numa_id)
|
||||||
{
|
{
|
||||||
char path[128];
|
char path[128];
|
||||||
snprintf(path, sizeof(path), "/sys/devices/system/node/node%d", numa_id);
|
snprintf(path, sizeof(path), "/sys/devices/system/node/node%d", numa_id);
|
||||||
return access(path, F_OK) == 0;
|
return access(path, F_OK) == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static size_t sn_linux_round_up_to_page_size(size_t size)
|
static size_t nif_linux_round_up_to_page_size(size_t size)
|
||||||
{
|
{
|
||||||
int64_t page_size_value = (int64_t)sysconf(_SC_PAGESIZE);
|
int64_t page_size_value = (int64_t)sysconf(_SC_PAGESIZE);
|
||||||
size_t effective_page_size = (page_size_value > 0) ? (size_t)page_size_value : 4096u;
|
size_t effective_page_size = (page_size_value > 0) ? (size_t)page_size_value : 4096u;
|
||||||
@@ -173,7 +173,7 @@ static size_t sn_linux_round_up_to_page_size(size_t size)
|
|||||||
return rounded - (rounded % effective_page_size);
|
return rounded - (rounded % effective_page_size);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_bind_memory_to_node(void *address, size_t size, int numa_id, uint32_t flags)
|
static int nif_linux_bind_memory_to_node(void *address, size_t size, int numa_id, uint32_t flags)
|
||||||
{
|
{
|
||||||
#if defined(SYS_mbind)
|
#if defined(SYS_mbind)
|
||||||
size_t bits_per_word = sizeof(unsigned long) * 8u;
|
size_t bits_per_word = sizeof(unsigned long) * 8u;
|
||||||
@@ -197,7 +197,7 @@ static int sn_linux_bind_memory_to_node(void *address, size_t size, int numa_id,
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
static int sn_linux_populate_writable_mapping(void *address, size_t size)
|
static int nif_linux_populate_writable_mapping(void *address, size_t size)
|
||||||
{
|
{
|
||||||
#if defined(MADV_POPULATE_WRITE)
|
#if defined(MADV_POPULATE_WRITE)
|
||||||
if (madvise(address, size, MADV_POPULATE_WRITE) == 0)
|
if (madvise(address, size, MADV_POPULATE_WRITE) == 0)
|
||||||
@@ -214,7 +214,7 @@ static int sn_linux_populate_writable_mapping(void *address, size_t size)
|
|||||||
/* Pin the calling thread to a single logical processor.
|
/* Pin the calling thread to a single logical processor.
|
||||||
* core_id >= 0 : bind to that logical processor (global index, across groups).
|
* core_id >= 0 : bind to that logical processor (global index, across groups).
|
||||||
* core_id < 0 : clear affinity constraint within the current group. */
|
* core_id < 0 : clear affinity constraint within the current group. */
|
||||||
SN_API void SN_DECL sn_set_thread_affinity(int core_id, int numa_id)
|
NIF_API void NIF_DECL nif_set_thread_affinity(int core_id, int numa_id)
|
||||||
{
|
{
|
||||||
int cpu_count = (int)sysconf(_SC_NPROCESSORS_ONLN);
|
int cpu_count = (int)sysconf(_SC_NPROCESSORS_ONLN);
|
||||||
if (cpu_count <= 0)
|
if (cpu_count <= 0)
|
||||||
@@ -238,14 +238,14 @@ SN_API void SN_DECL sn_set_thread_affinity(int core_id, int numa_id)
|
|||||||
CPU_FREE(set);
|
CPU_FREE(set);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API int SN_DECL sn_get_numa_overall(int *out_numa_count, int *count_of_each_numa)
|
NIF_API int NIF_DECL nif_get_numa_overall(int *out_numa_count, int *count_of_each_numa)
|
||||||
{
|
{
|
||||||
char buffer[256];
|
char buffer[256];
|
||||||
if (!sn_linux_read_first_line("/sys/devices/system/node/online", buffer, sizeof(buffer)))
|
if (!nif_linux_read_first_line("/sys/devices/system/node/online", buffer, sizeof(buffer)))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
sn_linux_max_context max_context = { -1 };
|
nif_linux_max_context max_context = { -1 };
|
||||||
if (!sn_linux_visit_id_list(buffer, sn_linux_track_max_id, &max_context) ||
|
if (!nif_linux_visit_id_list(buffer, nif_linux_track_max_id, &max_context) ||
|
||||||
max_context.max_value < 0)
|
max_context.max_value < 0)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
@@ -256,15 +256,15 @@ SN_API int SN_DECL sn_get_numa_overall(int *out_numa_count, int *count_of_each_n
|
|||||||
for (int index = 0; index <= max_context.max_value; index++)
|
for (int index = 0; index <= max_context.max_value; index++)
|
||||||
count_of_each_numa[index] = 0;
|
count_of_each_numa[index] = 0;
|
||||||
|
|
||||||
sn_linux_fill_node_count_context fill_context = { count_of_each_numa };
|
nif_linux_fill_node_count_context fill_context = { count_of_each_numa };
|
||||||
if (!sn_linux_visit_id_list(buffer, sn_linux_fill_node_cpu_count, &fill_context))
|
if (!nif_linux_visit_id_list(buffer, nif_linux_fill_node_cpu_count, &fill_context))
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API int SN_DECL sn_get_numa_each(int numa_id, uint64_t *internal, uint32_t *global)
|
NIF_API int NIF_DECL nif_get_numa_each(int numa_id, uint64_t *internal, uint32_t *global)
|
||||||
{
|
{
|
||||||
if (numa_id < 0)
|
if (numa_id < 0)
|
||||||
return 0;
|
return 0;
|
||||||
@@ -272,16 +272,16 @@ SN_API int SN_DECL sn_get_numa_each(int numa_id, uint64_t *internal, uint32_t *g
|
|||||||
char path[128];
|
char path[128];
|
||||||
char buffer[256];
|
char buffer[256];
|
||||||
snprintf(path, sizeof(path), "/sys/devices/system/node/node%d/cpulist", numa_id);
|
snprintf(path, sizeof(path), "/sys/devices/system/node/node%d/cpulist", numa_id);
|
||||||
if (!sn_linux_read_first_line(path, buffer, sizeof(buffer)))
|
if (!nif_linux_read_first_line(path, buffer, sizeof(buffer)))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
sn_linux_fill_cpu_context fill_context = { internal, global, 0 };
|
nif_linux_fill_cpu_context fill_context = { internal, global, 0 };
|
||||||
return sn_linux_visit_id_list(buffer, sn_linux_fill_cpu_id, &fill_context);
|
return nif_linux_visit_id_list(buffer, nif_linux_fill_cpu_id, &fill_context);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API void *SN_DECL sn_numa_alloc(size_t size, int numa_id)
|
NIF_API void *NIF_DECL nif_numa_alloc(size_t size, int numa_id)
|
||||||
{
|
{
|
||||||
size_t allocation_size = sn_linux_round_up_to_page_size(size);
|
size_t allocation_size = nif_linux_round_up_to_page_size(size);
|
||||||
if (allocation_size == 0)
|
if (allocation_size == 0)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
@@ -303,9 +303,9 @@ SN_API void *SN_DECL sn_numa_alloc(size_t size, int numa_id)
|
|||||||
bind_flags = MPOL_MF_MOVE | MPOL_MF_STRICT;
|
bind_flags = MPOL_MF_MOVE | MPOL_MF_STRICT;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (!sn_linux_node_exists(numa_id) ||
|
if (!nif_linux_node_exists(numa_id) ||
|
||||||
!sn_linux_bind_memory_to_node(memory, allocation_size, numa_id, bind_flags) ||
|
!nif_linux_bind_memory_to_node(memory, allocation_size, numa_id, bind_flags) ||
|
||||||
!sn_linux_populate_writable_mapping(memory, allocation_size)) {
|
!nif_linux_populate_writable_mapping(memory, allocation_size)) {
|
||||||
munmap(memory, allocation_size);
|
munmap(memory, allocation_size);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@@ -313,14 +313,14 @@ SN_API void *SN_DECL sn_numa_alloc(size_t size, int numa_id)
|
|||||||
return memory;
|
return memory;
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API void SN_DECL sn_numa_free(void *ptr, size_t size, int numa_id)
|
NIF_API void NIF_DECL nif_numa_free(void *ptr, size_t size, int numa_id)
|
||||||
{
|
{
|
||||||
(void)numa_id;
|
(void)numa_id;
|
||||||
|
|
||||||
if (ptr == NULL || size == 0)
|
if (ptr == NULL || size == 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
size_t allocation_size = sn_linux_round_up_to_page_size(size);
|
size_t allocation_size = nif_linux_round_up_to_page_size(size);
|
||||||
if (allocation_size != 0)
|
if (allocation_size != 0)
|
||||||
munmap(ptr, allocation_size);
|
munmap(ptr, allocation_size);
|
||||||
}
|
}
|
||||||
+8
-8
@@ -1,12 +1,12 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
#include "StgSharpNative.h"
|
#include "NitloadFrameWork.h"
|
||||||
|
|
||||||
#if SN_IS_OS(SN_OS_WINDOWS)
|
#if NIF_IS_OS(NIF_OS_WINDOWS)
|
||||||
|
|
||||||
/* Pin the calling thread to a single logical processor.
|
/* Pin the calling thread to a single logical processor.
|
||||||
* core_id >= 0 : bind to that logical processor (global index, across groups).
|
* core_id >= 0 : bind to that logical processor (global index, across groups).
|
||||||
* core_id < 0 : clear affinity constraint within the current group. */
|
* core_id < 0 : clear affinity constraint within the current group. */
|
||||||
SN_API void SN_DECL sn_set_thread_affinity(int core_id, int numa_id)
|
NIF_API void NIF_DECL nif_set_thread_affinity(int core_id, int numa_id)
|
||||||
{
|
{
|
||||||
if (core_id < 0 || numa_id < 0) {
|
if (core_id < 0 || numa_id < 0) {
|
||||||
/* Query which group the thread currently belongs to */
|
/* Query which group the thread currently belongs to */
|
||||||
@@ -32,7 +32,7 @@ SN_API void SN_DECL sn_set_thread_affinity(int core_id, int numa_id)
|
|||||||
SetThreadGroupAffinity(GetCurrentThread(), &ga, NULL);
|
SetThreadGroupAffinity(GetCurrentThread(), &ga, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API int SN_DECL sn_get_numa_overall(int *out_numa_count, int *count_of_each_numa)
|
NIF_API int NIF_DECL nif_get_numa_overall(int *out_numa_count, int *count_of_each_numa)
|
||||||
{
|
{
|
||||||
ULONG highest;
|
ULONG highest;
|
||||||
if (!GetNumaHighestNodeNumber(&highest))
|
if (!GetNumaHighestNodeNumber(&highest))
|
||||||
@@ -47,7 +47,7 @@ SN_API int SN_DECL sn_get_numa_overall(int *out_numa_count, int *count_of_each_n
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API int SN_DECL sn_get_numa_each(int numa_id, uint64_t *internal, uint32_t *global)
|
NIF_API int NIF_DECL nif_get_numa_each(int numa_id, uint64_t *internal, uint32_t *global)
|
||||||
{
|
{
|
||||||
ULONGLONG mask = 0;
|
ULONGLONG mask = 0;
|
||||||
if (!GetNumaNodeProcessorMask((UCHAR)numa_id, &mask))
|
if (!GetNumaNodeProcessorMask((UCHAR)numa_id, &mask))
|
||||||
@@ -67,7 +67,7 @@ SN_API int SN_DECL sn_get_numa_each(int numa_id, uint64_t *internal, uint32_t *g
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
SN_API void *SN_DECL sn_numa_alloc(size_t size, int numa_id)
|
NIF_API void *NIF_DECL nif_numa_alloc(size_t size, int numa_id)
|
||||||
{
|
{
|
||||||
if (size == 0)
|
if (size == 0)
|
||||||
return NULL;
|
return NULL;
|
||||||
@@ -83,7 +83,7 @@ SN_API void *SN_DECL sn_numa_alloc(size_t size, int numa_id)
|
|||||||
PAGE_READWRITE, (DWORD)numa_id);
|
PAGE_READWRITE, (DWORD)numa_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
SN_API void SN_DECL sn_numa_free(void *ptr, size_t size, int numa_id)
|
NIF_API void NIF_DECL nif_numa_free(void *ptr, size_t size, int numa_id)
|
||||||
{
|
{
|
||||||
(void)size;
|
(void)size;
|
||||||
(void)numa_id;
|
(void)numa_id;
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_internal.h"
|
#include "nif_internal.h"
|
||||||
|
|
||||||
INTERNAL void SN_DECL f32_normalize(VEC_SEGMENT(float) *restrict source, VEC_SEGMENT(float) *restrict target)
|
INTERNAL void NIF_DECL f32_normalize(VEC_SEGMENT(float) *restrict source, VEC_SEGMENT(float) *restrict target)
|
||||||
{
|
{
|
||||||
register __m128 s = source->f32_x[0];
|
register __m128 s = source->f32_x[0];
|
||||||
register __m128 a_length_sq = _mm_mul_ps(s, s);
|
register __m128 a_length_sq = _mm_mul_ps(s, s);
|
||||||
@@ -1,9 +1,9 @@
|
|||||||
#include "sn_intrinsic.h"
|
#include "nif_intrinsic.h"
|
||||||
#include "sn_internal.h"
|
#include "nif_internal.h"
|
||||||
|
|
||||||
static const int avxdot_indices[] = { 0, 4, 1, 5, 2, 3, 6, 7 };
|
static const int avxdot_indices[] = { 0, 4, 1, 5, 2, 3, 6, 7 };
|
||||||
|
|
||||||
INTERNAL void FORCEINLINE SN_DECL dot_41_sse(MAT_KERNEL(float) const *transpose,
|
INTERNAL void FORCEINLINE NIF_DECL dot_41_sse(MAT_KERNEL(float) const *transpose,
|
||||||
__m128 const *vector, __m128 *ans)
|
__m128 const *vector, __m128 *ans)
|
||||||
{
|
{
|
||||||
*ans = _mm_dp_ps(transpose->x[0], *vector, 0B11110001);
|
*ans = _mm_dp_ps(transpose->x[0], *vector, 0B11110001);
|
||||||
@@ -15,7 +15,7 @@ INTERNAL void FORCEINLINE SN_DECL dot_41_sse(MAT_KERNEL(float) const *transpose,
|
|||||||
SSE_INSERT_SIMPLE(1, 4));
|
SSE_INSERT_SIMPLE(1, 4));
|
||||||
}
|
}
|
||||||
|
|
||||||
INTERNAL void SN_DECL dot_41_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
INTERNAL void NIF_DECL dot_41_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
||||||
__m128 *ans)
|
__m128 *ans)
|
||||||
{
|
{
|
||||||
__m256 _double = _mm256_set_m128(vector[0], vector[0]);
|
__m256 _double = _mm256_set_m128(vector[0], vector[0]);
|
||||||
@@ -26,7 +26,7 @@ INTERNAL void SN_DECL dot_41_avx(MAT_KERNEL(float) const *transpose, __m128 cons
|
|||||||
_mm256_permutevar8x32_ps(tmp, _mm256_loadu_epi32(avxdot_indices)));
|
_mm256_permutevar8x32_ps(tmp, _mm256_loadu_epi32(avxdot_indices)));
|
||||||
}
|
}
|
||||||
|
|
||||||
INTERNAL void SN_DECL dot_42_sse(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
INTERNAL void NIF_DECL dot_42_sse(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
||||||
__m128 *ans)
|
__m128 *ans)
|
||||||
{
|
{
|
||||||
ans[0] = _mm_dp_ps(transpose->x[0], vector[0], 0B11110001);
|
ans[0] = _mm_dp_ps(transpose->x[0], vector[0], 0B11110001);
|
||||||
@@ -46,7 +46,7 @@ INTERNAL void SN_DECL dot_42_sse(MAT_KERNEL(float) const *transpose, __m128 cons
|
|||||||
SSE_INSERT_SIMPLE(1, 4));
|
SSE_INSERT_SIMPLE(1, 4));
|
||||||
}
|
}
|
||||||
|
|
||||||
INTERNAL void SN_DECL dot_42_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
INTERNAL void NIF_DECL dot_42_avx(MAT_KERNEL(float) const *transpose, __m128 const *vector,
|
||||||
__m128 *ans)
|
__m128 *ans)
|
||||||
{
|
{
|
||||||
__m256 temp = transpose->y[0];
|
__m256 temp = transpose->y[0];
|
||||||
+9
-9
@@ -1,8 +1,8 @@
|
|||||||
#include "sn_target.h"
|
#include "nif_target.h"
|
||||||
|
|
||||||
#if SN_IS_ARCH(SN_ARCH_X86_64)
|
#if NIF_IS_ARCH(NIF_ARCH_X86_64)
|
||||||
|
|
||||||
#define SN_MK_FMA_F32_512_CYCLE(i) \
|
#define NIF_MK_FMA_F32_512_CYCLE(i) \
|
||||||
do { \
|
do { \
|
||||||
c0 = _mm512_fmadd_ps(c0, a0, _mm512_permute_ps(b0, _FMA_SELECT(i))); \
|
c0 = _mm512_fmadd_ps(c0, a0, _mm512_permute_ps(b0, _FMA_SELECT(i))); \
|
||||||
c1 = _mm512_fmadd_ps(c1, a1, _mm512_permute_ps(b1, _FMA_SELECT(i))); \
|
c1 = _mm512_fmadd_ps(c1, a1, _mm512_permute_ps(b1, _FMA_SELECT(i))); \
|
||||||
@@ -10,7 +10,7 @@
|
|||||||
c3 = _mm512_fmadd_ps(c3, a3, _mm512_permute_ps(b3, _FMA_SELECT(i))); \
|
c3 = _mm512_fmadd_ps(c3, a3, _mm512_permute_ps(b3, _FMA_SELECT(i))); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define SN_MK_FMA_F32_AVX2_CYCLE(i) \
|
#define NIF_MK_FMA_F32_AVX2_CYCLE(i) \
|
||||||
do { \
|
do { \
|
||||||
c0 = _mm256_fmadd_ps(c0, a0, _mm256_permute_ps(b0, _FMA_SELECT(i))); \
|
c0 = _mm256_fmadd_ps(c0, a0, _mm256_permute_ps(b0, _FMA_SELECT(i))); \
|
||||||
c1 = _mm256_fmadd_ps(c1, a1, _mm256_permute_ps(b1, _FMA_SELECT(i))); \
|
c1 = _mm256_fmadd_ps(c1, a1, _mm256_permute_ps(b1, _FMA_SELECT(i))); \
|
||||||
@@ -18,7 +18,7 @@
|
|||||||
c3 = _mm256_fmadd_ps(c3, a3, _mm256_permute_ps(b3, _FMA_SELECT(i))); \
|
c3 = _mm256_fmadd_ps(c3, a3, _mm256_permute_ps(b3, _FMA_SELECT(i))); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define SN_MK_FMA_F64_AVX2_CYCLE(i) \
|
#define NIF_MK_FMA_F64_AVX2_CYCLE(i) \
|
||||||
do { \
|
do { \
|
||||||
c0 = _mm512_fmadd_ps(c0, a0, _mm512_permutex_pd(b0, _FMA_SELECT(i))); \
|
c0 = _mm512_fmadd_ps(c0, a0, _mm512_permutex_pd(b0, _FMA_SELECT(i))); \
|
||||||
c1 = _mm512_fmadd_ps(c1, a1, _mm512_permutex_pd(b1, _FMA_SELECT(i))); \
|
c1 = _mm512_fmadd_ps(c1, a1, _mm512_permutex_pd(b1, _FMA_SELECT(i))); \
|
||||||
@@ -26,7 +26,7 @@
|
|||||||
c3 = _mm512_fmadd_ps(c3, a3, _mm512_permutex_pd(b3, _FMA_SELECT(i))); \
|
c3 = _mm512_fmadd_ps(c3, a3, _mm512_permutex_pd(b3, _FMA_SELECT(i))); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define SN_FMA_F32_512_PACK_COLUMN(col, target) \
|
#define NIF_FMA_F32_512_PACK_COLUMN(col, target) \
|
||||||
do { \
|
do { \
|
||||||
register __m256 low = _mm512_castps512_ps256(col); \
|
register __m256 low = _mm512_castps512_ps256(col); \
|
||||||
register __m256 high = _mm512_extractf32x8_ps(col, 1); \
|
register __m256 high = _mm512_extractf32x8_ps(col, 1); \
|
||||||
@@ -37,7 +37,7 @@
|
|||||||
_mm_store_ps(target, half128); \
|
_mm_store_ps(target, half128); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define SN_FMA_F32_AVX2_PACK_COLUMN(col, target) \
|
#define NIF_FMA_F32_AVX2_PACK_COLUMN(col, target) \
|
||||||
do { \
|
do { \
|
||||||
register __m128 high128 = _mm256_extractf32x4_ps(col, 1); \
|
register __m128 high128 = _mm256_extractf32x4_ps(col, 1); \
|
||||||
register __m128 low128 = _mm256_castps256_ps128(col); \
|
register __m128 low128 = _mm256_castps256_ps128(col); \
|
||||||
@@ -45,7 +45,7 @@
|
|||||||
_mm_store_ps(target, half128); \
|
_mm_store_ps(target, half128); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define SN_FMA_F64_512_PACK_COLUMN(col, target) \
|
#define NIF_FMA_F64_512_PACK_COLUMN(col, target) \
|
||||||
do { \
|
do { \
|
||||||
register __m128 high128 = _mm256_extractf32x4_ps(col, 1); \
|
register __m128 high128 = _mm256_extractf32x4_ps(col, 1); \
|
||||||
register __m128 low128 = _mm256_castps256_ps128(col); \
|
register __m128 low128 = _mm256_castps256_ps128(col); \
|
||||||
@@ -54,7 +54,7 @@
|
|||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
// double
|
// double
|
||||||
#define SN_MK_FMA_F64_SSE_PHASE(i) \
|
#define NIF_MK_FMA_F64_SSE_PHASE(i) \
|
||||||
do { \
|
do { \
|
||||||
/* k = 0 */ \
|
/* k = 0 */ \
|
||||||
register __m128d b_lo = _mm_load_pd(right_values + (2 * i + 0)); \
|
register __m128d b_lo = _mm_load_pd(right_values + (2 * i + 0)); \
|
||||||
@@ -1,35 +0,0 @@
|
|||||||
#ifndef SNative
|
|
||||||
#define SNative
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
|
||||||
#error "This header is not meant to be included in C++ code. Nitload.Native is a C library and should be used with C linkage."
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "sn_internal.h"
|
|
||||||
#include "sn_target.h"
|
|
||||||
|
|
||||||
#include <immintrin.h>
|
|
||||||
#include <assert.h>
|
|
||||||
#include <glfw_function.h>
|
|
||||||
|
|
||||||
#define byte char
|
|
||||||
#define cs_char uint16_t
|
|
||||||
#define sn_null_assert(ptr) assert(ptr != NULL)
|
|
||||||
|
|
||||||
#ifndef SN_
|
|
||||||
#endif
|
|
||||||
|
|
||||||
SN_API void SN_DECL load_glfw_functions(GLFWFunctionTable *table);
|
|
||||||
SN_API void SN_DECL load_intrinsic_function(void *intrinsic_context, uint64_t id);
|
|
||||||
SN_API SIMDID SN_DECL sn_get_simd_level_global();
|
|
||||||
/* Per-core variant: always re-executes CPUID, never caches.
|
|
||||||
* Must be called on the target core (after affinity is set). */
|
|
||||||
SN_API SIMDID SN_DECL sn_get_simd_level_local();
|
|
||||||
SN_API SIMDID SN_DECL sn_get_unite_simd(SIMDID left, SIMDID right);
|
|
||||||
SN_API int SN_DECL sn_compare_simd(SIMDID left, SIMDID right);
|
|
||||||
SN_API void SN_DECL sn_set_thread_affinity(int core_id, int numa_id);
|
|
||||||
SN_API void* SN_DECL sn_numa_alloc(size_t size, int numa_id);
|
|
||||||
SN_API void SN_DECL sn_numa_free(void *ptr, size_t size, int numa_id);
|
|
||||||
SN_API int SN_DECL sn_get_numa_each(int numa_id, uint64_t *internal, uint32_t *global);
|
|
||||||
SN_API int SN_DECL sn_get_numa_overall(int *out_numa_count, int *count_of_each_numa);
|
|
||||||
#endif
|
|
||||||
@@ -1,54 +0,0 @@
|
|||||||
#ifndef SN_MATKERNEL
|
|
||||||
#define SN_MATKERNEL
|
|
||||||
|
|
||||||
#include <immintrin.h>
|
|
||||||
#include <stdint.h>
|
|
||||||
|
|
||||||
#include "sn_internal.h"
|
|
||||||
|
|
||||||
/* Kernel storage unions for a fixed 4x4 block. */
|
|
||||||
#define ELEMENTSIZE(T) sizeof(T)
|
|
||||||
#define XMMCOUNT(T) (sizeof(T))
|
|
||||||
#define YMMCOUNT(T) (sizeof(T) / 2)
|
|
||||||
#define ZMMCOUNT(T) (sizeof(T) / 4)
|
|
||||||
|
|
||||||
#define SN_MAT_KERNEL_MEMBER(T) \
|
|
||||||
{ \
|
|
||||||
__m128 x[XMMCOUNT(T)]; \
|
|
||||||
__m256 y[YMMCOUNT(T)]; \
|
|
||||||
__m512 z[ZMMCOUNT(T)]; \
|
|
||||||
T m[4][4]; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#define SN_MAT_KERNEL_DEFINE(T) \
|
|
||||||
typedef union SN_MAT_KERNEL_TYPE_##T SN_MAT_KERNEL_MEMBER(T) SN_MAT_KERNEL_TYPE_##T
|
|
||||||
|
|
||||||
#define MAT_KERNEL(T) SN_MAT_KERNEL_TYPE(T)
|
|
||||||
#define SN_MAT_KERNEL_TYPE(T) SN_MAT_KERNEL_TYPE_##T
|
|
||||||
|
|
||||||
SN_MAT_KERNEL_DEFINE(float);
|
|
||||||
SN_MAT_KERNEL_DEFINE(double);
|
|
||||||
SN_MAT_KERNEL_DEFINE(uint64_t);
|
|
||||||
|
|
||||||
|
|
||||||
#define SN_VEC_SEGMENT_MEMBER(T) \
|
|
||||||
{ \
|
|
||||||
__m128 f32_x[XMMCOUNT(T) / 4]; \
|
|
||||||
__m256 f32_y[YMMCOUNT(T) / 4]; \
|
|
||||||
__m512 f32_z[ZMMCOUNT(T) / 4]; \
|
|
||||||
T v[4]; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#define SN_VEC_SEGMENT_DEFINE(T) \
|
|
||||||
typedef union SN_VEC_SEGMENT_TYPE_##T SN_VEC_SEGMENT_MEMBER(T) SN_VEC_SEGMENT_TYPE_##T
|
|
||||||
|
|
||||||
#define VEC_SEGMENT(T) SN_VEC_SEGMENT_TYPE(T)
|
|
||||||
#define SN_VEC_SEGMENT_TYPE(T) SN_VEC_SEGMENT_TYPE_##T
|
|
||||||
|
|
||||||
SN_VEC_SEGMENT_DEFINE(float);
|
|
||||||
SN_VEC_SEGMENT_DEFINE(double);
|
|
||||||
|
|
||||||
/* Global zero kernel declaration (defined in dllmain.c), aligned to 64 bytes */
|
|
||||||
extern __declspec(align(64)) MAT_KERNEL(u64) SN_ZERO_KERNEL;
|
|
||||||
|
|
||||||
#endif /* SN_MATKERNEL */
|
|
||||||
@@ -1,94 +0,0 @@
|
|||||||
#ifndef SN_TARGET
|
|
||||||
#define SN_TARGET
|
|
||||||
|
|
||||||
#include "sn_internal.h"
|
|
||||||
#include <stdint.h>
|
|
||||||
|
|
||||||
#define SN_OS_WINDOWS 0
|
|
||||||
#define SN_OS_LINUX 1
|
|
||||||
#define SN_OS_MACOS 2
|
|
||||||
#define SN_OS_IOS 3
|
|
||||||
#define SN_OS_ANDROID 4
|
|
||||||
#define SN_OS_UNKNOWN 5
|
|
||||||
|
|
||||||
#define SN_ARCH_X86_64 0
|
|
||||||
#define SN_ARCH_ARM64 1
|
|
||||||
#define SN_ARCH_RISCV64 2
|
|
||||||
#define SN_ARCH_PPC64le 3
|
|
||||||
|
|
||||||
#if defined(_M_X64) || defined(_M_AMD64) || defined(__x86_64__) || defined(__amd64__)
|
|
||||||
#define SN_CURRENT_ARCH SN_ARCH_X86_64
|
|
||||||
|
|
||||||
#elif defined(_M_ARM64) || defined(__aarch64__)
|
|
||||||
#define SN_CURRENT_ARCH SN_ARCH_ARM64
|
|
||||||
|
|
||||||
#elif defined(_M_ARM) || defined(__arm__)
|
|
||||||
#define SN_CURRENT_ARCH SN_ARCH_ARM32
|
|
||||||
|
|
||||||
#elif defined(_M_IX86) || defined(__i386__)
|
|
||||||
#define SN_CURRENT_ARCH SN_ARCH_X86_32
|
|
||||||
|
|
||||||
#elif defined(__powerpc64__) && defined(__LITTLE_ENDIAN__)
|
|
||||||
#define SN_CURRENT_ARCH SN_ARCH_PPC64LE
|
|
||||||
|
|
||||||
#elif defined(__riscv) && (__riscv_xlen == 64)
|
|
||||||
#define SN_CURRENT_ARCH SN_ARCH_RISCV64
|
|
||||||
|
|
||||||
#else
|
|
||||||
#error "SN: Unsupported target architecture"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Target selection policy:
|
|
||||||
* - Default (no SN_EXTERN_TARGET): fixed Windows + x86_64.
|
|
||||||
* - External (SN_EXTERN_TARGET): build system must provide SN_OS and SN_ARCH.
|
|
||||||
*/
|
|
||||||
#ifndef SN_EXTERN_TARGET
|
|
||||||
|
|
||||||
#define SN_OS_TARGET SN_OS_WINDOWS
|
|
||||||
#define SN_ARCH_TARGET SN_ARCH_X86_64
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
#ifndef SN_OS_TARGET
|
|
||||||
#error "SN_EXTERN_TARGET is defined but SN_OS is not provided."
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef SN_ARCH_TARGET
|
|
||||||
#error "SN_EXTERN_TARGET is defined but SN_ARCH is not provided."
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Validate externally supplied values are within known enum constants. */
|
|
||||||
#if (SN_OS_TARGET != SN_OS_WINDOWS) && (SN_OS_TARGET != SN_OS_LINUX) && \
|
|
||||||
(SN_OS_TARGET != SN_OS_MACOS) && (SN_OS_TARGET != SN_OS_IOS) && \
|
|
||||||
(SN_OS_TARGET != SN_OS_ANDROID) && (SN_OS_TARGET != SN_OS_UNKNOWN)
|
|
||||||
#error "SN_OS has an invalid value. Use SN_OS_<...> enum constants."
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (SN_ARCH_TARGET != SN_ARCH_X86_64) && (SN_ARCH_TARGET != SN_ARCH_ARM64) && \
|
|
||||||
(SN_ARCH_TARGET != SN_ARCH_RISCV64) && (SN_ARCH_TARGET != SN_ARCH_PPC64le)
|
|
||||||
#error "SN_ARCH has an invalid value. Use SN_ARCH_<...> enum constants."
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define SN_IS_OS(os) ((SN_OS_TARGET) == (os))
|
|
||||||
|
|
||||||
#define SN_IS_ARCH(arch) ((SN_ARCH_TARGET) == (arch))
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Per-function ISA selection is required for runtime-dispatched kernels that
|
|
||||||
* mix multiple x86 feature levels in one build target.
|
|
||||||
*/
|
|
||||||
#if defined(__clang__) && ((SN_ARCH_TARGET) == SN_ARCH_X86_64)
|
|
||||||
#define SN_CLANG_TARGET_ATTR(options) __attribute__((target(options)))
|
|
||||||
#else
|
|
||||||
#define SN_CLANG_TARGET_ATTR(options)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
typedef union SIMDID {
|
|
||||||
uint64_t mask;
|
|
||||||
char make_byte[8];
|
|
||||||
} SIMDID;
|
|
||||||
|
|
||||||
#endif // SN_TARGET
|
|
||||||
@@ -1,204 +0,0 @@
|
|||||||
# NGRA `COUNT(UNIT)` 生成说明
|
|
||||||
|
|
||||||
本文记录 `TextRegexSourceGen.GenerateCount` 中单字符重复分支的当前设计,方便后续继续实现。
|
|
||||||
|
|
||||||
相关代码:[`Text/TextRegexSourceGen.GenClass.cs`](Text/TextRegexSourceGen.GenClass.cs)。
|
|
||||||
|
|
||||||
## 目标
|
|
||||||
|
|
||||||
对于 `a{min,max}`,不要把必需的 `min` 次匹配生成成逐字符循环。生成器先把字符重复 `min` 次,形成一个字符串字面量,并使用一次 `StartsWith` 验证下界:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
if (__remain.StartsWith("aaa"))
|
|
||||||
{
|
|
||||||
// 已经确认至少存在 min 个 a。
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// 当前工作 region 失败。
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
匹配成功后一次性消费这个前缀,再只处理区间中可选的部分:
|
|
||||||
|
|
||||||
```text
|
|
||||||
必需前缀:min 次
|
|
||||||
可选尾部:max - min 次
|
|
||||||
```
|
|
||||||
|
|
||||||
`max < 0` 表示尾部没有上限。
|
|
||||||
|
|
||||||
## AST 数据归属
|
|
||||||
|
|
||||||
`COUNT` 配置属于操作符节点,重复的字符属于其子节点:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
RegexCountPayload payload = node.PayloadAs<RegexCountPayload>();
|
|
||||||
RegexAstNode value = RegexAstNode.IsNullOrEmpty(node.Left)
|
|
||||||
? node.Right
|
|
||||||
: node.Left;
|
|
||||||
char expected = value.Value[0];
|
|
||||||
```
|
|
||||||
|
|
||||||
不要从 `value` 读取 `RegexCountPayload`。`value` 携带的是 `RegexLiteralPayload` 或其他被重复元素的 payload。
|
|
||||||
|
|
||||||
字符应从 `value.Value` 读取,因为它是解码后的值。使用 `value.Source.Source[0]` 会把 `\t` 等转义序列错误地识别成 `'\\'`。
|
|
||||||
|
|
||||||
## 量词语义
|
|
||||||
|
|
||||||
| 量词 | `min` | `max` | 尾部处理 |
|
|
||||||
| --- | ---: | ---: | --- |
|
|
||||||
| `a{n}` | `n` | `n` | 无可选尾部 |
|
|
||||||
| `a{m,n}` | `m` | `n` | 最多再消费 `n - m` 次 |
|
|
||||||
| `a*` | `0` | `-1` | 无上限 |
|
|
||||||
| `a+` | `1` | `-1` | 验证一次后无上限 |
|
|
||||||
| `a?` | `0` | `1` | 最多消费一次 |
|
|
||||||
| `a{m,}` | `m` | `-1` | 验证 `m` 次后无上限 |
|
|
||||||
|
|
||||||
有限上限可以生成:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
__remain = __remain.Slice(min);
|
|
||||||
|
|
||||||
for (int i = 0;
|
|
||||||
i < max - min &&
|
|
||||||
!__remain.IsEmpty &&
|
|
||||||
__remain[0] == expected;
|
|
||||||
i++)
|
|
||||||
{
|
|
||||||
__remain = __remain.Slice(1);
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
无上限不能计算 `max - min`,否则结果为负数、循环不会执行。应单独生成:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
__remain = __remain.Slice(min);
|
|
||||||
|
|
||||||
while (!__remain.IsEmpty && __remain[0] == expected)
|
|
||||||
{
|
|
||||||
__remain = __remain.Slice(1);
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
`!__remain.IsEmpty` 必须位于 `__remain[0]` 之前。输入恰好在必需前缀后耗尽时,直接索引会抛出 `IndexOutOfRangeException`。
|
|
||||||
|
|
||||||
## 贪婪与惰性
|
|
||||||
|
|
||||||
贪婪量词可以先消费尽可能多的可选尾部,再尝试后续 continuation。如果后续失败,需要逐次回退消费数量并重试。
|
|
||||||
|
|
||||||
惰性量词只应先消费 `min`,立即尝试后续 continuation;后续失败时,才逐次多消费一个匹配字符。
|
|
||||||
|
|
||||||
因此 `is_greedy` 不能只改变扫描循环,它最终需要与后续节点的 continuation 和回溯状态一起实现。若 COUNT 位于匹配末尾,贪婪模式可直接扫描至上限,惰性模式保留在 `min` 即可。
|
|
||||||
|
|
||||||
## 失败工作 region
|
|
||||||
|
|
||||||
当前试点使用 `do { } while (false)`,使局部失败可以写成 `break`:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
bool regionSucceeded = false;
|
|
||||||
ReadOnlySpan<char> checkpoint = __remain;
|
|
||||||
|
|
||||||
do
|
|
||||||
{
|
|
||||||
if (!__remain.StartsWith(requiredPrefix))
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
__remain = __remain.Slice(min);
|
|
||||||
// 匹配可选尾部和后续节点。
|
|
||||||
|
|
||||||
regionSucceeded = true;
|
|
||||||
}
|
|
||||||
while (false);
|
|
||||||
|
|
||||||
if (!regionSucceeded)
|
|
||||||
{
|
|
||||||
__remain = checkpoint;
|
|
||||||
// 向父 region 传播失败,或者在顶层返回失败结果。
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
只有 COUNT 自己被 `do/while(false)` 包裹时,`break` 结束后仍会执行下一个 CONCAT 节点,不能真正表达匹配失败。最终 region 应由以下之一持有:
|
|
||||||
|
|
||||||
- 包含后续 continuation 的 `CONCAT`;
|
|
||||||
- 一条完整的 ALT 候选路径;
|
|
||||||
- 顶层匹配方法。
|
|
||||||
|
|
||||||
父 region 负责保存 cursor 和 capture checkpoint。子节点失败后退出父 region,由父 region 统一恢复状态。ALT 和贪婪/惰性 COUNT 还需要保存多个可重试位置,不能只依赖一次 `break`。
|
|
||||||
|
|
||||||
## 摊平阈值
|
|
||||||
|
|
||||||
不要无条件执行:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
Span<char> required = stackalloc char[min];
|
|
||||||
```
|
|
||||||
|
|
||||||
量词来自用户输入,`a{1000000}` 会让源生成器尝试进行巨大的栈分配,并生成巨型字符串字面量。建议设置较小阈值,例如 32 或 64:
|
|
||||||
|
|
||||||
- `min <= threshold`:摊平为字面量并调用 `StartsWith`;
|
|
||||||
- `min > threshold`:循环比较固定长度的摊平块,最后比较不足一个块的余数;
|
|
||||||
- 非法或超过生成器限制的数量:报告 Roslyn diagnostic,而不是让生成器崩溃。
|
|
||||||
|
|
||||||
以阈值 64 为例,`a{150}` 被拆成两个 64 字符块和一个 22 字符余数块。运行时使用局部 span 逐块调用 `StartsWith`,全部成功后才一次性推进正式 cursor。这样失败时无需恢复已经提交的 `__remain`:
|
|
||||||
|
|
||||||
```csharp
|
|
||||||
if (__remain.Length < 150)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
ReadOnlySpan<char> __requiredRest_0 = __remain;
|
|
||||||
bool __requiredMatched_0 = true;
|
|
||||||
|
|
||||||
for (int __requiredChunkIndex_0 = 0; __requiredChunkIndex_0 < 2; __requiredChunkIndex_0++)
|
|
||||||
{
|
|
||||||
if (!__requiredRest_0.StartsWith("aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"))
|
|
||||||
{
|
|
||||||
__requiredMatched_0 = false;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
__requiredRest_0 = __requiredRest_0.Slice(64);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (__requiredMatched_0 && !__requiredRest_0.StartsWith("aaaaaaaaaaaaaaaaaaaaaa"))
|
|
||||||
{
|
|
||||||
__requiredMatched_0 = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!__requiredMatched_0)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
__remain = __remain.Slice(150);
|
|
||||||
```
|
|
||||||
|
|
||||||
## 后续实现顺序
|
|
||||||
|
|
||||||
1. 从 `node` 读取 `RegexCountPayload`,并用 Empty sentinel 安全选择子节点。
|
|
||||||
2. 改用 `value.Value[0]` 获取解码字符。
|
|
||||||
3. 为所有尾部循环加入 `!__remain.IsEmpty`。
|
|
||||||
4. 分开生成有限上限和 `max < 0` 两种循环。
|
|
||||||
5. 增加摊平阈值,避免巨大 `stackalloc` 和生成源膨胀。
|
|
||||||
6. 将工作 region 上移到 CONCAT/候选路径,完成失败传播和 checkpoint 恢复。
|
|
||||||
7. 接入 greedy/lazy continuation 回溯。
|
|
||||||
8. 最后处理 capture 状态的保存与恢复。
|
|
||||||
|
|
||||||
## 最小测试矩阵
|
|
||||||
|
|
||||||
至少覆盖以下模式和输入:
|
|
||||||
|
|
||||||
- `a{0}`:空输入、`a`;
|
|
||||||
- `a{3}`:`aa`、`aaa`、`aaaa`;
|
|
||||||
- `a{2,4}`:长度 1 到 5;
|
|
||||||
- `a*`、`a+`、`a?`、`a{2,}`;
|
|
||||||
- `\t{2}`:确认使用解码字符;
|
|
||||||
- `a{2,4}ab`:验证贪婪回退;
|
|
||||||
- `a{2,4}?ab`:验证惰性扩展;
|
|
||||||
- COUNT 位于 CONCAT、ALT 和捕获 GROUP 内的失败恢复;
|
|
||||||
- 输入恰好在 `min` 处结束,确认不会索引空 span;
|
|
||||||
- 超大 `min`,确认不会导致生成器栈溢出或生成巨型源码。
|
|
||||||
@@ -0,0 +1,215 @@
|
|||||||
|
[CmdletBinding()]
|
||||||
|
param(
|
||||||
|
[switch] $Apply
|
||||||
|
)
|
||||||
|
|
||||||
|
Set-StrictMode -Version Latest
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
$taskWorkspaceRoot = [IO.Path]::GetFullPath((Join-Path $PSScriptRoot '..'))
|
||||||
|
$nativeProjectRoot = Join-Path $taskWorkspaceRoot 'src\Nitload.Native'
|
||||||
|
$textRoots = @(
|
||||||
|
$nativeProjectRoot
|
||||||
|
(Join-Path $taskWorkspaceRoot 'src\Nitload.Common')
|
||||||
|
(Join-Path $taskWorkspaceRoot 'src\Nitload.Mathematics')
|
||||||
|
(Join-Path $taskWorkspaceRoot 'src\Nitload.Graphics')
|
||||||
|
)
|
||||||
|
|
||||||
|
$textExtensions = [Collections.Generic.HashSet[string]]::new(
|
||||||
|
[StringComparer]::OrdinalIgnoreCase
|
||||||
|
)
|
||||||
|
@(
|
||||||
|
'.c', '.h', '.inl', '.inc', '.ipp',
|
||||||
|
'.cs', '.cmake', '.txt', '.md',
|
||||||
|
'.csproj', '.vcxproj', '.filters',
|
||||||
|
'.json', '.props', '.targets'
|
||||||
|
) | ForEach-Object { [void] $textExtensions.Add($_) }
|
||||||
|
|
||||||
|
$replacementRules = @(
|
||||||
|
@{ Pattern = '\bSTGSHARP_'; Replacement = 'NIF_' }
|
||||||
|
@{ Pattern = '\bSN_'; Replacement = 'NIF_' }
|
||||||
|
@{ Pattern = '(?<![A-Za-z0-9])sn_'; Replacement = 'nif_' }
|
||||||
|
@{ Pattern = '\bload_glfw_functions\b'; Replacement = 'nif_load_glfw_functions' }
|
||||||
|
@{ Pattern = '\bload_intrinsic_function\b'; Replacement = 'nif_load_intrinsic_function' }
|
||||||
|
@{ Pattern = '\bStgSharpNative\b'; Replacement = 'NitloadFrameWork' }
|
||||||
|
@{ Pattern = '\bNitloadInnovationFramework\b'; Replacement = 'NitloadFrameWork' }
|
||||||
|
@{ Pattern = '\bNitloadFramework\b'; Replacement = 'NitloadFrameWork' }
|
||||||
|
@{ Pattern = '\bSNative\b'; Replacement = 'NIF_NATIVE_H' }
|
||||||
|
@{ Pattern = 'sn-head'; Replacement = 'nif-head' }
|
||||||
|
@{ Pattern = 'sn-src'; Replacement = 'nif-src' }
|
||||||
|
@{ Pattern = 'sn-template'; Replacement = 'nif-template' }
|
||||||
|
)
|
||||||
|
|
||||||
|
function Test-TaskPath {
|
||||||
|
param([Parameter(Mandatory)][string] $Path)
|
||||||
|
|
||||||
|
$resolvedPath = [IO.Path]::GetFullPath($Path)
|
||||||
|
if (-not $resolvedPath.StartsWith(
|
||||||
|
$taskWorkspaceRoot + [IO.Path]::DirectorySeparatorChar,
|
||||||
|
[StringComparison]::OrdinalIgnoreCase
|
||||||
|
)) {
|
||||||
|
throw "Path escapes workspace: $resolvedPath"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function Get-TaskTextFile {
|
||||||
|
foreach ($textRoot in $textRoots) {
|
||||||
|
Get-ChildItem -LiteralPath $textRoot -Recurse -File | Where-Object {
|
||||||
|
$relativePath = [IO.Path]::GetRelativePath($taskWorkspaceRoot, $_.FullName)
|
||||||
|
if ($relativePath -match '(^|[\\/])(bin|obj|\.discard)([\\/]|$)') {
|
||||||
|
return $false
|
||||||
|
}
|
||||||
|
|
||||||
|
$nativeLibRoot = Join-Path $nativeProjectRoot 'lib'
|
||||||
|
if ($_.FullName.StartsWith(
|
||||||
|
$nativeLibRoot + [IO.Path]::DirectorySeparatorChar,
|
||||||
|
[StringComparison]::OrdinalIgnoreCase
|
||||||
|
) -and $_.Name -ne 'CMakeLists.txt') {
|
||||||
|
return $false
|
||||||
|
}
|
||||||
|
|
||||||
|
return $textExtensions.Contains($_.Extension)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function Read-TaskText {
|
||||||
|
param([Parameter(Mandatory)][string] $Path)
|
||||||
|
|
||||||
|
$bytes = [IO.File]::ReadAllBytes($Path)
|
||||||
|
$encoding = [Text.UTF8Encoding]::new($false, $true)
|
||||||
|
$preambleLength = 0
|
||||||
|
$preambleBytes = [byte[]]::new(0)
|
||||||
|
|
||||||
|
if ($bytes.Length -ge 3 -and
|
||||||
|
$bytes[0] -eq 0xEF -and $bytes[1] -eq 0xBB -and $bytes[2] -eq 0xBF) {
|
||||||
|
$preambleLength = 3
|
||||||
|
}
|
||||||
|
elseif ($bytes.Length -ge 2 -and $bytes[0] -eq 0xFF -and $bytes[1] -eq 0xFE) {
|
||||||
|
$encoding = [Text.UnicodeEncoding]::new($false, $false, $true)
|
||||||
|
$preambleLength = 2
|
||||||
|
}
|
||||||
|
elseif ($bytes.Length -ge 2 -and $bytes[0] -eq 0xFE -and $bytes[1] -eq 0xFF) {
|
||||||
|
$encoding = [Text.UnicodeEncoding]::new($true, $false, $true)
|
||||||
|
$preambleLength = 2
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($preambleLength -ne 0) {
|
||||||
|
$preambleBytes = [byte[]] $bytes[0..($preambleLength - 1)]
|
||||||
|
}
|
||||||
|
|
||||||
|
[PSCustomObject]@{
|
||||||
|
Text = $encoding.GetString($bytes, $preambleLength, $bytes.Length - $preambleLength)
|
||||||
|
Encoding = $encoding
|
||||||
|
Preamble = $preambleBytes
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function Write-TaskText {
|
||||||
|
param(
|
||||||
|
[Parameter(Mandatory)][string] $Path,
|
||||||
|
[Parameter(Mandatory)][string] $Text,
|
||||||
|
[Parameter(Mandatory)] $Encoding,
|
||||||
|
[Parameter(Mandatory)][AllowEmptyCollection()][byte[]] $Preamble
|
||||||
|
)
|
||||||
|
|
||||||
|
$body = $Encoding.GetBytes($Text)
|
||||||
|
$output = [byte[]]::new($Preamble.Length + $body.Length)
|
||||||
|
if ($Preamble.Length -ne 0) {
|
||||||
|
[Buffer]::BlockCopy($Preamble, 0, $output, 0, $Preamble.Length)
|
||||||
|
}
|
||||||
|
[Buffer]::BlockCopy($body, 0, $output, $Preamble.Length, $body.Length)
|
||||||
|
[IO.File]::WriteAllBytes($Path, $output)
|
||||||
|
}
|
||||||
|
|
||||||
|
$changedTextFiles = [Collections.Generic.List[string]]::new()
|
||||||
|
foreach ($textFile in Get-TaskTextFile) {
|
||||||
|
$fileContent = Read-TaskText -Path $textFile.FullName
|
||||||
|
$updatedText = $fileContent.Text
|
||||||
|
foreach ($rule in $replacementRules) {
|
||||||
|
$updatedText = [Text.RegularExpressions.Regex]::Replace(
|
||||||
|
$updatedText,
|
||||||
|
$rule.Pattern,
|
||||||
|
$rule.Replacement,
|
||||||
|
[Text.RegularExpressions.RegexOptions]::CultureInvariant
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($updatedText -ceq $fileContent.Text) {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
$relativePath = [IO.Path]::GetRelativePath($taskWorkspaceRoot, $textFile.FullName)
|
||||||
|
$changedTextFiles.Add($relativePath)
|
||||||
|
if ($Apply) {
|
||||||
|
Write-TaskText -Path $textFile.FullName `
|
||||||
|
-Text $updatedText `
|
||||||
|
-Encoding $fileContent.Encoding `
|
||||||
|
-Preamble $fileContent.Preamble
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$pathMoves = [Collections.Generic.List[object]]::new()
|
||||||
|
Get-ChildItem -LiteralPath $nativeProjectRoot -Recurse -File |
|
||||||
|
Where-Object {
|
||||||
|
$_.Name -match '^sn_' -or
|
||||||
|
$_.Name -cin @(
|
||||||
|
'StgSharpNative.h',
|
||||||
|
'NitloadInnovationFramework.h',
|
||||||
|
'NitloadFramework.h'
|
||||||
|
)
|
||||||
|
} |
|
||||||
|
ForEach-Object {
|
||||||
|
$newName = if ($_.Name -cin @(
|
||||||
|
'StgSharpNative.h',
|
||||||
|
'NitloadInnovationFramework.h',
|
||||||
|
'NitloadFramework.h'
|
||||||
|
)) {
|
||||||
|
'NitloadFrameWork.h'
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
$_.Name -replace '^sn_', 'nif_'
|
||||||
|
}
|
||||||
|
$pathMoves.Add([PSCustomObject]@{
|
||||||
|
Source = $_.FullName
|
||||||
|
Target = Join-Path $_.DirectoryName $newName
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
Get-ChildItem -LiteralPath $nativeProjectRoot -Recurse -Directory |
|
||||||
|
Where-Object { $_.Name -in @('sn-head', 'sn-src', 'sn-template') } |
|
||||||
|
Sort-Object { $_.FullName.Length } -Descending |
|
||||||
|
ForEach-Object {
|
||||||
|
$pathMoves.Add([PSCustomObject]@{
|
||||||
|
Source = $_.FullName
|
||||||
|
Target = Join-Path $_.Parent.FullName ($_.Name -replace '^sn-', 'nif-')
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach ($pathMove in $pathMoves) {
|
||||||
|
Test-TaskPath -Path $pathMove.Source
|
||||||
|
Test-TaskPath -Path $pathMove.Target
|
||||||
|
if (Test-Path -LiteralPath $pathMove.Target) {
|
||||||
|
throw "Rename target already exists: $($pathMove.Target)"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
"Text files to update: $($changedTextFiles.Count)"
|
||||||
|
$changedTextFiles | ForEach-Object { " TEXT $_" }
|
||||||
|
"Paths to rename: $($pathMoves.Count)"
|
||||||
|
$pathMoves | ForEach-Object {
|
||||||
|
$source = [IO.Path]::GetRelativePath($taskWorkspaceRoot, $_.Source)
|
||||||
|
$target = [IO.Path]::GetRelativePath($taskWorkspaceRoot, $_.Target)
|
||||||
|
" MOVE $source -> $target"
|
||||||
|
}
|
||||||
|
|
||||||
|
if (-not $Apply) {
|
||||||
|
'Dry run only. Re-run with -Apply to perform the migration.'
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach ($pathMove in $pathMoves) {
|
||||||
|
Move-Item -LiteralPath $pathMove.Source -Destination $pathMove.Target
|
||||||
|
}
|
||||||
|
|
||||||
|
'NIF prefix migration completed.'
|
||||||
Reference in New Issue
Block a user