o
    ZhG-                     @   s   d dl mZ d dlZg dZG dd dejjZG dd dejjZG dd	 d	ejjZG d
d dejj	Z	G dd dejj
Z
G dd dejjZG dd dejjjjZG dd dejjZdS )    )warnN)ReLU6	HardswishELU	LeakyReLUSigmoidSoftmaxMultiheadAttentionPReLUc                       s@   e Zd ZdZd fdd	Zdd Zdd Zedd	d
Z  Z	S )r   a  Applies the element-wise function:

    :math:`\text{ReLU6}(x) = \min(\max(x_0, x), q(6))`, where :math:`x_0` is the
    zero_point, and :math:`q(6)` is the quantized representation of number 6.

    Args:
        inplace: can optionally do the operation in-place. Default: ``False``

    Shape:
        - Input: :math:`(N, *)` where `*` means, any number of additional
          dimensions
        - Output: :math:`(N, *)`, same shape as the input

    .. image:: ../scripts/activation_images/ReLU6.png

    Examples::

        >>> m = nn.quantized.ReLU6()
        >>> input = torch.randn(2)
        >>> # xdoctest: +SKIP
        >>> input = torch.quantize_per_tensor(input, 1.0, 0, dtype=torch.qint32)
        >>> output = m(input)
    Fc                    s   t  | || _d S N)super__init__inplace)selfr   	__class__ W/var/www/auris/lib/python3.10/site-packages/torch/ao/nn/quantized/modules/activation.pyr   ,   s   
zReLU6.__init__c                 C   s   t jj|| jS r   )torchops	quantizedZrelu6r   r   inputr   r   r   forward0   s   zReLU6.forwardc                 C      dS )NZQuantizedReLU6r   r   r   r   r   	_get_name3      zReLU6._get_namec                 C   s
   t | jS r   )r   r   )moduse_precomputed_fake_quantr   r   r   
from_float6   s   
zReLU6.from_floatF)
__name__
__module____qualname____doc__r   r   r   staticmethodr    __classcell__r   r   r   r   r      s    r   c                       L   e Zd ZdZd fdd	Zdd Zdd Zedd
dZe	dd Z
  ZS )r   zThis is the quantized version of :class:`~torch.nn.Hardswish`.

    Args:
        scale: quantization scale of the output tensor
        zero_point: quantization zero point of the output tensor
    Nc                    sL   ||d}t    | dtj|fi | | dtj|fi | d S N)devicedtypescale
zero_pointr   r   Zregister_bufferr   Ztensor)r   r,   r-   r*   r+   factory_kwargsr   r   r   r   C   s   

zHardswish.__init__c                 C      t jj|| j| jS r   )r   r   r   Z	hardswishr,   r-   r   r   r   r   r   I   s   zHardswish.forwardc                 C   r   )NZQuantizedHardswishr   r   r   r   r   r   L   r   zHardswish._get_nameFc                 C   s    | j  \}}tt|t|S r   )activation_post_processcalculate_qparamsr   floatintr   r   r,   r-   r   r   r   r    O   s   zHardswish.from_floatc                 C   s   | t |t|S r   )r3   r4   clsr   r,   r-   r   r   r   from_referenceT   s   zHardswish.from_reference)NNr!   r"   r#   r$   r%   r   r   r   r&   r    classmethodr8   r'   r   r   r   r   r   ;   s    r   c                       r(   )r   zThis is the quantized equivalent of :class:`~torch.nn.ELU`.

    Args:
        scale: quantization scale of the output tensor
        zero_point: quantization zero point of the output tensor
        alpha: the alpha constant
          ?c                    s   t  | || _|| _d S r   )r   r   r,   r-   )r   r,   r-   alphar   r   r   r   b   s   
zELU.__init__c                 C   s   t jjjj|| j| j| jS r   )	r   aonnr   
functionalZelur,   r-   r<   r   r   r   r   r   g   s   zELU.forwardc                 C   r   )NZQuantizedELUr   r   r   r   r   r   l   r   zELU._get_nameFc                 C   s$   | j  \}}tt|t|| jS r   )r1   r2   r   r3   r4   r<   r5   r   r   r   r    o      zELU.from_floatc                 C   s   | t |t||jS r   )r3   r4   r<   r6   r   r   r   r8   t      zELU.from_reference)r;   r!   r9   r   r   r   r   r   Y   s    r   c                       sj   e Zd ZdZ				ddedededed	df
 fd
dZdd Zdd Z	e
dddZe
dd Z  ZS )r   a  This is the quantized equivalent of :class:`~torch.nn.LeakyReLU`.

    Args:
        scale: quantization scale of the output tensor
        zero_point: quantization zero point of the output tensor
        negative_slope: Controls the angle of the negative slope. Default: 1e-2
    {Gz?FNr,   r-   negative_sloper   returnc                    sP   ||d}t  || | dtj|fi | | dtj|fi | d S r)   r.   )r   r,   r-   rC   r   r*   r+   r/   r   r   r   r      s   
	zLeakyReLU.__init__c                 C   s   t jj|| j| j| j| jS r   )r   r   r   Z
leaky_relurC   r   r,   r-   r   r   r   r   r      s   zLeakyReLU.forwardc                 C   r   )NZQuantizedLeakyReLUr   r   r   r   r   r      r   zLeakyReLU._get_namec                 C   s(   |j  \}}| t|t||j|jS r   )r1   r2   r3   r4   rC   r   )r7   r   r   r,   r-   r   r   r   r       s   zLeakyReLU.from_floatc                 C   s   | t |t||j|jS r   )r3   r4   rC   r   r6   r   r   r   r8      s   zLeakyReLU.from_reference)rB   FNNr!   )r"   r#   r$   r%   r3   r4   boolr   r   r   r:   r    r8   r'   r   r   r   r   r   y   s.    r   c                       s@   e Zd ZdZdedef fddZdd Zedd	d
Z	  Z
S )r   zThis is the quantized equivalent of :class:`~torch.nn.Sigmoid`.

    Args:
        scale: quantization scale of the output tensor
        zero_point: quantization zero point of the output tensor
    output_scaleoutput_zero_pointc                    s   t    || _|| _d S r   )r   r   rF   rG   )r   rF   rG   r   r   r   r      s   

zSigmoid.__init__c                 C   r0   r   )r   r   r   ZsigmoidrF   rG   r   r   r   r   r      s   
zSigmoid.forwardFc                 C   s    |j  \}}| t|t|S r   )r1   r2   r3   r4   )r7   r   r   rF   rG   r   r   r   r       s
   zSigmoid.from_floatr!   )r"   r#   r$   r%   r3   r4   r   r   r:   r    r'   r   r   r   r   r      s    r   c                       sL   e Zd ZdZd fdd	Zdd Zd	d
 ZedddZe	dd Z
  ZS )r   a,  This is the quantized version of :class:`~torch.nn.Softmax`.

    Args:
        dim: A dimension along which Softmax will be computed (so every slice along dim will sum to 1).
        scale: quantization scale of the output tensor
        zero_point: quantization zero point of the output tensor
    Nr;   r   c                    s    t    || _|| _|| _d S r   )r   r   dimr,   r-   )r   rH   r,   r-   r   r   r   r      s   

zSoftmax.__init__c                 C   s@   | j }|d u rd}tjjd|  |}tjj||| j| j	S )N   softmax)
rH   r   r>   r?   Z_get_softmax_dimr   r   rJ   r,   r-   )r   r   rH   
stacklevelr   r   r   r      s   
zSoftmax.forwardc                 C   r   )NZQuantizedSoftmaxr   r   r   r   r   r      r   zSoftmax._get_nameFc                 C   s$   | j  \}}t| jt|t|S r   )r1   r2   r   rH   r3   r4   r5   r   r   r   r       r@   zSoftmax.from_floatc                 C   s   | |j t|t|S r   )rH   r3   r4   r6   r   r   r   r8      rA   zSoftmax.from_reference)Nr;   r   r!   r9   r   r   r   r   r      s    r   c                   @   s8   e Zd ZejjjjZdd Z	e
dd Ze
dd ZdS )r	   c                 C   r   )NZQuantizedMultiheadAttentionr   r   r   r   r   r      r   zMultiheadAttention._get_namec                 C   s   t d)NzpIt looks like you are trying to convert a non-observed MHA module. Please, see the examples on quantizable MHAs.)NotImplementedError)r7   otherr   r   r   r       s   zMultiheadAttention.from_floatc                 C   s   t jjj|d ddd d}| |_|jd ur2|jd}t j|dd\}}t 	|||t j
}t|d| |jd urU|jd}t j|dd\}}t 	|||t j
}t|d| |`|`|S )NFT)mappingr   Zremove_qconfigZconvert_custom_config_dictbias_k)Zreduce_rangebias_v)r   r=   Zquantizationconvertr   rO   _parameterspopZ_choose_qparams_per_tensorquantize_per_tensorquint8setattrrP   Zin_proj_weightZin_proj_bias)r7   rM   Z	convertedrO   scZzprP   r   r   r   from_observed   s.   


z MultiheadAttention.from_observedN)r"   r#   r$   r   r=   r>   quantizabler	   Z_FLOAT_MODULEr   r:   r    rX   r   r   r   r   r	      s    
	r	   c                	       s   e Zd ZdZ	ddedededdf fdd	Zd
ejddfddZ	dejdejfddZ
dd ZedddZedd Z  ZS )r
   a%  This is the quantized equivalent of :class:`~torch.nn.PReLU`.

    Args:
        scale: quantization scale of the output tensor
        zero_point: quantization zero point of the output tensor
        num_parameters: number of parameters: 1, or the number of channels at input. Default: 1
       rF   rG   num_parametersrD   Nc                    sN   t    || _|| _|| _tj|tjd}tj|ddtj	d}| 
| d S )N)r+   r;   r   )r,   r-   r+   )r   r   r[   r,   r-   r   Zrandnr3   rT   rU   
set_weight)r   rF   rG   r[   wZqwr   r   r   r      s   
zPReLU.__init__r]   c                 C   s
   || _ d S r   )weight)r   r]   r   r   r   r\   +  s   
zPReLU.set_weightr   c                 C   s   t jj|| j| j| jS r   )r   r   r   Zprelur^   r,   r-   r   r   r   r   r   .  s   zPReLU.forwardc                 C   r   )NZQuantizedPReLUr   r   r   r   r   r   3  r   zPReLU._get_nameFc                 C   s   |j  \}}| t|t||j}|j }|j }|| |jtj	kr.t
d|j  | \}}	t|t|t|	tj	}
||
 |S Nz9PReLU's weight observer should have dtype quint8 but got )r1   r2   r3   r4   r[   r^   qconfigr+   r   rU   r   rT   r\   )r7   r   r   r,   r-   qprelufloat_wtobserverwt_scalewt_zpqweightr   r   r   r    6  s   



zPReLU.from_floatc           
      C   s   | t |t||j}|j  }|j }|| |jtjkr'td|j  |	 \}}t
|t |t|tj}	||	 |S r_   )r3   r4   r[   r^   r`   r+   r   rU   r   r2   rT   r\   )
r7   r   r,   r-   ra   rb   rc   rd   re   rf   r   r   r   r8   H  s   



zPReLU.from_reference)rZ   r!   )r"   r#   r$   r%   r3   r4   r   r   ZTensorr\   r   r   r:   r    r8   r'   r   r   r   r   r
     s&    	r
   )warningsr   r   __all__r>   ZReLUr   r   r   r   r   r   r=   rY   r	   Moduler
   r   r   r   r   <module>   s   ( )'3