From 1a26f5a548d9631a8e3e6ba2880087637307a616 Mon Sep 17 00:00:00 2001 From: Abhinav Arora Date: Fri, 27 Oct 2017 10:51:54 -0700 Subject: [PATCH 1/3] Adding the Sign Op for L1 Weight Decay Regularization (#5138) --- paddle/operators/sign_op.cc | 70 +++++++++++++++++++ paddle/operators/sign_op.cu | 18 +++++ paddle/operators/sign_op.h | 38 ++++++++++ .../paddle/v2/framework/tests/test_sign_op.py | 22 ++++++ 4 files changed, 148 insertions(+) create mode 100644 paddle/operators/sign_op.cc create mode 100644 paddle/operators/sign_op.cu create mode 100644 paddle/operators/sign_op.h create mode 100644 python/paddle/v2/framework/tests/test_sign_op.py diff --git a/paddle/operators/sign_op.cc b/paddle/operators/sign_op.cc new file mode 100644 index 0000000000..1b2f879d6d --- /dev/null +++ b/paddle/operators/sign_op.cc @@ -0,0 +1,70 @@ +/* Copyright (c) 2016 PaddlePaddle Authors. All Rights Reserve. + + 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. */ + +#include "paddle/operators/sign_op.h" + +namespace paddle { +namespace operators { + +class SignOp : public framework::OperatorWithKernel { + public: + using framework::OperatorWithKernel::OperatorWithKernel; + + void InferShape(framework::InferShapeContext *ctx) const override { + PADDLE_ENFORCE(ctx->HasInput("X"), + "Input(X) of SignOp should not be null."); + PADDLE_ENFORCE(ctx->HasOutput("Out"), + "Output(Out) of SignOp should not be null."); + ctx->SetOutputDim("Out", ctx->GetInputDim("X")); + ctx->ShareLoD("X", /*->*/ "Out"); + } +}; + +template +class SignOpMaker : public framework::OpProtoAndCheckerMaker { + public: + SignOpMaker(framework::OpProto *proto, framework::OpAttrChecker *op_checker) + : OpProtoAndCheckerMaker(proto, op_checker) { + AddInput("X", "(Tensor) Input tensor of sign operator."); + AddOutput("Out", "(Tensor) Output tensor of sign operator."); + AddComment(R"DOC(Sign operator + +The equation is: Out = X.sign() +)DOC"); + } +}; + +class SignGradMaker : public framework::SingleGradOpDescMaker { + public: + using framework::SingleGradOpDescMaker::SingleGradOpDescMaker; + + std::unique_ptr Apply() const override { + auto *grad_op = new framework::OpDescBind(); + grad_op->SetType("scale"); + grad_op->SetInput("X", OutputGrad("Out")); + grad_op->SetOutput("Out", InputGrad("X")); + grad_op->SetAttr("scale", 0.0f); + return std::unique_ptr(grad_op); + } +}; + +} // namespace operators +} // namespace paddle + +namespace ops = paddle::operators; + +REGISTER_OPERATOR(sign, ops::SignOp, ops::SignOpMaker, + ops::SignGradMaker); +REGISTER_OP_CPU_KERNEL(sign, + ops::SignKernel); diff --git a/paddle/operators/sign_op.cu b/paddle/operators/sign_op.cu new file mode 100644 index 0000000000..4d0638cb97 --- /dev/null +++ b/paddle/operators/sign_op.cu @@ -0,0 +1,18 @@ +/* Copyright (c) 2016 PaddlePaddle Authors. All Rights Reserve. + + 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. */ + +#include "paddle/operators/sign_op.h" + +REGISTER_OP_GPU_KERNEL( + sign, paddle::operators::SignKernel); diff --git a/paddle/operators/sign_op.h b/paddle/operators/sign_op.h new file mode 100644 index 0000000000..ab5cd4bac0 --- /dev/null +++ b/paddle/operators/sign_op.h @@ -0,0 +1,38 @@ +/* Copyright (c) 2016 PaddlePaddle Authors. All Rights Reserve. + + 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. */ + +#pragma once + +#include "paddle/framework/eigen.h" +#include "paddle/framework/op_registry.h" + +namespace paddle { +namespace operators { +template +class SignKernel : public framework::OpKernel { + public: + virtual void Compute(const framework::ExecutionContext& context) const { + auto* out = context.Output("Out"); + auto* in = context.Input("X"); + out->mutable_data(in->place()); + + auto eigen_out = framework::EigenVector::Flatten(*out); + auto eigen_in = framework::EigenVector::Flatten(*in); + auto& place = context.GetEigenDevice(); + eigen_out.device(place) = eigen_in.sign(); + } +}; + +} // namespace operators +} // namespace paddle diff --git a/python/paddle/v2/framework/tests/test_sign_op.py b/python/paddle/v2/framework/tests/test_sign_op.py new file mode 100644 index 0000000000..c6b59bcfd8 --- /dev/null +++ b/python/paddle/v2/framework/tests/test_sign_op.py @@ -0,0 +1,22 @@ +import unittest +import numpy as np +from op_test import OpTest + + +class TestSignOp(OpTest): + def setUp(self): + self.op_type = "sign" + self.inputs = { + 'X': np.random.uniform(-10, 10, (10, 10)).astype("float32") + } + self.outputs = {'Out': np.sign(self.inputs['X'])} + + def test_check_output(self): + self.check_output() + + def test_check_grad(self): + self.check_grad(['X'], 'Out') + + +if __name__ == "__main__": + unittest.main() From b067639621f526e75ca4c20788b2475e2e61cafd Mon Sep 17 00:00:00 2001 From: Yu Yang Date: Fri, 27 Oct 2017 14:07:06 -0700 Subject: [PATCH 2/3] Fix clang compile (#5171) --- paddle/operators/sequence_pool_op.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/paddle/operators/sequence_pool_op.h b/paddle/operators/sequence_pool_op.h index ead30e8e90..07bf61df45 100644 --- a/paddle/operators/sequence_pool_op.h +++ b/paddle/operators/sequence_pool_op.h @@ -144,11 +144,11 @@ class SequencePoolGradKernel : public framework::OpKernel { Eigen::Map> in_t_map(in_t.data(), h, w); int row_id; - Eigen::array extents = {1, 1}; + Eigen::array extents{{1, 1}}; for (int col_id = 0; col_id < w; col_id++) { in_t_map.col(col_id).maxCoeff(&row_id); - Eigen::array in_offsets = {row_id, col_id}; - Eigen::array out_offsets = {0, col_id}; + Eigen::array in_offsets{{row_id, col_id}}; + Eigen::array out_offsets{{0, col_id}}; in_g_e.slice(in_offsets, extents).device(place) = out_g_e.slice(out_offsets, extents); } From 2a5edec03eaa513857d665020e3783fb4f8453b9 Mon Sep 17 00:00:00 2001 From: Yu Yang Date: Fri, 27 Oct 2017 15:09:24 -0700 Subject: [PATCH 3/3] Add debug logs in scope, meta_cache and memory (#5170) * Add debug logs in scope, meta_cache and memory * Add missing deps --- paddle/framework/CMakeLists.txt | 2 +- paddle/framework/scope.cc | 7 ++++++- paddle/memory/CMakeLists.txt | 2 +- paddle/memory/detail/meta_cache.cc | 5 ++++- paddle/memory/memory.cc | 6 +++++- 5 files changed, 17 insertions(+), 5 deletions(-) diff --git a/paddle/framework/CMakeLists.txt b/paddle/framework/CMakeLists.txt index 0d1617424e..f69a3cfbf8 100644 --- a/paddle/framework/CMakeLists.txt +++ b/paddle/framework/CMakeLists.txt @@ -15,7 +15,7 @@ nv_test(lod_tensor_gpu_test SRCS lod_tensor_test.cu DEPS lod_tensor) cc_test(variable_test SRCS variable_test.cc) -cc_library(scope SRCS scope.cc) +cc_library(scope SRCS scope.cc DEPS glog) cc_test(scope_test SRCS scope_test.cc DEPS scope) diff --git a/paddle/framework/scope.cc b/paddle/framework/scope.cc index 19e25fba05..14cc530448 100644 --- a/paddle/framework/scope.cc +++ b/paddle/framework/scope.cc @@ -16,6 +16,7 @@ limitations under the License. */ #include // for unique_ptr #include // for call_once +#include "glog/logging.h" #include "paddle/string/printf.h" namespace paddle { @@ -23,7 +24,10 @@ namespace framework { Scope::~Scope() { DropKids(); - for (auto& kv : vars_) delete kv.second; + for (auto& kv : vars_) { + VLOG(3) << "Destroy variable " << kv.first; + delete kv.second; + } } Scope& Scope::NewScope() const { @@ -38,6 +42,7 @@ Variable* Scope::Var(const std::string& name) { } Variable* v = new Variable(); vars_[name] = v; + VLOG(3) << "Create variable " << name << " on scope"; v->name_ = &(vars_.find(name)->first); return v; } diff --git a/paddle/memory/CMakeLists.txt b/paddle/memory/CMakeLists.txt index 9cc4233e43..aed5275dbf 100644 --- a/paddle/memory/CMakeLists.txt +++ b/paddle/memory/CMakeLists.txt @@ -1,6 +1,6 @@ add_subdirectory(detail) -cc_library(memory SRCS memory.cc) +cc_library(memory SRCS memory.cc DEPS place) cc_library(memcpy SRCS memcpy.cc) cc_library(paddle_memory diff --git a/paddle/memory/detail/meta_cache.cc b/paddle/memory/detail/meta_cache.cc index 30ff80e7ba..f0721c3b94 100644 --- a/paddle/memory/detail/meta_cache.cc +++ b/paddle/memory/detail/meta_cache.cc @@ -13,6 +13,7 @@ limitations under the License. */ #include "paddle/memory/detail/meta_cache.h" +#include "glog/logging.h" #include "paddle/memory/detail/memory_block.h" #include "paddle/platform/assert.h" @@ -28,7 +29,9 @@ Metadata MetadataCache::load(const MemoryBlock* block) { PADDLE_ASSERT(existing_metadata->second.check_guards()); return existing_metadata->second; } else { - PADDLE_ASSERT(reinterpret_cast(block)->check_guards()); + auto* meta = reinterpret_cast(block); + VLOG(3) << "Load MetaData type=" << meta->type; + PADDLE_ASSERT(meta->check_guards()); return *reinterpret_cast(block); } } diff --git a/paddle/memory/memory.cc b/paddle/memory/memory.cc index 8e561528f0..0b648642f9 100644 --- a/paddle/memory/memory.cc +++ b/paddle/memory/memory.cc @@ -39,11 +39,15 @@ BuddyAllocator* GetCPUBuddyAllocator() { template <> void* Alloc(platform::CPUPlace place, size_t size) { - return GetCPUBuddyAllocator()->Alloc(size); + VLOG(3) << "Allocate " << size << " bytes on " << platform::Place(place); + void* p = GetCPUBuddyAllocator()->Alloc(size); + VLOG(3) << " pointer=" << p; + return p; } template <> void Free(platform::CPUPlace place, void* p) { + VLOG(3) << "Free pointer=" << p << " on " << platform::Place(place); GetCPUBuddyAllocator()->Free(p); }