Addgrad
=================


逐元素计算加法梯度

.. math::

    dx1 = \frac{\partial L}{\partial X1} = \frac{\partial L}{\partial Y} * 1 = \frac{\partial L}{\partial Y}\\
    dx2 = \frac{\partial L}{\partial X2} = \frac{\partial L}{\partial Y} * 1 = \frac{\partial L}{\partial Y}

输入：
    - **dy** - dy数据地址。
    - **dx1_dim** - x1的维度信息。
    - **dx2_dim** - x2的维度信息。
    - **dy_dims** - dy的维度信息。
    - **num_dims** - 维度数
    - **core_mask** - 核掩码。

输出：
    - **dx1** - dx1的数据地址。
    - **dx2** - dx2的数据地址。

支持平台：
    ``FT78NE``
    ``MT7004``

.. note::
    - FT78NE 支持fp32
    - MT7004 支持fp16, fp32


**共享存储版本:**

.. c:function:: void fp_addgrad_s(float* dy, int* x1_dims, int* x2_dims, int* dy_dims, int num_dims, float* dx1, float* dx2, int core_mask)
.. c:function:: void hp_addgrad_s(half* dy, int* x1_dims, int* x2_dims, int* dy_dims, int num_dims, half* dx1, half* dx2, int core_mask)

**C调用示例：**

.. code-block:: c
    :linenos:
    :emphasize-lines: 14

    //FT78NE示例
    #include <stdio.h>
    #include <addgrad.h>
    
    int main(int argc, char* argv[]) {
        float *dy = (float *)0xA0000000;   //input在DDR空间
        float *dx1 = (float *)0xB0000000;   //dx1
        float *dx2 = (float *)0xC0000000;   //dxx
        int dx1_dims[] = {13, 183, 47};  // 2x2
        int dx2_dims[] = {1, 183, 47};  // 2x2
        int dy_dims[] = {13, 183, 47};  // 2x2
        int num_dims = 3;
        int core_mask = 0xff;
        fp_addgrad_s(dy, dx1_dims, dx2_dims, dy_dims, num_dims, dx1, dx2, core_mask);
        return 0;
    }


**私有存储版本:**

.. c:function:: void fp_addgrad_p(float* dy, int* x1_dims, int* x2_dims, int* dy_dims, int num_dims, float* dx1, float* dx2)
.. c:function:: void hp_addgrad_p(half* dy, int* x1_dims, int* x2_dims, int* dy_dims, int num_dims, half* dx1, half* dx2)


**C调用示例：**

.. code-block:: c
    :linenos:
    :emphasize-lines: 13

    //FT78NE示例
    #include <stdio.h>
    #include <addgrad.h>
    
    int main(int argc, char* argv[]) {
        float *dy = (float *)0x10000000;   //input在L2空间
        float *dx1 = (float *)0x10001000;   //dx1
        float *dx2 = (float *)0x10002000;   //dxx
        int dx1_dims[] = {13, 183, 47};  // 2x2
        int dx2_dims[] = {1, 183, 47};  // 2x2
        int dy_dims[] = {13, 183, 47};  // 2x2
        int num_dims = 3;
        fp_addgrad_p(dy, dx1_dims, dx2_dims, dy_dims, num_dims, dx1, dx2);
        return 0;
    }