Skip to content
Open
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -155,3 +155,4 @@ conda-bld

# Custom debug environment setup script for VS Code (used by scripts/debug_python)
/scripts/debug_env.sh
PR_DESCRIPTION.md
1 change: 1 addition & 0 deletions conda/environments/all_cuda-129_arch-aarch64.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ dependencies:
- imagecodecs>=2021.6.8
- ipython
- lazy-loader>=0.4
- libnvimgcodec-dev=0.6.0
- libnvjpeg-dev
- matplotlib-base>=3.7
- nbsphinx
Expand Down
1 change: 1 addition & 0 deletions conda/environments/all_cuda-129_arch-x86_64.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ dependencies:
- ipython
- lazy-loader>=0.4
- libcufile-dev
- libnvimgcodec-dev=0.6.0
- libnvjpeg-dev
- matplotlib-base>=3.7
- nbsphinx
Expand Down
1 change: 1 addition & 0 deletions conda/environments/all_cuda-130_arch-aarch64.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ dependencies:
- imagecodecs>=2021.6.8
- ipython
- lazy-loader>=0.4
- libnvimgcodec-dev=0.6.0
- libnvjpeg-dev
- matplotlib-base>=3.7
- nbsphinx
Expand Down
1 change: 1 addition & 0 deletions conda/environments/all_cuda-130_arch-x86_64.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ dependencies:
- ipython
- lazy-loader>=0.4
- libcufile-dev
- libnvimgcodec-dev=0.6.0
- libnvjpeg-dev
- matplotlib-base>=3.7
- nbsphinx
Expand Down
3 changes: 3 additions & 0 deletions conda/recipes/libcucim/conda_build_config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,3 +15,6 @@ c_stdlib_version:

cmake_version:
- ">=3.30.4"

nvimgcodec_version:
- ">=0.6.0"
3 changes: 3 additions & 0 deletions conda/recipes/libcucim/meta.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ requirements:
- cuda-cudart-dev
- libcufile-dev
- libnvjpeg-dev
- libnvimgcodec-dev {{ nvimgcodec_version }} # nvImageCodec development headers and libraries
- nvtx-c >=3.1.0
- openslide
run:
Expand All @@ -71,8 +72,10 @@ requirements:
{% endif %}
- cuda-cudart
- libnvjpeg
- libnvimgcodec0 {{ nvimgcodec_version }} # nvImageCodec runtime library
run_constrained:
- {{ pin_compatible('openslide') }}
- libnvimgcodec-dev {{ nvimgcodec_version }} # Optional: for development/debugging

about:
home: https://developer.nvidia.com/multidimensional-image-processing
Expand Down
240 changes: 240 additions & 0 deletions cpp/cmake/deps/nvimgcodec.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,240 @@
#
# Copyright (c) 2020-2025, NVIDIA CORPORATION.
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#

if (NOT TARGET deps::nvimgcodec)
# Option to automatically install nvImageCodec via conda
option(AUTO_INSTALL_NVIMGCODEC "Automatically install nvImageCodec via conda" ON)
set(NVIMGCODEC_VERSION "0.6.0" CACHE STRING "nvImageCodec version to install")

# Automatic installation logic
if(AUTO_INSTALL_NVIMGCODEC)
message(STATUS "Configuring automatic nvImageCodec installation...")

# Try to find micromamba or conda in various locations
find_program(MICROMAMBA_EXECUTABLE
NAMES micromamba
PATHS ${CMAKE_CURRENT_SOURCE_DIR}/../../../bin
${CMAKE_CURRENT_SOURCE_DIR}/../../bin
${CMAKE_CURRENT_SOURCE_DIR}/bin
$ENV{HOME}/micromamba/bin
$ENV{HOME}/.local/bin
/usr/local/bin
/opt/conda/bin
/opt/miniconda/bin
DOC "Path to micromamba executable"
)

find_program(CONDA_EXECUTABLE
NAMES conda mamba
PATHS $ENV{HOME}/miniconda3/bin
$ENV{HOME}/anaconda3/bin
/opt/conda/bin
/opt/miniconda/bin
/usr/local/bin
DOC "Path to conda/mamba executable"
)

# Determine which conda tool to use
set(CONDA_CMD "")
set(CONDA_TYPE "")
if(MICROMAMBA_EXECUTABLE)
set(CONDA_CMD ${MICROMAMBA_EXECUTABLE})
set(CONDA_TYPE "micromamba")
message(STATUS "Found micromamba: ${MICROMAMBA_EXECUTABLE}")
elseif(CONDA_EXECUTABLE)
set(CONDA_CMD ${CONDA_EXECUTABLE})
set(CONDA_TYPE "conda")
message(STATUS "Found conda/mamba: ${CONDA_EXECUTABLE}")
endif()

if(CONDA_CMD)
# Check if nvImageCodec is already installed
message(STATUS "Checking for existing nvImageCodec installation...")
execute_process(
COMMAND ${CONDA_CMD} list libnvimgcodec-dev
RESULT_VARIABLE NVIMGCODEC_CHECK_RESULT
OUTPUT_VARIABLE NVIMGCODEC_CHECK_OUTPUT
ERROR_QUIET
)

# Parse version from output if installed
set(NVIMGCODEC_INSTALLED_VERSION "")
if(NVIMGCODEC_CHECK_RESULT EQUAL 0)
string(REGEX MATCH "libnvimgcodec-dev[ ]+([0-9]+\\.[0-9]+\\.[0-9]+)"
VERSION_MATCH "${NVIMGCODEC_CHECK_OUTPUT}")
if(CMAKE_MATCH_1)
set(NVIMGCODEC_INSTALLED_VERSION ${CMAKE_MATCH_1})
endif()
endif()

# Install or upgrade if needed
set(NEED_INSTALL FALSE)
if(NOT NVIMGCODEC_CHECK_RESULT EQUAL 0)
message(STATUS "nvImageCodec not found - installing version ${NVIMGCODEC_VERSION}")
set(NEED_INSTALL TRUE)
elseif(NVIMGCODEC_INSTALLED_VERSION AND NVIMGCODEC_INSTALLED_VERSION VERSION_LESS NVIMGCODEC_VERSION)
message(STATUS "nvImageCodec ${NVIMGCODEC_INSTALLED_VERSION} found - upgrading to ${NVIMGCODEC_VERSION}")
set(NEED_INSTALL TRUE)
else()
message(STATUS "nvImageCodec ${NVIMGCODEC_INSTALLED_VERSION} already installed (>= ${NVIMGCODEC_VERSION})")
endif()

if(NEED_INSTALL)
# Install nvImageCodec with specific version
message(STATUS "Installing nvImageCodec ${NVIMGCODEC_VERSION} via ${CONDA_TYPE}...")
execute_process(
COMMAND ${CONDA_CMD} install
libnvimgcodec-dev=${NVIMGCODEC_VERSION}
libnvimgcodec0=${NVIMGCODEC_VERSION}
-c conda-forge -y
RESULT_VARIABLE CONDA_INSTALL_RESULT
OUTPUT_VARIABLE CONDA_INSTALL_OUTPUT
ERROR_VARIABLE CONDA_INSTALL_ERROR
TIMEOUT 300 # 5 minute timeout
)

if(CONDA_INSTALL_RESULT EQUAL 0)
message(STATUS "โœ“ Successfully installed nvImageCodec ${NVIMGCODEC_VERSION}")
else()
message(WARNING "โœ— Failed to install nvImageCodec via ${CONDA_TYPE}")
message(WARNING "Error: ${CONDA_INSTALL_ERROR}")

# Try alternative installation without version constraint
message(STATUS "Attempting installation without version constraint...")
execute_process(
COMMAND ${CONDA_CMD} install libnvimgcodec-dev libnvimgcodec0 -c conda-forge -y
RESULT_VARIABLE CONDA_FALLBACK_RESULT
OUTPUT_QUIET
ERROR_QUIET
)

if(CONDA_FALLBACK_RESULT EQUAL 0)
message(STATUS "โœ“ Fallback installation successful")
else()
message(WARNING "โœ— Fallback installation also failed")
endif()
endif()
endif()
else()
message(STATUS "No conda/micromamba found - skipping automatic installation")
endif()
endif()

# First try to find it as a package
find_package(nvimgcodec QUIET)

if(nvimgcodec_FOUND)
# Use the found package
add_library(deps::nvimgcodec INTERFACE IMPORTED GLOBAL)
target_link_libraries(deps::nvimgcodec INTERFACE nvimgcodec::nvimgcodec)
message(STATUS "โœ“ nvImageCodec found via find_package")
else()
# Manual detection in various environments
set(NVIMGCODEC_LIB_PATH "")
set(NVIMGCODEC_INCLUDE_PATH "")

# Try conda environment detection (both Python packages and native packages)
if(DEFINED ENV{CONDA_BUILD})
# Conda build environment
set(NVIMGCODEC_LIB_PATH "$ENV{PREFIX}/lib/libnvimgcodec.so.0")
set(NVIMGCODEC_INCLUDE_PATH "$ENV{PREFIX}/include/")
if(NOT EXISTS "${NVIMGCODEC_LIB_PATH}")
set(NVIMGCODEC_LIB_PATH "$ENV{PREFIX}/lib/libnvimgcodec.so")
endif()
elseif(DEFINED ENV{CONDA_PREFIX})
# Active conda environment - try native package first
set(CONDA_NATIVE_ROOT "$ENV{CONDA_PREFIX}")
if(EXISTS "${CONDA_NATIVE_ROOT}/include/nvimgcodec.h")
set(NVIMGCODEC_INCLUDE_PATH "${CONDA_NATIVE_ROOT}/include/")
if(EXISTS "${CONDA_NATIVE_ROOT}/lib/libnvimgcodec.so.0")
set(NVIMGCODEC_LIB_PATH "${CONDA_NATIVE_ROOT}/lib/libnvimgcodec.so.0")
elseif(EXISTS "${CONDA_NATIVE_ROOT}/lib/libnvimgcodec.so")
set(NVIMGCODEC_LIB_PATH "${CONDA_NATIVE_ROOT}/lib/libnvimgcodec.so")
endif()
else()
# Fallback: try Python site-packages in conda environment
foreach(PY_VER "3.13" "3.12" "3.11" "3.10" "3.9")
set(CONDA_PYTHON_ROOT "$ENV{CONDA_PREFIX}/lib/python${PY_VER}/site-packages/nvidia/nvimgcodec")
if(EXISTS "${CONDA_PYTHON_ROOT}/include/nvimgcodec.h")
set(NVIMGCODEC_INCLUDE_PATH "${CONDA_PYTHON_ROOT}/include/")
if(EXISTS "${CONDA_PYTHON_ROOT}/lib/libnvimgcodec.so.0")
set(NVIMGCODEC_LIB_PATH "${CONDA_PYTHON_ROOT}/lib/libnvimgcodec.so.0")
elseif(EXISTS "${CONDA_PYTHON_ROOT}/lib/libnvimgcodec.so")
set(NVIMGCODEC_LIB_PATH "${CONDA_PYTHON_ROOT}/lib/libnvimgcodec.so")
endif()
break()
endif()
endforeach()
endif()
else()
# Try Python site-packages detection
find_package(Python3 COMPONENTS Interpreter)
if(Python3_FOUND)
execute_process(
COMMAND ${Python3_EXECUTABLE} -c "import site; print(site.getsitepackages()[0])"
OUTPUT_VARIABLE PYTHON_SITE_PACKAGES
OUTPUT_STRIP_TRAILING_WHITESPACE
ERROR_QUIET
)

if(PYTHON_SITE_PACKAGES)
set(NVIMGCODEC_PYTHON_ROOT "${PYTHON_SITE_PACKAGES}/nvidia/nvimgcodec")
if(EXISTS "${NVIMGCODEC_PYTHON_ROOT}/include/nvimgcodec.h")
set(NVIMGCODEC_INCLUDE_PATH "${NVIMGCODEC_PYTHON_ROOT}/include/")
if(EXISTS "${NVIMGCODEC_PYTHON_ROOT}/lib/libnvimgcodec.so.0")
set(NVIMGCODEC_LIB_PATH "${NVIMGCODEC_PYTHON_ROOT}/lib/libnvimgcodec.so.0")
elseif(EXISTS "${NVIMGCODEC_PYTHON_ROOT}/lib/libnvimgcodec.so")
set(NVIMGCODEC_LIB_PATH "${NVIMGCODEC_PYTHON_ROOT}/lib/libnvimgcodec.so")
endif()
endif()
endif()
endif()

# System-wide installation fallback
if(NOT NVIMGCODEC_LIB_PATH)
if(EXISTS /usr/lib/x86_64-linux-gnu/libnvimgcodec.so.0)
set(NVIMGCODEC_LIB_PATH /usr/lib/x86_64-linux-gnu/libnvimgcodec.so.0)
set(NVIMGCODEC_INCLUDE_PATH "/usr/include/")
elseif(EXISTS /usr/lib/aarch64-linux-gnu/libnvimgcodec.so.0)
set(NVIMGCODEC_LIB_PATH /usr/lib/aarch64-linux-gnu/libnvimgcodec.so.0)
set(NVIMGCODEC_INCLUDE_PATH "/usr/include/")
elseif(EXISTS /usr/lib64/libnvimgcodec.so.0) # CentOS (x86_64)
set(NVIMGCODEC_LIB_PATH /usr/lib64/libnvimgcodec.so.0)
set(NVIMGCODEC_INCLUDE_PATH "/usr/include/")
endif()
endif()
endif()

# Create the target if we found the library
if(NVIMGCODEC_LIB_PATH AND EXISTS "${NVIMGCODEC_LIB_PATH}")
add_library(deps::nvimgcodec SHARED IMPORTED GLOBAL)
set_target_properties(deps::nvimgcodec PROPERTIES
IMPORTED_LOCATION "${NVIMGCODEC_LIB_PATH}"
INTERFACE_INCLUDE_DIRECTORIES "${NVIMGCODEC_INCLUDE_PATH}"
)
message(STATUS "โœ“ nvImageCodec found:")
message(STATUS " Library: ${NVIMGCODEC_LIB_PATH}")
message(STATUS " Headers: ${NVIMGCODEC_INCLUDE_PATH}")
else()
# Create a dummy target to prevent build failures
add_library(deps::nvimgcodec INTERFACE IMPORTED GLOBAL)
message(STATUS "โœ— nvImageCodec not found - GPU acceleration disabled")
message(STATUS "To enable nvImageCodec support:")
message(STATUS " Option 1 (conda): micromamba install libnvimgcodec-dev -c conda-forge")
message(STATUS " Option 2 (pip): pip install nvidia-nvimgcodec-cu12[all]")
message(STATUS " Option 3 (cmake): cmake -DAUTO_INSTALL_NVIMGCODEC=ON ..")
endif()
endif()
endif()
86 changes: 86 additions & 0 deletions cpp/plugins/cucim.kit.cuslide2/.clang-format
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
AccessModifierOffset: -4
AlignAfterOpenBracket: Align
AlignConsecutiveAssignments: false
AlignConsecutiveDeclarations: false
AlignEscapedNewlinesLeft: false
AlignTrailingComments: false
AllowAllParametersOfDeclarationOnNextLine: true
AllowShortFunctionsOnASingleLine: false
AllowShortIfStatementsOnASingleLine: false
AllowShortCaseLabelsOnASingleLine : false
AllowShortLoopsOnASingleLine: false
AlwaysBreakAfterDefinitionReturnType: false
AlwaysBreakBeforeMultilineStrings: true
AlwaysBreakTemplateDeclarations: true
BinPackArguments: true
BinPackParameters: false
BreakBeforeBinaryOperators: false
BreakBeforeBraces: Custom
BraceWrapping:
AfterClass: true
AfterControlStatement: true
AfterEnum: true
AfterFunction: true
AfterNamespace: true
AfterObjCDeclaration: true
AfterStruct: true
AfterUnion: true
AfterExternBlock: true
BeforeCatch: true
BeforeElse: true
IndentBraces: false
SplitEmptyFunction: true
SplitEmptyRecord: true
SplitEmptyNamespace : true
BreakBeforeTernaryOperators: false
BreakConstructorInitializersBeforeComma: false
BreakStringLiterals: false
ColumnLimit: 120
CommentPragmas: ''
ConstructorInitializerAllOnOneLineOrOnePerLine: true
ConstructorInitializerIndentWidth: 4
ContinuationIndentWidth: 4
Cpp11BracedListStyle: false
DerivePointerBinding: false
FixNamespaceComments: true
IndentCaseLabels: false
IndentPPDirectives: AfterHash
IndentFunctionDeclarationAfterType: false
IndentWidth: 4
SortIncludes: false
IncludeCategories:
- Regex: '[<"](.*\/)?Defines.h[>"]'
Priority: 1
# - Regex: '<cuslide\/.+>'
# Priority: 3
- Regex: '<[[:alnum:]_.]+>'
Priority: 5
- Regex: '<[[:alnum:]_.\/]+>'
Priority: 4
- Regex: '".*"'
Priority: 2
IncludeBlocks: Regroup
Language: Cpp
MaxEmptyLinesToKeep: 2
NamespaceIndentation: None
ObjCSpaceAfterProperty: true
ObjCSpaceBeforeProtocolList: true
PenaltyBreakBeforeFirstCallParameter: 0
PenaltyBreakComment: 1
PenaltyBreakFirstLessLess: 0
PenaltyBreakString: 1
PenaltyExcessCharacter: 10
PenaltyReturnTypeOnItsOwnLine: 1000
PointerAlignment: Left
SpaceBeforeAssignmentOperators: true
SpaceBeforeParens: ControlStatements
SpaceInEmptyParentheses: false
SpacesBeforeTrailingComments: 1
SpacesInAngles: false
SpacesInCStyleCastParentheses: false
SpacesInContainerLiterals: false
SpacesInParentheses: false
Standard: Cpp11
ReflowComments: true
TabWidth: 4
UseTab: Never
7 changes: 7 additions & 0 deletions cpp/plugins/cucim.kit.cuslide2/.editorconfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
[*]
indent_style = space
indent_size = 4
charset = utf-8
trim_trailing_whitespace = true
max_line_length = 120
insert_final_newline = true
Loading