-----2019-7-22 更新
mmdetection 维护人员看来很用心啊,已经适配到了最新的pytorch 1.1 并且修改了编译的方式,看来是要官方支持Windows了,但是目前win下有两个bug 。
sigmoid_focal_loss 和 mask 那个层的编译有问题。官方作者在github 上已经给予了回复。貌似是torch的bug
目前如果想用的话,只能先注释掉相关的代码。
商汤科技(2018 COCO 目标检测挑战赛冠军)和香港中文大学最近开源了一个基于Pytorch实现的深度学习目标检测工具箱mmdetection,支持Faster-RCNN,Mask-RCNN,Fast-RCNN等主流的目标检测框架,后续会加入Cascade-RCNN以及其他一系列目标检测框架。
相比于Facebook开源的Detectron框架,作者声称mmdetection有三点优势:performance稍高、训练速度稍快、所需显存稍小。
我很早就听说了这个工具箱,但是一直没有开源。现在总算是开源了,发现官方没有对Windows系统进行适配,于是就迫不及待地对win10 进行了适配。下面将记录一下
首先官方给出的编译的方法是./compile.sh 我们发现这里面其实是执行了4 个python脚本,但是这4个setup.py 在win下执行会报错,我修改了一个版本。
首先dcn 目录下的setup.py 修改为两个文件,否则链接时候会出现错误。分别为setup_conv.py setup_pool.py
import os
from setuptools import setup
from torch.utils.cpp_extension import BuildExtension, CUDAExtension,CppExtension,CUDA_HOME
import torch
def get_extensions():
this_dir = os.path.dirname(os.path.abspath(__file__))
extension = CppExtension
extra_compile_args = {"cxx": []}
define_macros = []
sources=[
'src/deform_conv_cuda.cpp',
'src/deform_conv_cuda_kernel.cu']
if torch.cuda.is_available() and CUDA_HOME is not None:
extension = CUDAExtension
extra_compile_args["nvcc"] = [
"-DCUDA_HAS_FP16=1",
"-D__CUDA_NO_HALF_OPERATORS__",
"-D__CUDA_NO_HALF_CONVERSIONS__",
"-D__CUDA_NO_HALF2_OPERATORS__",
]
ext_modules = [
extension(
"deform_conv_cuda",
sources,
extra_compile_args=extra_compile_args,
),
]
return ext_modules
setup(
name='deform_conv',
ext_modules=get_extensions(),
cmdclass={'build_ext': BuildExtension})
import os
from setuptools import setup
from torch.utils.cpp_extension import BuildExtension, CUDAExtension,CppExtension,CUDA_HOME
import torch
def get_extensions():
this_dir = os.path.dirname(os.path.abspath(__file__))
extension = CppExtension
extra_compile_args = {"cxx": []}
define_macros = []
sources=[
'src/deform_pool_cuda.cpp',
'src/deform_pool_cuda_kernel.cu'
]
if torch.cuda.is_available() and CUDA_HOME is not None:
extension = CUDAExtension
extra_compile_args["nvcc"] = [
"-DCUDA_HAS_FP16=1",
"-D__CUDA_NO_HALF_OPERATORS__",
"-D__CUDA_NO_HALF_CONVERSIONS__",
"-D__CUDA_NO_HALF2_OPERATORS__",
]
ext_modules = [
extension(
"deform_pool_cuda",
sources,
extra_compile_args=extra_compile_args,
),
]
return ext_modules
setup(
name='deform_conv',
ext_modules=get_extensions(),
cmdclass={'build_ext': BuildExtension})
接着 nms 目录下,
import os.path as osp
from setuptools import setup, Extension
import numpy as np
from Cython.Build import cythonize
from Cython.Distutils import build_ext
from torch.utils.cpp_extension import BuildExtension, CUDAExtension
ext_args = dict(
include_dirs=[np.get_include()],
language='c++',
extra_compile_args={
'cc': ['-Wno-unused-function', '-Wno-write-strings'],
'nvcc': ['-c', '--compiler-options', '-fPIC'],
},
)
extensions = [
Extension('soft_nms_cpu', ['src/soft_nms_cpu.pyx'], **ext_args),
]
def customize_compiler_for_nvcc(self):
"""inject deep into distutils to customize how the dispatch
to cc/nvcc works.
If you subclass UnixCCompiler, it's not trivial to get your subclass
injected in, and still have the right customizations (i.e.
distutils.sysconfig.customize_compiler) run on it. So instead of going
the OO route, I have this. Note, it's kindof like a wierd functional
subclassing going on."""
# tell the compiler it can processes .cu
self.src_extensions.append('.cu')
super = self._compile
# now redefine the _compile method. This gets executed for each
# object but distutils doesn't have the ability to change compilers
# based on source extension: we add it.
def _compile(obj, src, ext, cc_args, extra_postargs, pp_opts):
if osp.splitext(src)[1] == '.cu':
# use the cuda for .cu files
self.set_executable('nvcc')
# use only a subset of the extra_postargs, which are 1-1 translated
# from the extra_compile_args in the Extension class
postargs = extra_postargs['nvcc']
else:
postargs = extra_postargs['cc']
super(obj, src, ext, cc_args, postargs, pp_opts)
# inject our redefined _compile method into the class
self._compile = _compile
class custom_build_ext(build_ext):
def build_extensions(self):
customize_compiler_for_nvcc(self.compiler)
build_ext.build_extensions(self)
setup(
name='soft_nms',
cmdclass={'build_ext': custom_build_ext},
ext_modules=cythonize(extensions),
)
setup(
name='nms_cuda',
ext_modules=[
CUDAExtension('nms_cuda', [
'src/nms_cuda.cpp',
'src/nms_kernel.cu',
]),
CUDAExtension('nms_cpu', [
'src/nms_cpu.cpp',
]),
],
cmdclass={'build_ext': BuildExtension})
roi_align 目录下
import os
from setuptools import setup
from torch.utils.cpp_extension import BuildExtension, CUDAExtension,CppExtension,CUDA_HOME
import torch
def get_extensions():
this_dir = os.path.dirname(os.path.abspath(__file__))
extension = CppExtension
extra_compile_args = {"cxx": []}
define_macros = []
sources=[
'src/roi_align_cuda.cpp',
'src/roi_align_kernel.cu']
if torch.cuda.is_available() and CUDA_HOME is not None:
extension = CUDAExtension
extra_compile_args["nvcc"] = [
"-DCUDA_HAS_FP16=1",
"-D__CUDA_NO_HALF_OPERATORS__",
"-D__CUDA_NO_HALF_CONVERSIONS__",
"-D__CUDA_NO_HALF2_OPERATORS__",
]
ext_modules = [
extension(
"roi_align_cuda",
sources,
extra_compile_args=extra_compile_args,
)
]
return ext_modules
setup(
name='roi_align_cuda',
ext_modules=get_extensions(),
cmdclass={'build_ext': BuildExtension})
roi_pool 目录下
import os
from setuptools import setup
from torch.utils.cpp_extension import BuildExtension, CUDAExtension,CppExtension,CUDA_HOME
import torch
def get_extensions():
this_dir = os.path.dirname(os.path.abspath(__file__))
extension = CppExtension
extra_compile_args = {"cxx": []}
define_macros = []
sources=[
'src/roi_pool_cuda.cpp',
'src/roi_pool_kernel.cu']
if torch.cuda.is_available() and CUDA_HOME is not None:
extension = CUDAExtension
extra_compile_args["nvcc"] = [
"-DCUDA_HAS_FP16=1",
"-D__CUDA_NO_HALF_OPERATORS__",
"-D__CUDA_NO_HALF_CONVERSIONS__",
"-D__CUDA_NO_HALF2_OPERATORS__",
]
ext_modules = [
extension(
"roi_pool_cuda",
sources,
extra_compile_args=extra_compile_args,
)
]
return ext_modules
setup(
name='roi_pool_cuda',
ext_modules=get_extensions(),
cmdclass={'build_ext': BuildExtension})
至此,就修改完了全部的setup.py 然后去各个目录分别执行python setup.py build_ext --inplace
执行完成之后,到项目根目录下执行 python setuy.py install 即可。
注意,VC++ 版本要和cuda 版本对应上,pytorch版本1.0 以上,
Windows不支持distribution 库,训练时候,可能需要相应的修改源码,否则会报错。