-
Notifications
You must be signed in to change notification settings - Fork 5.6k
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
[DO NOT MERGE] MKLDNN layouts #10291
Conversation
TODO: fc needs reorder implemented for backpropagation
@pzelazko-intel Sorry for the late reply. For examples, fluid_op_A->mkldnn_op_B->fluid_op_C, if mkldnn_op_B doesn't use LoDTensor, how should fluid_op_C get the LoD information? |
@luotao1 Please let me know what you think. |
I an not sure what is the problem of
Data transform use plain tensor here because it only need to use the data inside the tensor, most of the inputs are actually LoDTensor. |
The problem is that DataTransform does not have information about MKLDNN format (which would be in MKLDNNLoDTensor). |
Cay we use tensor->layout to judge if a tensor is MKLDNNLoDTensor and then cast it to MKLDNNLoDTensor? |
We could, but in mentioned DataTransform and in OperatorWithKernel::RunImpl we instantiate Tensor class, not LoDTensor: https://github.com/PaddlePaddle/Paddle/blob/develop/paddle/fluid/framework/operator.cc#L575. Having to cast Tensor to MKLDNNLoDTensor, we would have to do it in many places, making our code full of if-else constructions. |
How about new files named |
Where exactly is there a cast? Anyway cast won't solve my problem, because DataTransform operates on Tensor instance: https://github.com/PaddlePaddle/Paddle/blob/develop/paddle/fluid/framework/operator.cc#L575. |
The relationship is |
Yes, but the output of DataTransform is an instance of plain Tensor: https://github.com/PaddlePaddle/Paddle/blob/develop/paddle/fluid/framework/operator.cc#L575. Moreover please take a look at: https://github.com/PaddlePaddle/Paddle/blob/develop/paddle/fluid/framework/data_transform.cc#L33 - there are again plain Tensor instances used. How would you overcome this obstacle? |
@pzelazko-intel I have another question, could we use mkldnn op do inference if MKLDNN layout not finished? |
@luotao1 yes, but it will have worse performance than version with MKLDNN layouts. |
Oh, could some PRs (run inference model with current mkldnn ops in c++ end) created first to validate the whole process? |
@luotao1 I'm not sure if I understand - you mean PR with some inference model test with MKLDNN OPs enabled? |
For MKLDNNTensor, what is needed in DataTransform? Because for the current LoDTensor, in DataTransform, we only need the field in Tensor. |
MKLDNNTensor has additionally information about MKLDNN format used and MKLDNN engine (MKLDNNTensorData class), but the latter one can be extracted from MKLDNNDeviceContext. So we have to know MKLDNN format in which the data is organized. There are many such formats and MKLDNN can choose which one to use, so I would not recommend to simply add every one of them to the the DataLayout. Instead, we could add field like mkldnn_format to the Tensor in place of extended_data if you don't like concept of extended data. |
I notice that in the current implementation extended_data is one filed of Tensor, does it means that we can get all the information we need to do data transform from Tensor and then construct a MKLDNNTensor with the data inside the transformed tensor, like: https://github.com/PaddlePaddle/Paddle/blob/develop/paddle/fluid/framework/operator.cc#L578 |
It may work with some workarounds, because in DataTransform we reorder only from MKLDNN format to common ones. So eventually you don't like extended_data concept and want me to reimplement it to MKLDNNLoDTensor, right? Could you please check if other changes are acceptable? That can save me from future reimplementations. Thank you |
Sorry, maybe my expression is not so clear, I think to add extended_data in Tensor is Ok, what I want to do is to make clear what is needed for data_transform. If all we need is inside tensor itself(such as layout, data, and extended_data) then deriving from Tensor or deriving from LoDTensor seems to have no different, but we need the LoD information to pass along with operators running. |
If I modified Tensor and Tensor is a base class for LoDTensor, then LoD information still passes along operators? Moreover I assumed that doing reorders I don't need to modify LoD information. Am I right? |
Yes, you are right.
Yes, you are right. The LoD information is independent of Tensor. |
@pzelazko-intel After data transform, we will copy the transformed data inside tensor back to it's original var type, the lod infromation will also be copied. Paddle/paddle/fluid/framework/operator.cc Lines 574 to 578 in 18f527b
Paddle/paddle/fluid/framework/data_transform.cc Lines 65 to 81 in f09aed0
If we add MKLDNNLoDTensor, we also need to do this, and the LoD information should maintain in the MKLDNNLoDTensor. That is why we think MKLDNNLoDTensor should derive from LoDTensor, because it need to store the LoD information inside it. |
@jacquesqiao I agree, but please notice that in proposed solution I don't create any class deriving from Tensor. MKLDNNTensor is only a decorator for Tensor class. If we are on the same page and you have no other questions, then please let me know if I should stay with the current design or reimplement it to MKLDNNLoDTensor deriving from LoDTensor. Thank you |
@pzelazko-intel After discussion, we think use decorator is ok, we should move on now, thanks! |
@pzelazko-intel Discussed with @jacquesqiao and @Superjomn , if you can ensure the lod information transfer among different ops, we think that you can stay with your current design. |
DO NOT MERGE IT
Please take a look at MKLDNN layout Proof of Concept and assess if we can stay with this design. This code is not finished - there are debug VLOG prints, some parts are missing and the code needs cleanup.
We need MKLDNN layouts for MKLDNN kernels to be performed efficiently - especially for convolution and fully-connected OPs.
In #8305 it was recommended to create
MKLDNNLoDTensor
class deriving fromLoDTensor
. But that approach was causing too many problems - in many placesTensor
class is used explicitly and I would need to differentiate betweenLoDTensor
andMKLDNNLoDTensor
.I came up with a different approach - I've added
Tensor::ExtendedData
interface and a pointer to this interface inTensor
class. It is a placeholder for additional data. I use it for MKLDNN layout case -mkldnn::memory::format
andmkldnn::engine
are held inMKLDNNTensorData
, which derives fromTensor::ExtendedData
. IfTensor
layout is set tokMKLDNN
, then I can treat this tensor as holding data in MKLDNN format layout. To make use of such a tensor, I've created decorator classesMKLDNNTensor
andMutableMKLDNNTensor
. The data is kept still inPlaceholder
withinTensor
.Reorders to MKLDNN format happen within convolution and fully-connected, because:
When the next OP expected kernel is not a MKLDNN one, then we transform tensor to
NCHW
layout.