-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Roi pool operator #5831
Roi pool operator #5831
Conversation
25f84c7
to
e9d8c71
Compare
paddle/operators/roi_pool_op.cu
Outdated
|
||
#define FLT_MAX __FLT_MAX__ | ||
|
||
constexpr int PADDLE_OPERATORS_ROIPOOL_CUDA_NUM_THREADS = 512; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
According to https://google.github.io/styleguide/cppguide.html#Constant_Names, constants should be named as
constexpr int kPaddleOperatorsROIPoolNumCUDAThreads = 512;
Also, I vaguely remember (but not sure) that we can declare this variable static so to limit its usage within this file, and we can have a much shorter name for it:
static constexpr int kNumCUDAThreads = 512;
paddle/operators/roi_pool_op.cu
Outdated
namespace paddle { | ||
namespace operators { | ||
|
||
#define FLT_MAX __FLT_MAX__ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The use of __FLT_MAX__
is not a good idea because it is a GCC-specific predefined macro. If we are using another compiler other than GCC, it is probable that we don't have __FLT_MAX__
defined.
It seems to me that the solution could be using standard C library
#include <float.h>
printf("%f", FLT_MAX);
or the standard C++ library
#include <limits>
printf("%f", numeric_limits<float>::max());
This problem doesn't block the merge of this PR. I created an issue reminding us to fix it.
paddle/operators/roi_pool_op.cu
Outdated
constexpr int PADDLE_OPERATORS_ROIPOOL_CUDA_NUM_THREADS = 512; | ||
constexpr int PADDLE_OPERATORS_ROIPOOL_MAXIMUM_NUM_BLOCKS = 4096; | ||
|
||
inline int PADDLE_OPERATORS_ROIPOOL_GET_BLOCKS(const int N) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I understand that you might want to mark this function returning a constant value, but according to the Google C++ Style Guide, we should name functions something like
static inline int NumBlocks(const int N) {
paddle/operators/roi_pool_op.cc
Outdated
namespace paddle { | ||
namespace operators { | ||
|
||
class RoiPoolOp : public framework::OperatorWithKernel { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I understand that in many places of our codebase, we haven't strictly followed the English writing rule that acronyms must be capitalized, but let us start doing so from here by changing Roi
into ROI
. Thanks!
paddle/operators/roi_pool_op.cu
Outdated
int c = (index / pooled_width / pooled_height) % channels; | ||
int n = index / pooled_width / pooled_height / channels; | ||
|
||
const int64_t* offset_input_rois = input_rois + n * 5; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about add a comment about the magic number 5, or define it a constexpr value?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
Is this ROIPool operator being added into CMakeLists.txt? @wanghaox |
a9a3f15
to
1aba956
Compare
paddle/operators/roi_pool_op.h
Outdated
"The spatial scale must greater than 0"); | ||
|
||
auto in_dims = in->dims(); | ||
int batch_size = in_dims[0]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Might it be better to add dim ENFORCE
of input before or in inferShape
since the usage of in_dim
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
int channels = in_dims[1]; | ||
int height = in_dims[2]; | ||
int width = in_dims[3]; | ||
int rois_num = rois->dims()[0]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Similar with in_dims
, might it be better to add dim ENFORCE before.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
paddle/operators/roi_pool_op.cc
Outdated
"(Tensor), " | ||
"ROIs (Regions of Interest) to pool over. " | ||
"Should be a 2-D tensor of shape (num_rois, 5)" | ||
"given as [[batch_id, x1, y1, x2, y2], …]."); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Might it be better to declare what each of [batch_id, x1, y1, x2, y2]
represents for. And some spelling like Should
should be correct.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cc
Outdated
: OpProtoAndCheckerMaker(proto, op_checker) { | ||
AddInput("X", | ||
"(Tensor), " | ||
"the input of ROIPoolOp."); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Addition of the shape and meaning(like feature maps from conv) of X
might be better.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.h
Outdated
out_dims[1] = channels; | ||
out_dims[2] = pooled_height; | ||
out_dims[3] = pooled_width; | ||
out->Resize(out_dims); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Might it be better to set shape in inferShape
rather than shape resizing in here, but I am not sure whether actual shapes are necessary for inferShape
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
paddle/operators/roi_pool_op.cc
Outdated
"given as [[batch_id, x1, y1, x2, y2], …]."); | ||
AddOutput("Out", | ||
"(Tensor), " | ||
"ROI pooled output 4-D tensor of shape " |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe "The output of ROIPoolOp is a 4-D tensor with shape" is better.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
|
||
auto in_dims = in->dims(); | ||
auto in_stride = framework::stride(in_dims); | ||
int channels = in_dims[1]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Similar to the CPU kernel, might it be better to add dim ENFORCE before.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
paddle/operators/roi_pool_op.cu
Outdated
out->mutable_data<T>(ctx.GetPlace()), | ||
argmax->mutable_data<int64_t>(ctx.GetPlace())); | ||
|
||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about deleting the return
in here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
pooled_width, | ||
x_grad->mutable_data<T>(ctx.GetPlace())); | ||
} | ||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about deleting the return
in here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
auto spatial_scale = ctx.Attr<float>("spatial_scale"); | ||
|
||
int rois_num = rois->dims()[0]; | ||
int channels = in->dims()[1]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Similar to the CPU kernel, might it be better to add dim ENFORCE before.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
update code
paddle/operators/roi_pool_op.cc
Outdated
: OpProtoAndCheckerMaker(proto, op_checker) { | ||
AddInput("X", | ||
"(Tensor), " | ||
"the input of ROIPoolOp."); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cc
Outdated
"(Tensor), " | ||
"ROIs (Regions of Interest) to pool over. " | ||
"Should be a 2-D tensor of shape (num_rois, 5)" | ||
"given as [[batch_id, x1, y1, x2, y2], …]."); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cc
Outdated
"given as [[batch_id, x1, y1, x2, y2], …]."); | ||
AddOutput("Out", | ||
"(Tensor), " | ||
"ROI pooled output 4-D tensor of shape " |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
out->mutable_data<T>(ctx.GetPlace()), | ||
argmax->mutable_data<int64_t>(ctx.GetPlace())); | ||
|
||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
pooled_width, | ||
x_grad->mutable_data<T>(ctx.GetPlace())); | ||
} | ||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
int channels = in_dims[1]; | ||
int height = in_dims[2]; | ||
int width = in_dims[3]; | ||
int rois_num = rois->dims()[0]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
paddle/operators/roi_pool_op.cu
Outdated
auto spatial_scale = ctx.Attr<float>("spatial_scale"); | ||
|
||
int rois_num = rois->dims()[0]; | ||
int channels = in->dims()[1]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
paddle/operators/roi_pool_op.cu
Outdated
|
||
auto in_dims = in->dims(); | ||
auto in_stride = framework::stride(in_dims); | ||
int channels = in_dims[1]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, added at ROIPoolOp::InferShape()
for w in range(wstart, wend): | ||
if x_i[c, h, w] > out_data[i, c, ph, pw]: | ||
out_data[i, c, ph, pw] = x_i[c, h, w] | ||
argmax_data[i, c, ph, pw] = h * \ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
python needs the '\'
size_t pool_channel_offset = pooled_height * pooled_width; | ||
const int64_t* argmax_data = argmax->data<int64_t>(); | ||
|
||
for (size_t n = 0; n < rois_num; ++n) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cc
Outdated
ops::CPUROIPoolOpKernel<paddle::platform::CPUPlace, float>); | ||
REGISTER_OP_CPU_KERNEL( | ||
roi_pool_grad, | ||
ops::CPUROIPoolGradOpKernel<paddle::platform::CPUPlace, float>); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Need to register double type. And please check whether the slice_sequence_op
registered double type, thanks.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, slice_sequence_op will be fixed in another commit.
paddle/operators/roi_pool_op.h
Outdated
#pragma once | ||
#include "paddle/framework/op_registry.h" | ||
#include "paddle/operators/math/math_function.h" | ||
#include "paddle/operators/strided_memcpy.h" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This header file is not used?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.h
Outdated
|
||
using Tensor = framework::Tensor; | ||
using LoDTensor = framework::LoDTensor; | ||
using LoD = framework::LoD; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
see comments: #5826 (comment)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.h
Outdated
// Define an empty pooling region to be zero | ||
bool is_empty = (hend <= hstart) || (wend <= wstart); | ||
output_data[pool_index] = | ||
is_empty ? 0 : -std::numeric_limits<float>::max(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
-std::numeric_limits<T>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.h
Outdated
int64_t* argmax_data = argmax->mutable_data<int64_t>(ctx.GetPlace()); | ||
|
||
math::SetConstant<Place, T> set_zero; | ||
set_zero(ctx.device_context(), out, static_cast<T>(0)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There is no need to set out zero here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
"The format of input tensor is NCHW."); | ||
PADDLE_ENFORCE(rois_dims.size() == 2, | ||
"ROIs should be a 2-D tensor of shape (num_rois, 5)" | ||
"given as [[batch_id, x1, y1, x2, y2], …]."); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also needs to check rois_dims[1] == kROISize
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
set_zero(ctx.device_context(), out, static_cast<T>(0)); | ||
argmax->mutable_data<int64_t>(ctx.GetPlace()); | ||
math::SetConstant<Place, int64_t> set_init; | ||
set_init(ctx.device_context(), argmax, static_cast<int64_t>(-1)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There is no need to set out zero and set argmax -1 here. For GPU, will launch two kernels twice here. Please remove these and handle them in GPUROIPoolForward
correctly.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
if (x_grad) { | ||
x_grad->mutable_data<T>(ctx.GetPlace()); | ||
math::SetConstant<Place, T> set_zero; | ||
set_zero(ctx.device_context(), x_grad, static_cast<T>(0)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same as above, there is no need to set zero here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
checked, bp needs to set zero.
paddle/operators/roi_pool_op.cu
Outdated
ops::GPUROIPoolOpKernel<paddle::platform::GPUPlace, float>); | ||
REGISTER_OP_GPU_KERNEL( | ||
roi_pool_grad, | ||
ops::GPUROIPoolGradOpKernel<paddle::platform::GPUPlace, float>); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
register double type.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
wstart = min(max(wstart + roi_start_w, 0), self.width) | ||
wend = min(max(wend + roi_start_w, 0), self.width) | ||
|
||
out_data[i, c, ph, pw] = 0 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As @guoshengCS said, why the code here is not consistant with C++:
// Define an empty pooling region to be zero
bool is_empty = (hend <= hstart) || (wend <= wstart);
output_data[pool_index] = is_empty ? 0 : -std::numeric_limits<float>::max();
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
update code
"The format of input tensor is NCHW."); | ||
PADDLE_ENFORCE(rois_dims.size() == 2, | ||
"ROIs should be a 2-D tensor of shape (num_rois, 5)" | ||
"given as [[batch_id, x1, y1, x2, y2], …]."); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cc
Outdated
ops::CPUROIPoolOpKernel<paddle::platform::CPUPlace, float>); | ||
REGISTER_OP_CPU_KERNEL( | ||
roi_pool_grad, | ||
ops::CPUROIPoolGradOpKernel<paddle::platform::CPUPlace, float>); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done, slice_sequence_op will be fixed in another commit.
paddle/operators/roi_pool_op.cu
Outdated
static inline int NumBlocks(const int N) { | ||
return std::min((N + kNumCUDAThreads - 1) / kNumCUDAThreads, | ||
kNumMaxinumNumBlocks); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
ops::GPUROIPoolOpKernel<paddle::platform::GPUPlace, float>); | ||
REGISTER_OP_GPU_KERNEL( | ||
roi_pool_grad, | ||
ops::GPUROIPoolGradOpKernel<paddle::platform::GPUPlace, float>); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.h
Outdated
#pragma once | ||
#include "paddle/framework/op_registry.h" | ||
#include "paddle/operators/math/math_function.h" | ||
#include "paddle/operators/strided_memcpy.h" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.cu
Outdated
set_zero(ctx.device_context(), out, static_cast<T>(0)); | ||
argmax->mutable_data<int64_t>(ctx.GetPlace()); | ||
math::SetConstant<Place, int64_t> set_init; | ||
set_init(ctx.device_context(), argmax, static_cast<int64_t>(-1)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
if (x_grad) { | ||
x_grad->mutable_data<T>(ctx.GetPlace()); | ||
math::SetConstant<Place, T> set_zero; | ||
set_zero(ctx.device_context(), x_grad, static_cast<T>(0)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
checked, bp needs to set zero.
paddle/operators/roi_pool_op.h
Outdated
|
||
using Tensor = framework::Tensor; | ||
using LoDTensor = framework::LoDTensor; | ||
using LoD = framework::LoD; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
paddle/operators/roi_pool_op.h
Outdated
int64_t* argmax_data = argmax->mutable_data<int64_t>(ctx.GetPlace()); | ||
|
||
math::SetConstant<Place, T> set_zero; | ||
set_zero(ctx.device_context(), out, static_cast<T>(0)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
wstart = min(max(wstart + roi_start_w, 0), self.width) | ||
wend = min(max(wend + roi_start_w, 0), self.width) | ||
|
||
out_data[i, c, ph, pw] = 0 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM.
resolve #5788
Add CPU forward and backward kernel code
Add GPU forward and backward kernel code
Add unitest