
from typing import List, Optional, Tuple, Union

import torch
from torch import nn
from torch.nn import CrossEntropyLoss

from ... import AutoBackbone
from ...modeling_outputs import SemanticSegmenterOutput
from ...modeling_utils import PreTrainedModel
from ...utils import add_start_docstrings, add_start_docstrings_to_model_forward, replace_return_docstrings
from ...utils.backbone_utils import BackboneMixin
from .configuration_upernet import UperNetConfig


UpperCAmelCase	      = [
    '''openmmlab/upernet-convnext-tiny''',
    # See all UperNet models at https://huggingface.co/models?filter=upernet
]

# General docstring
UpperCAmelCase	      = '''UperNetConfig'''







class        A_   (			nn.Module   ):




	'''simple docstring'''


	def __init__(       self		,    snake_case		,    snake_case		,    snake_case		,    snake_case = 0		,    snake_case = False		,    snake_case = 1		,    ):
		super().__init__()
		lowercase       =    nn.Convad(
		    in_channels=snake_case		,    out_channels=snake_case		,    kernel_size=snake_case		,    padding=snake_case		,    bias=snake_case		,    dilation=snake_case		,    )
		lowercase       =    nn.BatchNormad(snake_case       )
		lowercase       =    nn.ReLU()





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		lowercase       =    self.conv(snake_case       )
		lowercase       =    self.batch_norm(snake_case       )
		lowercase       =    self.activation(snake_case       )

		return output







class        A_   (			nn.Module   ):




	'''simple docstring'''


	def __init__(       self		,    snake_case		,    snake_case		,    snake_case       ):
		super().__init__()
		lowercase       =    [
		    nn.AdaptiveAvgPoolad(snake_case       ),
		    UperNetConvModule(snake_case		,    snake_case		,    kernel_size=1       ),
		]
		for i, layer in enumerate(self.layers       ):
			self.add_module(str(snake_case       )		,    snake_case       )





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		lowercase       =    input
		for layer in self.layers:
			lowercase       =    layer(snake_case       )
		return hidden_state







class        A_   (			nn.Module   ):




	'''simple docstring'''


	def __init__(       self		,    snake_case		,    snake_case		,    snake_case		,    snake_case       ):
		super().__init__()
		lowercase       =    pool_scales
		lowercase       =    align_corners
		lowercase       =    in_channels
		lowercase       =    channels
		lowercase       =    []
		for i, pool_scale in enumerate(snake_case       ):
			lowercase       =    UperNetPyramidPoolingBlock(pool_scale=snake_case		,    in_channels=snake_case		,    channels=snake_case       )
			self.blocks.append(snake_case       )
			self.add_module(str(snake_case       )		,    snake_case       )





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		lowercase       =    []
		for ppm in self.blocks:
			lowercase       =    ppm(snake_case       )
			lowercase       =    nn.functional.interpolate(
			    snake_case		,    size=x.size()[2:]		,    mode='bilinear'		,    align_corners=self.align_corners       )
			ppm_outs.append(snake_case       )
		return ppm_outs







class        A_   (			nn.Module   ):




	'''simple docstring'''


	def __init__(       self		,    snake_case		,    snake_case       ):
		super().__init__()

		lowercase       =    config
		lowercase       =    config.pool_scales  # e.g. (1, 2, 3, 6)
		lowercase       =    in_channels
		lowercase       =    config.hidden_size
		lowercase       =    False
		lowercase       =    nn.Convad(self.channels		,    config.num_labels		,    kernel_size=1       )

		# PSP Module
		lowercase       =    UperNetPyramidPoolingModule(
		    self.pool_scales		,    self.in_channels[-1]		,    self.channels		,    align_corners=self.align_corners		,    )
		lowercase       =    UperNetConvModule(
		    self.in_channels[-1] + len(self.pool_scales       ) * self.channels		,    self.channels		,    kernel_size=3		,    padding=1		,    )
		# FPN Module
		lowercase       =    nn.ModuleList()
		lowercase       =    nn.ModuleList()
		for in_channels in self.in_channels[:-1]:  # skip the top layer
			lowercase       =    UperNetConvModule(snake_case		,    self.channels		,    kernel_size=1       )
			lowercase       =    UperNetConvModule(self.channels		,    self.channels		,    kernel_size=3		,    padding=1       )
			self.lateral_convs.append(snake_case       )
			self.fpn_convs.append(snake_case       )

		lowercase       =    UperNetConvModule(
		    len(self.in_channels       ) * self.channels		,    self.channels		,    kernel_size=3		,    padding=1		,    )





	def 	SCREAMING_SNAKE_CASE__						(       self       ):
		self.apply(self._init_weights       )





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		if isinstance(snake_case		,    nn.Convad       ):
			module.weight.data.normal_(mean=0.0		,    std=self.config.initializer_range       )
			if module.bias is not None:
				module.bias.data.zero_()





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		lowercase       =    inputs[-1]
		lowercase       =    [x]
		psp_outs.extend(self.psp_modules(snake_case       )       )
		lowercase       =    torch.cat(snake_case		,    dim=1       )
		lowercase       =    self.bottleneck(snake_case       )

		return output





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		# build laterals
		lowercase       =    [lateral_conv(encoder_hidden_states[i]       ) for i, lateral_conv in enumerate(self.lateral_convs       )]

		laterals.append(self.psp_forward(snake_case       )       )

		# build top-down path
		lowercase       =    len(snake_case       )
		for i in range(used_backbone_levels - 1		,    0		,    -1       ):
			lowercase       =    laterals[i - 1].shape[2:]
			lowercase       =    laterals[i - 1] + nn.functional.interpolate(
			    laterals[i]		,    size=snake_case		,    mode='bilinear'		,    align_corners=self.align_corners       )

		# build outputs
		lowercase       =    [self.fpn_convs[i](laterals[i]       ) for i in range(used_backbone_levels - 1       )]
		# append psp feature
		fpn_outs.append(laterals[-1]       )

		for i in range(used_backbone_levels - 1		,    0		,    -1       ):
			lowercase       =    nn.functional.interpolate(
			    fpn_outs[i]		,    size=fpn_outs[0].shape[2:]		,    mode='bilinear'		,    align_corners=self.align_corners       )
		lowercase       =    torch.cat(snake_case		,    dim=1       )
		lowercase       =    self.fpn_bottleneck(snake_case       )
		lowercase       =    self.classifier(snake_case       )

		return output







class        A_   (			nn.Module   ):




	'''simple docstring'''


	def __init__(       self		,    snake_case		,    snake_case = 2		,    snake_case = 3		,    snake_case = 1       ):
		super().__init__()

		lowercase       =    config
		lowercase       =    config.auxiliary_in_channels
		lowercase       =    config.auxiliary_channels
		lowercase       =    config.auxiliary_num_convs
		lowercase       =    config.auxiliary_concat_input
		lowercase       =    in_index

		lowercase       =    (kernel_size // 2) * dilation
		lowercase       =    []
		convs.append(
		    UperNetConvModule(
		        self.in_channels		,    self.channels		,    kernel_size=snake_case		,    padding=snake_case		,    dilation=snake_case       )       )
		for i in range(self.num_convs - 1       ):
			convs.append(
			    UperNetConvModule(
			        self.channels		,    self.channels		,    kernel_size=snake_case		,    padding=snake_case		,    dilation=snake_case       )       )
		if self.num_convs == 0:
			lowercase       =    nn.Identity()
		else:
			lowercase       =    nn.Sequential(*snake_case       )
		if self.concat_input:
			lowercase       =    UperNetConvModule(
			    self.in_channels + self.channels		,    self.channels		,    kernel_size=snake_case		,    padding=kernel_size // 2       )

		lowercase       =    nn.Convad(self.channels		,    config.num_labels		,    kernel_size=1       )





	def 	SCREAMING_SNAKE_CASE__						(       self       ):
		self.apply(self._init_weights       )





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		if isinstance(snake_case		,    nn.Convad       ):
			module.weight.data.normal_(mean=0.0		,    std=self.config.initializer_range       )
			if module.bias is not None:
				module.bias.data.zero_()





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		# just take the relevant feature maps
		lowercase       =    encoder_hidden_states[self.in_index]
		lowercase       =    self.convs(snake_case       )
		if self.concat_input:
			lowercase       =    self.conv_cat(torch.cat([hidden_states, output]		,    dim=1       )       )
		lowercase       =    self.classifier(snake_case       )
		return output







class        A_   (			__lowerCamelCase   ):




	'''simple docstring'''


	_UpperCamelCase     :     List[Any]							 =       UperNetConfig
	_UpperCamelCase     :     List[str]							 =       """pixel_values"""
	_UpperCamelCase     :     Any							 =       True





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case       ):
		if isinstance(snake_case		,    snake_case       ):
			module.backbone.init_weights()
			module.decode_head.init_weights()
			module.auxiliary_head.init_weights()





	def 	SCREAMING_SNAKE_CASE__						(       self       ):
		self.backbone.init_weights()
		self.decode_head.init_weights()
		self.auxiliary_head.init_weights()





	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case		,    snake_case=False       ):
		if isinstance(snake_case		,    snake_case       ):
			lowercase       =    value




UpperCAmelCase	      = R'''
    Parameters:
    This model is a PyTorch [torch.nn.Module](https://pytorch.org/docs/stable/nn.html#torch.nn.Module) sub-class. Use
    it as a regular PyTorch Module and refer to the PyTorch documentation for all matter related to general usage and
    behavior.
        config ([`UperNetConfig`]): Model configuration class with all the parameters of the model.
            Initializing with a config file does not load the weights associated with the model, only the
            configuration. Check out the [`~PreTrainedModel.from_pretrained`] method to load the model weights.
'''

UpperCAmelCase	      = R'''
    Args:
        pixel_values (`torch.FloatTensor` of shape `(batch_size, num_channels, height, width)`):
            Pixel values. Padding will be ignored by default should you provide it. Pixel values can be obtained using
            [`AutoImageProcessor`]. See [`SegformerImageProcessor.__call__`] for details.
        output_attentions (`bool`, *optional*):
            Whether or not to return the attentions tensors of all attention layers in case the backbone has them. See
            `attentions` under returned tensors for more detail.
        output_hidden_states (`bool`, *optional*):
            Whether or not to return the hidden states of all layers of the backbone. See `hidden_states` under
            returned tensors for more detail.
        return_dict (`bool`, *optional*):
            Whether or not to return a [`~utils.ModelOutput`] instead of a plain tuple.
'''







@add_start_docstrings(
    """UperNet framework leveraging any vision backbone e.g. for ADE20k, CityScapes."""      ,	__lowerCamelCase      ,	)
class        A_   (			__lowerCamelCase   ):




	'''simple docstring'''


	def __init__(       self		,    snake_case       ):
		super().__init__(snake_case       )

		lowercase       =    AutoBackbone.from_config(config.backbone_config       )

		# Semantic segmentation head(s)
		lowercase       =    UperNetHead(snake_case		,    in_channels=self.backbone.channels       )
		lowercase       =    UperNetFCNHead(snake_case       ) if config.use_auxiliary_head else None

		# Initialize weights and apply final processing
		self.post_init()





	@add_start_docstrings_to_model_forward(UPERNET_INPUTS_DOCSTRING.format('batch_size, sequence_length'       )       )
	@replace_return_docstrings(output_type=snake_case		,    config_class=_CONFIG_FOR_DOC       )
	def 	SCREAMING_SNAKE_CASE__						(       self		,    snake_case = None		,    snake_case = None		,    snake_case = None		,    snake_case = None		,    snake_case = None		,    ):
		lowercase       =    return_dict if return_dict is not None else self.config.use_return_dict
		lowercase       =    (
		    output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
		)
		lowercase       =    output_attentions if output_attentions is not None else self.config.output_attentions

		lowercase       =    self.backbone.forward_with_filtered_kwargs(
		    snake_case		,    output_hidden_states=snake_case		,    output_attentions=snake_case       )
		lowercase       =    outputs.feature_maps

		lowercase       =    self.decode_head(snake_case       )
		lowercase       =    nn.functional.interpolate(snake_case		,    size=pixel_values.shape[2:]		,    mode='bilinear'		,    align_corners=snake_case       )

		lowercase       =    None
		if self.auxiliary_head is not None:
			lowercase       =    self.auxiliary_head(snake_case       )
			lowercase       =    nn.functional.interpolate(
			    snake_case		,    size=pixel_values.shape[2:]		,    mode='bilinear'		,    align_corners=snake_case       )

		lowercase       =    None
		if labels is not None:
			if self.config.num_labels == 1:
				raise ValueError('The number of labels should be greater than one'       )
			else:
				# compute weighted loss
				lowercase       =    CrossEntropyLoss(ignore_index=self.config.loss_ignore_index       )
				lowercase       =    loss_fct(snake_case		,    snake_case       )
				lowercase       =    loss_fct(snake_case		,    snake_case       )
				lowercase       =    main_loss + self.config.auxiliary_loss_weight * auxiliary_loss

		if not return_dict:
			if output_hidden_states:
				lowercase       =    (logits,) + outputs[1:]
			else:
				lowercase       =    (logits,) + outputs[2:]
			return ((loss,) + output) if loss is not None else output

		return SemanticSegmenterOutput(
		    loss=snake_case		,    logits=snake_case		,    hidden_states=outputs.hidden_states		,    attentions=outputs.attentions		,    )



import copy
import os
from typing import Union

from ...configuration_utils import PretrainedConfig
from ...models.auto.modeling_auto import MODEL_FOR_CAUSAL_LM_MAPPING_NAMES
from ...utils import logging
from ..auto import CONFIG_MAPPING


UpperCAmelCase	      = logging.get_logger(__name__)

UpperCAmelCase	      = {
    '''salesforce/blip2-opt-2.7b''': '''https://huggingface.co/salesforce/blip2-opt-2.7b/resolve/main/config.json''',
}







class        A_   (			__lowerCamelCase   ):




	'''simple docstring'''


	_UpperCamelCase     :     Optional[Any]							 =       """blip_2_vision_model"""





	def __init__(       self		,    snake_case=1408		,    snake_case=6144		,    snake_case=39		,    snake_case=16		,    snake_case=224		,    snake_case=14		,    snake_case="gelu"		,    snake_case=0.00_001		,    snake_case=0.0		,    snake_case=1E-10		,    snake_case=True		,    **snake_case		,    ):
		super().__init__(**snake_case       )

		lowercase       =    hidden_size
		lowercase       =    intermediate_size
		lowercase       =    num_hidden_layers
		lowercase       =    num_attention_heads
		lowercase       =    patch_size
		lowercase       =    image_size
		lowercase       =    initializer_range
		lowercase       =    attention_dropout
		lowercase       =    layer_norm_eps
		lowercase       =    hidden_act
		lowercase       =    qkv_bias





	@classmethod
	def 	SCREAMING_SNAKE_CASE__						(       cls		,    snake_case		,    **snake_case       ):
		cls._set_token_in_kwargs(snake_case       )

		lowercase  ,					lowercase       =    cls.get_config_dict(snake_case		,    **snake_case       )

		# get the vision config dict if we are loading from Blip2Config
		if config_dict.get('model_type'       ) == "blip-2":
			lowercase       =    config_dict['vision_config']

		if "model_type" in config_dict and hasattr(cls		,    'model_type'       ) and config_dict["model_type"] != cls.model_type:
			logger.warning(
			    F'''You are using a model of type {config_dict['model_type']} to instantiate a model of type '''
			    F'''{cls.model_type}. This is not supported for all configurations of models and can yield errors.'''       )

		return cls.from_dict(snake_case		,    **snake_case       )







class        A_   (			__lowerCamelCase   ):




	'''simple docstring'''


	_UpperCamelCase     :     int							 =       """blip_2_qformer"""





	def __init__(       self		,    snake_case=3_0522		,    snake_case=768		,    snake_case=12		,    snake_case=12		,    snake_case=3072		,    snake_case="gelu"		,    snake_case=0.1		,    snake_case=0.1		,    snake_case=512		,    snake_case=0.02		,    snake_case=1E-12		,    snake_case=0		,    snake_case="absolute"		,    snake_case=2		,    snake_case=1408		,    **snake_case		,    ):
		super().__init__(pad_token_id=snake_case		,    **snake_case       )

		lowercase       =    vocab_size
		lowercase       =    hidden_size
		lowercase       =    num_hidden_layers
		lowercase       =    num_attention_heads
		lowercase       =    hidden_act
		lowercase       =    intermediate_size
		lowercase       =    hidden_dropout_prob
		lowercase       =    attention_probs_dropout_prob
		lowercase       =    max_position_embeddings
		lowercase       =    initializer_range
		lowercase       =    layer_norm_eps
		lowercase       =    position_embedding_type
		lowercase       =    cross_attention_frequency
		lowercase       =    encoder_hidden_size





	@classmethod
	def 	SCREAMING_SNAKE_CASE__						(       cls		,    snake_case		,    **snake_case       ):
		cls._set_token_in_kwargs(snake_case       )

		lowercase  ,					lowercase       =    cls.get_config_dict(snake_case		,    **snake_case       )

		# get the qformer config dict if we are loading from Blip2Config
		if config_dict.get('model_type'       ) == "blip-2":
			lowercase       =    config_dict['qformer_config']

		if "model_type" in config_dict and hasattr(cls		,    'model_type'       ) and config_dict["model_type"] != cls.model_type:
			logger.warning(
			    F'''You are using a model of type {config_dict['model_type']} to instantiate a model of type '''
			    F'''{cls.model_type}. This is not supported for all configurations of models and can yield errors.'''       )

		return cls.from_dict(snake_case		,    **snake_case       )







class        A_   (			__lowerCamelCase   ):




	'''simple docstring'''


	_UpperCamelCase     :     List[Any]							 =       """blip-2"""
	_UpperCamelCase     :     str							 =       True





	def __init__(       self		,    snake_case=None		,    snake_case=None		,    snake_case=None		,    snake_case=32		,    **snake_case       ):
		super().__init__(**snake_case       )

		if vision_config is None:
			lowercase       =    {}
			logger.info('vision_config is None. initializing the Blip2VisionConfig with default values.'       )

		if qformer_config is None:
			lowercase       =    {}
			logger.info('qformer_config is None. Initializing the Blip2QFormerConfig with default values.'       )

		if text_config is None:
			lowercase       =    {}
			logger.info('text_config is None. Initializing the text config with default values (`OPTConfig`).'       )

		lowercase       =    BlipaVisionConfig(**snake_case       )
		lowercase       =    BlipaQFormerConfig(**snake_case       )
		lowercase       =    text_config['model_type'] if 'model_type' in text_config else 'opt'
		lowercase       =    CONFIG_MAPPING[text_model_type](**snake_case       )

		lowercase       =    self.text_config.tie_word_embeddings
		lowercase       =    self.text_config.is_encoder_decoder

		lowercase       =    num_query_tokens
		lowercase       =    self.vision_config.hidden_size
		lowercase       =    self.text_config.model_type in MODEL_FOR_CAUSAL_LM_MAPPING_NAMES
		lowercase       =    1.0
		lowercase       =    0.02





	@classmethod
	def 	SCREAMING_SNAKE_CASE__						(       cls		,    snake_case		,    snake_case		,    snake_case		,    **snake_case		,    ):
		return cls(
		    vision_config=vision_config.to_dict()		,    qformer_config=qformer_config.to_dict()		,    text_config=text_config.to_dict()		,    **snake_case		,    )





	def 	SCREAMING_SNAKE_CASE__						(       self       ):
		lowercase       =    copy.deepcopy(self.__dict__       )
		lowercase       =    self.vision_config.to_dict()
		lowercase       =    self.qformer_config.to_dict()
		lowercase       =    self.text_config.to_dict()
		lowercase       =    self.__class__.model_type
		return output

