r""" Processor for implementing memory efficient attention using xFormers. Args: attention_op (`Callable`, *optional*, defaults to `None`): The base [operator](https://facebookresearch.github.io/xformers/components/ops.html#xformers.ops.AttentionOpBase) to
| 1079 | |
| 1080 | |
| 1081 | class XFormersAttnProcessor: |
| 1082 | r""" |
| 1083 | Processor for implementing memory efficient attention using xFormers. |
| 1084 | |
| 1085 | Args: |
| 1086 | attention_op (`Callable`, *optional*, defaults to `None`): |
| 1087 | The base |
| 1088 | [operator](https://facebookresearch.github.io/xformers/components/ops.html#xformers.ops.AttentionOpBase) to |
| 1089 | use as the attention operator. It is recommended to set to `None`, and allow xFormers to choose the best |
| 1090 | operator. |
| 1091 | """ |
| 1092 | |
| 1093 | def __init__(self, attention_op: Optional[Callable] = None): |
| 1094 | self.attention_op = attention_op |
| 1095 | |
| 1096 | def __call__( |
| 1097 | self, |
| 1098 | attn: Attention, |
| 1099 | hidden_states: torch.FloatTensor, |
| 1100 | encoder_hidden_states: Optional[torch.FloatTensor] = None, |
| 1101 | attention_mask: Optional[torch.FloatTensor] = None, |
| 1102 | temb: Optional[torch.FloatTensor] = None, |
| 1103 | scale: float = 1.0, |
| 1104 | ) -> torch.FloatTensor: |
| 1105 | residual = hidden_states |
| 1106 | |
| 1107 | args = () if USE_PEFT_BACKEND else (scale,) |
| 1108 | |
| 1109 | if attn.spatial_norm is not None: |
| 1110 | hidden_states = attn.spatial_norm(hidden_states, temb) |
| 1111 | |
| 1112 | input_ndim = hidden_states.ndim |
| 1113 | |
| 1114 | if input_ndim == 4: |
| 1115 | batch_size, channel, height, width = hidden_states.shape |
| 1116 | hidden_states = hidden_states.view(batch_size, channel, height * width).transpose(1, 2) |
| 1117 | |
| 1118 | batch_size, key_tokens, _ = ( |
| 1119 | hidden_states.shape if encoder_hidden_states is None else encoder_hidden_states.shape |
| 1120 | ) |
| 1121 | |
| 1122 | attention_mask = attn.prepare_attention_mask(attention_mask, key_tokens, batch_size) |
| 1123 | if attention_mask is not None: |
| 1124 | # expand our mask's singleton query_tokens dimension: |
| 1125 | # [batch*heads, 1, key_tokens] -> |
| 1126 | # [batch*heads, query_tokens, key_tokens] |
| 1127 | # so that it can be added as a bias onto the attention scores that xformers computes: |
| 1128 | # [batch*heads, query_tokens, key_tokens] |
| 1129 | # we do this explicitly because xformers doesn't broadcast the singleton dimension for us. |
| 1130 | _, query_tokens, _ = hidden_states.shape |
| 1131 | attention_mask = attention_mask.expand(-1, query_tokens, -1) |
| 1132 | |
| 1133 | if attn.group_norm is not None: |
| 1134 | hidden_states = attn.group_norm(hidden_states.transpose(1, 2)).transpose(1, 2) |
| 1135 | |
| 1136 | query = attn.to_q(hidden_states, *args) |
| 1137 | |
| 1138 | if encoder_hidden_states is None: |
no outgoing calls
no test coverage detected