text:
"""K-FAC optimized functions for patches second moment(PSM) computation."""
import functools
from typing import List, Optional, Sequence, Tuple, TypeVar, Union

import chex
import jax
from jax import interpreters
from jax import lax
import jax.numpy as jnp

from kfac_jax._src import utils

# Types for annotation
T = TypeVar("T")
TracedType = interpreters.partial_eval.DynamicJaxprTracer
DimNumbers = Tuple[chex.Shape, chex.Shape, chex.Shape]
PaddingVariants = Union[str, int, Sequence[int], Sequence[Tuple[int, int]]]

# Special global variables
_USE_4D_CONVOLUTION: bool = True

def set_use_4d_convolution_in_psm_loop(value: bool):
  """Sets whether a 4D convolution is used for the PSM computation."""
  if not isinstance(value, bool):
    raise ValueError("The value provided must be a python bool.")
  global _USE_4D_CONVOLUTION
  _USE_4D_CONVOLUTION = value

def get_use_4d_convolution_in_psm_loop() -> bool:
  """Returns whether a 4D convolution is used for the PSM computation."""
  return _USE_4D_CONVOLUTION

def _ceil(x: int, y: int) -> int:
  """Computes `ceil(x / y)` with only integer operations."""
  return - (- x // y)

class _ConvSpec:
  """Layout specification for arrays that will be used in a convolution."""

  def __init__(self, order: Sequence[int]):
    """Initializes the array specification with the provided order."""
    self.order = tuple(order)

  def __len__(self):
    return len(self.order)

  @property
  def n_axis(self) -> int:
    """Returns the index of the batch axis."""
    return self.order[0]

  @property
  def c_axis(self) -> int:
    """Returns the index of the channel axis."""
    return self.order[1]

  @property
  def spatial_axes(self) -> Tuple[int]:
    """Returns the indices of the spatial axes."""
    return self.order[2:]

  def get_n(self, shape: chex.Shape) -> int:
    """Returns the batch size of the given shape, under this spec layout."""
    return shape[self.n_axis]

  def get_c(self, shape: chex.Shape) -> int:
    """Returns the channel size of the given shape, under this spec layout."""
    return shape[self.c_axis]

  def get_spatial(self, shape: chex.Shape) -> Tuple[int, ...]:
    """Returns the spatial sizes of the given shape, under this spec layout."""
    return tuple(shape[i] for i in self.spatial_axes)

  def expand_spatial_axes(self) -> "_ConvSpec":
    """Expands the layout spatial axes by preserving `n` and `c` order."""
    n_axis = self.n_axis + sum(self.n_axis > axis for axis in self.spatial_axes)
    c_axis = self.c_axis + sum(self.c_axis > axis for axis in self.spatial_axes)
    spatial_axes = []
    for axis in self.spatial_axes:
      spatial_axes.append(axis + sum(axis > a for a in self.spatial_axes))
      spatial_axes.append(spatial_axes[-1] + 1)
    return _ConvSpec([n_axis, c_axis, *spatial_axes])

  def swap_n_and_c(self) -> "_ConvSpec":
    """Swaps the batch and channel indices of the layout."""
    return _ConvSpec([self.c_axis, self.n_axis, *self.spatial_axes])

  def create_shape(self, n: T, c: T, *spatial_dims: T) -> Tuple[T, ...]:
    """Creates a shape according to this layout specification."""
    if len(spatial_dims) != len(self.order) - 2:
      raise ValueError("Incorrect number of spatial dimensions.")
    result: List[T] = [None] * len(self)
    result[self.n_axis] = n
    result[self.c_axis] = c
    for ax, dim in zip(self.spatial_axes, spatial_dims):
      result[ax] = dim
    assert all(r is not None for r in result)
    return tuple(result)

  def change_nhwc_to_ihwo(self) -> "_ConvSpec":
    """Changes the layout from `NHWC` to `IHWO` where `I=C`, `O=N`."""
    # Change the spec: NHWC -> IHWO where I=C, O=N
    order = [i - 2 if i > self.spatial_axes[1] else i for i in self.order[:4]]
    return _ConvSpec(order).swap_n_and_c()

def _slice_array(
    array: chex.Array,
    indices: Sequence[Union[int, TracedType]],
    sizes: Sequence[int],
) -> chex.Array:
  """Takes a slice from the array provided."""
  if any(isinstance(x, TracedType) for x in indices):
    # Any of the indices are dynamic values.
    return lax.dynamic_slice_p.bind(array, *indices, slice_sizes=sizes)
  else:
    # All indices are static values.
    index = tuple(slice(i, i + size) for i, size in zip(indices, sizes))
    return array[index]

def _output_spatial_shape(
    inputs_spatial_shape: chex.Shape,
    kernel_spatial_shape: chex.Shape,
    spatial_strides: chex.Shape,
    padding: Union[str, Sequence[Tuple[int, int]]],
) -> chex.Shape:
  """Returns the output spatial shape of the corresponding convolution."""
  if isinstance(padding, str):
    if padding.lower() == "valid":
      return tuple(_ceil(d - k + 1, s) for d, k, s in zip(inputs_spatial_shape,
                                                          kernel_spatial_shape,
                                                          spatial_strides))
    elif padding.lower() == "same":
      return tuple(_ceil(d, s) for d, s in zip(inputs_spatial_shape,
                                               spatial_strides))
    else:
      raise ValueError(f"Unrecognized padding string {padding}!")
  else:
    shapes_strides_padding = zip(
        inputs_spatial_shape, kernel_spatial_shape, spatial_strides, padding)
    return tuple(_ceil(d + p[0] + p[1] - k + 1, s)
                 for d, k, s, p in shapes_strides_padding)

def _normalize_padding(
    inputs_spatial_shape: chex.Shape,
    kernel_spatial_shape: chex.Shape,
    spatial_strides: chex.Shape,
    padding: PaddingVariants,
) -> Tuple[Tuple[int, int], ...]:
  """Returns the padding as a tuple of pairs of integers."""
  n = len(kernel_spatial_shape)
  if isinstance(padding, str):
    if padding.lower() == "valid":
      return ((0, 0),) * n
    elif padding.lower() == "same":
      # https://github.com/tensorflow/tensorflow/blob/r1.8/tensorflow/core/kernels/conv_ops.cc#L571
      output_shape = _output_spatial_shape(inputs_spatial_shape,
                                           kernel_spatial_shape,
                                           spatial_strides, "same")
      padding = []
      for out_d, d, k, s in zip(output_shape, inputs_spatial_shape,
                                kernel_spatial_shape, spatial_strides):
        pad = max(0, (out_d - 1) * s + k - d)
        padding.append((pad // 2, pad - pad // 2))
      return tuple(padding)
    else:
      raise ValueError(f"Unrecognized padding: {padding}!")
  elif isinstance(padding, int):
    return ((padding, padding),) * n
  else:
    final_padding = []
    for pad in padding:
      if isinstance(pad, int):
        final_padding.append((pad, pad))
      else:
        final_padding.append(pad)
    return tuple(final_padding)

def _normalize_strides(
    kernel_spatial_shape: chex.Shape,
    strides: Union[int, chex.Shape],
) -> Tuple[int, ...]:
  """Returns the strides as a tuple of integers."""
  n = len(kernel_spatial_shape)
  if strides is None:
    return (1,) * n
  elif isinstance(strides, int):
    return (strides,) * n
  else:
    assert len(strides) == n
    return tuple(strides)

def _data_format_to_dim_numbers(
    data_format: Optional[str],
    kernel_format: str = "HWIO",
) -> lax.ConvDimensionNumbers:
  """Converts the data format in dim numbers."""
  if data_format is None:
    data_format = "NHWC"
  if not isinstance(data_format, str):
    raise ValueError("data_format must be either a python string or `None`.")
  data_format = lax.conv_general_permutations([data_format,
                                               kernel_format,
                                               data_format])
  return lax.ConvDimensionNumbers(*data_format)

def _parse_simple_args(
    inputs_shape: chex.Shape,
    kernel_spatial_shape: Union[int, chex.Shape],
    strides: Union[int, chex.Shape] = 1,
    padding: PaddingVariants = "VALID",
    data_format: Optional[str] = "NHWC",
    dim_numbers: Optional[Union[DimNumbers, lax.ConvDimensionNumbers]] = None,
) -> Tuple[
    Tuple[int, ...],
    Tuple[int, ...],
    Tuple[Tuple[int, int], ...],
    lax.ConvDimensionNumbers
]:
  """Parses all convolutional arguments to a single unified format.

  Args:
    inputs_shape: A sequence of ints specifying the input's shape.
    kernel_spatial_shape: A sequence of ints specifying the kernel's shape.
    strides: A sequence of ints specifying strides in each spatial dimension,
      or a single int specifying the strides in every spatial dimension.
    padding: The padding can take one of the following formats:
      * str - Either 'VALID' or 'SAME'
      * int - Specifies the padding on both of sides of every spatial dimension.
      * sequence of ints - Specifies the padding on both sides of each spatial
        dimension.
      * sequence of pairs of ints - Specifies the padding on each side of each
        spatial dimension.
    data_format: The data format layout of the inputs.
    dim_numbers: If `data_format` is `None` this can specify the layout instead.

  Returns:
    A tuple of the (kernel shape, strides, padding, dim_numbers)
  """
  spatial_dims = len(inputs_shape) - 2

  if data_format is not None and dim_numbers is not None:
    raise ValueError("At least one of `data_format` and `dim_numbers` "
                     "must be None.")

  if dim_numbers is not None:

    if not isinstance(dim_numbers, lax.ConvDimensionNumbers):

      if not isinstance(dim_numbers, (list, tuple)):
        raise ValueError("The provided dim_numbers argument must be either a "
                         "list, tuple or lax.ConvDimensionNumbers.")

      if len(dim_numbers) != 3:
        raise ValueError("When the provided dim_numbers argument is a list or "
                         "tuple it must have length 3, but has length "
                         f"{len(dim_numbers)}.")

      lax_dim_numbers = lax.ConvDimensionNumbers(*dim_numbers)

    else:
      lax_dim_numbers: lax.ConvDimensionNumbers = dim_numbers

  else:
    lax_dim_numbers = _data_format_to_dim_numbers(data_format)

  if isinstance(kernel_spatial_shape, int):
    kernel_spatial_shape = (kernel_spatial_shape,) * spatial_dims

  if len(kernel_spatial_shape) != spatial_dims:
    raise ValueError("The provided argument `kernel_spatial_shape` must have "
                     f"length equal to the spatial dimensions {spatial_dims} of"
                     f" the inputs, but got {len(kernel_spatial_shape)}.")

  inputs_spatial_shape = _ConvSpec(lax_dim_numbers.lhs_spec).get_spatial(
      inputs_shape)

  kernel_spatial_shape = _ConvSpec(lax_dim_numbers.rhs_spec).get_spatial(
      kernel_spatial_shape)
  strides = _normalize_strides(kernel_spatial_shape, strides)

  padding = _normalize_padding(
      inputs_spatial_shape, kernel_spatial_shape, strides, padding)

  return kernel_spatial_shape, strides, padding, lax_dim_numbers

def _num_conv_locations_full_spec(
    input_spatial_shape: chex.Shape,
    kernel_spatial_shape: chex.Shape,
    spatial_strides: chex.Shape,
    spatial_padding: Sequence[Tuple[int, int]],
) -> int:
  """The number of convolution locations from the unified spec for arguments."""
  if len(kernel_spatial_shape) != len(input_spatial_shape):
    raise ValueError("The `kernel_spatial_shape` and `input_spatial_shape` "
                     "must have the same number of elements, got "
                     f"{len(kernel_spatial_shape)} and "
                     f"{len(input_spatial_shape)}.")
  if len(spatial_strides) != len(input_spatial_shape):
    raise ValueError("The `spatial_strides` and `input_spatial_shape` "
                     "must have the same number of elements, got "
                     f"{len(spatial_strides)} and "
                     f"{len(input_spatial_shape)}.")
  if len(spatial_padding) != len(input_spatial_shape):
    raise ValueError("The `spatial_padding` and `input_spatial_shape` "
                     "must have the same number of elements, got "
                     f"{len(spatial_padding)} and "
                     f"{len(input_spatial_shape)}.")

  num_locations = 1
  for in_dim, k_dim, stride, padding in zip(
      input_spatial_shape, kernel_spatial_shape,
      spatial_strides, spatial_padding):
    num_locations *= _ceil(in_dim + padding[0] + padding[1] - k_dim + 1, stride)
  return num_locations

def num_conv_locations(
    inputs_spatial_shape: chex.Shape,
    kernel_spatial_shape: Union[int, chex.Shape],
    spatial_strides: Union[int, chex.Shape],
    spatial_padding: Union[str, int, Sequence[Tuple[int, int]]],
) -> int:
  """Returns the number of convolution locations for the provided shapes."""
  inputs_spatial_shape = tuple(inputs_spatial_shape)
  n = len(inputs_spatial_shape)
  if isinstance(kernel_spatial_shape, int):
    kernel_spatial_shape = (kernel_spatial_shape,) * n
  spatial_strides = _normalize_strides(kernel_spatial_shape, spatial_strides)
  spatial_padding = _normalize_padding(
      inputs_spatial_shape, kernel_spatial_shape,
      spatial_strides, spatial_padding)
  return _num_conv_locations_full_spec(
      inputs_spatial_shape, kernel_spatial_shape,
      spatial_strides, spatial_padding)

@utils.auto_scope_function
def _the_conv4d(
    lhs: chex.Array,
    lhs_spec: _ConvSpec,
    rhs: chex.Array,
    rhs_spec: _ConvSpec,
    pad_h: int,
    pad_w: int,
    stride_h: int,
    stride_w: int,
    per_channel: bool = False,
    precision: Optional[jax.lax.Precision] = None,
) -> chex.Array:
  """Performs a special conv4d or conv2d based on the global flag."""
  assert len(rhs_spec) == 6
  if get_use_4d_convolution_in_psm_loop():
    # Reshape lhs to 6D array - (n, extra_h, 1, extra_w, 1, c)
    lhs_shape = list(lhs.shape)
    lhs_shape.insert(lhs_spec.spatial_axes[1] + 1, 1)
    lhs_shape.insert(lhs_spec.spatial_axes[0] + 1, 1)
    lhs = jnp.reshape(lhs, lhs_shape)
    # Change the spec: NHAWBC -> CHAWBN
    lhs_spec = rhs_spec.swap_n_and_c()
    # Change the spec: NHAWBC -> IHAWBO where I=C, O=N
    rhs_spec = rhs_spec.swap_n_and_c()
    dim_specs = (lhs_spec.order, rhs_spec.order, lhs_spec.order)
    if per_channel:
      @functools.partial(jax.vmap,
                         in_axes=(lhs_spec.n_axis, rhs_spec.n_axis),
                         out_axes=-1)
      def single_conv(x, y):
        return lax.conv_general_dilated(
            lhs=jnp.expand_dims(x, lhs_spec.n_axis),
            rhs=jnp.expand_dims(y, rhs_spec.n_axis),
            window_strides=(1, 1, 1, 1),
            padding=((0, pad_h), (0, 0), (0, pad_w), (0, 0)),
            lhs_dilation=(1, 1, 1, 1),
            rhs_dilation=(stride_h, 1, stride_w, 1),
            dimension_numbers=lax.ConvDimensionNumbers(*dim_specs),
            precision=precision,
        )

      result = single_conv(lhs, rhs)
      assert result.shape[lhs_spec.n_axis] == 1
      result = jnp.squeeze(result, lhs_spec.n_axis)
      assert result.shape[2] == 1
      assert result.shape[4] == 1
      result = jnp.squeeze(result, (2, 4))
      return result[None]
    else:
      result = lax.conv_general_dilated(
          lhs=lhs,
          rhs=rhs,
          window_strides=(1, 1, 1, 1),
          padding=((0, pad_h), (0, 0), (0, pad_w), (0, 0)),
          lhs_dilation=(1, 1, 1, 1),
          rhs_dilation=(stride_h, 1, stride_w, 1),
          dimension_numbers=lax.ConvDimensionNumbers(*dim_specs),
          precision=precision,
      )
      # Order the result such that one of the channel dims is after spatial dims
      if lhs_spec != (5, 0, 1, 2, 3, 4):
        min_index = 0 if lhs_spec.n_axis < lhs_spec.c_axis else 1
        max_index = 1 - min_index
        axes = list(range(6))
        if lhs_spec.order[min_index] != 0:
          axes.insert(0, axes.pop(lhs_spec.order[min_index]))
        if lhs_spec.order[max_index] != 5:
          axes.insert(5, axes.pop(lhs_spec.order[max_index]))
        result = jnp.transpose(result, axes=axes)
      assert result.shape[2] == 1
      assert result.shape[4] == 1
      result = jnp.squeeze(result, (2, 4))
      return result[None, None]
  else:
    # Change the spec: NHWC -> CHWN
    lhs_spec = lhs_spec.swap_n_and_c()
    # Index rhs and remove the trivial dimensions
    rhs_slice: List[Union[slice, int]] = [slice(None)] * rhs.ndim
    rhs_slice[rhs_spec.spatial_axes[1]] = 0
    rhs_slice[rhs_spec.spatial_axes[3]] = 0
    rhs = rhs[tuple(rhs_slice)]
    rhs_spec = rhs_spec.change_nhwc_to_ihwo()
    dim_specs = (lhs_spec.order, rhs_spec.order, lhs_spec.order)
    if per_channel:
      vmap_single_conv = jax.vmap(lambda x, y: lax.conv_general_dilated(  # pylint: disable=g-long-lambda
          lhs=jnp.expand_dims(x, lhs_spec.n_axis),
          rhs=jnp.expand_dims(y, rhs_spec.n_axis),
          window_strides=(1, 1),
          padding=((0, pad_h), (0, pad_w)),
          lhs_dilation=(1, 1),
          rhs_dilation=(stride_h, stride_w),
          dimension_numbers=lax.ConvDimensionNumbers(*dim_specs),
          precision=precision,
      ), in_axes=(lhs_spec.n_axis, rhs_spec.n_axis), out_axes=-1)
      result = vmap_single_conv(lhs, rhs)
      assert result.shape[lhs_spec.n_axis] == 1
      result = jnp.squeeze(result, lhs_spec.n_axis)
      return result[None]
    else:
      result = lax.conv_general_dilated(
          lhs=lhs,
          rhs=rhs,
          window_strides=(1, 1),
          padding=((0, pad_h), (0, pad_w)),
          lhs_dilation=(1, 1),
          rhs_dilation=(stride_h, stride_w),
          dimension_numbers=lax.ConvDimensionNumbers(*dim_specs),
          precision=precision,
      )
      # Order the result such that one of the channel dims is after spatial dims
      if lhs_spec != (3, 0, 1, 2):
        min_index = 0 if lhs_spec.n_axis < lhs_spec.c_axis else 1
        max_index = 1 - min_index
        axes = list(range(4))
        if lhs_spec.order[min_index] != 0:
          axes.insert(0, axes.pop(lhs_spec.order[min_index]))
        if lhs_spec.order[max_index] != 5:
          axes.insert(5, axes.pop(lhs_spec.order[max_index]))
        result = jnp.transpose(result, axes=axes)
      return result[None, None]

def _validate_inputs_lengths(
    inputs: chex.Array,
    kernel_spatial_shape: chex.Shape,
    strides: chex.Shape,
    padding: Tuple[Tuple[int, int], ...],
) -> None:
  """Checks that the provided arguments are valid."""
  spatial_dims = inputs.ndim - 2
  if spatial_dims != 2:
    raise ValueError("Currently `patches_second_moment` supports only 2D "
                     "convolution, hence the input is expected to have rank 4,"
                     f" but has rank {inputs.ndim}.")
  if len(kernel_spatial_shape) != spatial_dims:
    raise ValueError("The argument `kernel_spatial_shape` must have length "
                     f"equal to the number of spatial dimensions of the input -"
                     f" {spatial_dims}, but instead has length "
                     f"{len(kernel_spatial_shape)}.")
  if len(padding) != spatial_dims:
    raise ValueError("The argument `padding` must have length equal to the "
                     "number of spatial dimensions of the input - "
                     f"{spatial_dims}, but instead has length "
                     f"{len(kernel_spatial_shape)}.")
  if len(strides) != 2:
    raise ValueError("The argument `strides` must have length equal to the "
                     "number of spatial dimensions of the input - "
                     f"{spatial_dims}, but instead has length "
                     f"{len(kernel_spatial_shape)}.")

@functools.partial(jax.jit, static_argnums=list(range(1, 12)),
                   static_argnames=(
                       "kernel_spatial_shape", "strides", "padding",
                       "data_format", "dim_numbers", "inputs_dilation",
                       "kernel_dilation", "feature_group_count",
                       "batch_group_count", "unroll_loop", "precision"))
@utils.auto_scope_function
def patches_moments_explicit(
    inputs: chex.Array,
    kernel_spatial_shape: Union[int, chex.Shape],
    strides: Union[int, chex.Shape] = 1,
    padding: PaddingVariants = "VALID",
    data_format: Optional[str] = "NHWC",
    dim_numbers: Optional[Union[DimNumbers, lax.ConvDimensionNumbers]] = None,
    inputs_dilation: Optional[Sequence[int]] = None,
    kernel_dilation: Optional[Sequence[int]] = None,
    feature_group_count: int = 1,
    batch_group_count: int = 1,
    unroll_loop: bool = False,
    precision: Optional[jax.lax.Precision] = None,
    weighting_array: Optional[chex.Array] = None,
) -> Tuple[chex.Array, chex.Array]:
  """The exact same functionality as :func:`~patches_moments`, but explicitly extracts the patches via :func:`jax.lax.conv_general_dilated_patches`, potentially having a higher memory usage."""
  kernel_spatial_shape, strides, padding, dim_numbers = _parse_simple_args(
      inputs.shape, kernel_spatial_shape, padding=padding, strides=strides,
      data_format=data_format, dim_numbers=dim_numbers)
  _validate_inputs_lengths(inputs, kernel_spatial_shape, strides, padding)

  in_spec = _ConvSpec(dim_numbers.lhs_spec)
  out_spec = _ConvSpec(dim_numbers.out_spec)
  n = in_spec.get_n(inputs.shape)
  c = in_spec.get_c(inputs.shape)
  inputs_spatial_shape = in_spec.get_spatial(inputs.shape)
  spec = _ConvSpec(dim_numbers.out_spec).swap_n_and_c().order
  matmul_dim_numbers = lax.ConvDimensionNumbers(spec, spec, spec)

  if feature_group_count not in (1, in_spec.get_c(inputs.shape)):
    raise ValueError("`patches_moments_explicit` does not support "
                     "`feature_group_count` different from 1 or the number of "
                     "channels of the inputs.")
  if batch_group_count != 1:
    raise ValueError("`patches_moments_explicit` does not support "
                     "`batch_group_count` different from 1.")

  per_channel = feature_group_count != 1
  vector_target_shape = kernel_spatial_shape + (c,)
  leading_shape = kernel_spatial_shape if per_channel else vector_target_shape
  matrix_target_shape = leading_shape + vector_target_shape
  vector_axis = tuple(a for a in range(4) if a != out_spec.c_axis)

  # Broadcast the weighting function
  if weighting_array is not None:
    if weighting_array.ndim == inputs.ndim:
      pass
    elif weighting_array.ndim == inputs.ndim - 1:
      axis = dim_numbers.lhs_spec[1]
      weighting_array = jnp.expand_dims(weighting_array, axis=axis)
    elif weighting_array.ndim == 1:
      while weighting_array.ndim < inputs.ndim:
        weighting_array = weighting_array[:, None]
    else:
      raise ValueError(f"`weighting_array` shape {weighting_array.shape} is "
                       f"not compatible with the inputs shape {inputs.shape}"
                       ".")

  if not per_channel:
    vector_shape = (c,) + kernel_spatial_shape
    matrix_shape = vector_shape + vector_shape
    if weighting_array is None:
      weighting_array = jnp.ones([], dtype=inputs.dtype)

    # Standard explicit patches calculation
    extracted_patches = lax.conv_general_dilated_patches(
        inputs,
        filter_shape=kernel_spatial_shape,
        window_strides=strides,
        padding=padding,
        lhs_dilation=inputs_dilation,
        rhs_dilation=kernel_dilation,
        dimension_numbers=dim_numbers,
        precision=precision,
    )

    weighted_patches = extracted_patches * weighting_array
    matrix_results = lax.conv_general_dilated(
        extracted_patches,
        weighted_patches,
        window_strides=strides,
        padding="VALID",
        dimension_numbers=matmul_dim_numbers,
        precision=precision,
    )
    matrix_results = jnp.reshape(matrix_results, matrix_shape)
    vector_results = jnp.reshape(
        jnp.sum(weighted_patches, axis=vector_axis), vector_shape)

    if c > 1:
      # The output of `conv_general_dilated_patches` is ordered `chw`
      return (jnp.transpose(matrix_results, (1, 2, 0, 4, 5, 3)),
              jnp.transpose(vector_results, [1, 2, 0]))
    else:
      return (jnp.reshape(matrix_results, matrix_target_shape),
              jnp.reshape(vector_results, vector_target_shape))

  # Loop over channels
  def general_loop_body(i, image):
    index = in_spec.create_shape(0, i, 0, 0)
    sizes = in_spec.create_shape(n, 1, *inputs_spatial_shape)
    image_channel = _slice_array(image, index, sizes)

    # Index the weighting function
    if weighting_array is not None:
      if weighting_array.shape[in_spec.c_axis] == 1:
        wf_i = weighting_array
      else:
        wf_n = weighting_array[in_spec.n_axis]
        wf_spatial = [weighting_array.shape[a] for a in in_spec.spatial_axes]
        wf_sizes = in_spec.create_shape(wf_n, 1, *wf_spatial)
        wf_i = _slice_array(weighting_array, index, wf_sizes)
    else:
      wf_i = None

    matrix, vector = patches_moments_explicit(
        image_channel,
        kernel_spatial_shape=kernel_spatial_shape,
        strides=strides,
        padding=padding,
        data_format=None,
        dim_numbers=dim_numbers,
        precision=precision,
        weighting_array=wf_i,
    )
    return jnp.squeeze(matrix, axis=2), vector

  if unroll_loop:
    results = [general_loop_body(ii, inputs) for ii in range(c)]
    matrix_results, vector_results = zip(*results)
    matrix_results = jnp.concatenate(matrix_results, axis=-1)
    vector_results = jnp.concatenate(vector_results, axis=-1)
    return matrix_results, vector_results

  def loop_cond(args):
    return args[0] < c
  def loop_body(args):
    i, image, matrix_result, vector_result = args
    matrix_update, vector_update = general_loop_body(i, image)
    matrix_result = lax.dynamic_update_slice(
        matrix_result, matrix_update, (0, 0, 0, 0, i))
    vector_result = lax.dynamic_update_slice(
        vector_result, vector_update, (0, 0, i))
    return i + 1, image, matrix_result, vector_result
  init_vals = (0, inputs,
               jnp.zeros(matrix_target_shape),
               jnp.zeros(vector_target_shape))
  return lax.while_loop(loop_cond, loop_body, init_vals)[-2:]

@functools.partial(jax.jit, static_argnums=list(range(1, 12)),
                   static_argnames=(
                       "kernel_spatial_shape", "strides", "padding",
                       "data_format", "dim_numbers", "inputs_dilation",
                       "kernel_dilation", "feature_group_count",
                       "batch_group_count", "unroll_loop", "precision"))
@utils.auto_scope_function
def patches_moments(
    inputs: chex.Array,
    kernel_spatial_shape: Union[int, chex.Shape],
    strides: Union[int, chex.Shape] = 1,
    padding: PaddingVariants = "VALID",
    data_format: Optional[str] = "NHWC",
    dim_numbers: Optional[Union[DimNumbers, lax.ConvDimensionNumbers]] = None,
    inputs_dilation: Optional[Sequence[int]] = None,
    kernel_dilation: Optional[Sequence[int]] = None,
    feature_group_count: int = 1,
    batch_group_count: int = 1,
    unroll_loop: bool = False,
    precision: Optional[jax.lax.Precision] = None,
    weighting_array: Optional[chex.Array] = None,
) -> Tuple[chex.Array, chex.Array]:
  """Computes the first and second moment of the convolutional patches.

  Since the code is written to support arbitrary convolution data formats, e.g.
  both NHWC and NCHW, in comments above any of the procedures is written the
  simplified version of what the statements below do, if the data format
  was fixed to NHWC.

  Args:
    inputs: The batch of images.
    kernel_spatial_shape: The spatial dimensions of the filter (int or list of
      ints).
    strides: The spatial dimensions of the strides (int or list of ints).
    padding: The padding (str or list of pairs of ints).
    data_format: The data format of the inputs (None, NHWC, NCHW).
    dim_numbers: Instance of :class:`jax.lax.ConvDimensionNumbers` instead of
      data_format.
    inputs_dilation: An integer or sequence of integers, specifying the dilation
      for the image. Currently, `patches_moments` does not support dilation, so
      the only allowed values are `None, 1, (1,1)`.
    kernel_dilation: An integer or sequence of integers, specifying the dilation
      for the kernel. Currently, `patches_moments` does not support dilation, so
      the only allowed values are `None, 1, (1,1)`.
    feature_group_count: The feature grouping for grouped convolutions.
      Currently, `patches_moments` supports only 1 and number of channels of the
      inputs.
    batch_group_count: The batch grouping for grouped convolutions. Currently,
      `patches_moments` supports only 1.
    unroll_loop: Whether to unroll the loop in python.
    precision: In what precision to run the computation. For more details please
      read Jax documentation of :func:`jax.lax.conv_general_dilated`.
    weighting_array: A tensor specifying additional weighting of each element
      of the moment's average.

  Returns:
    The matrix of the patches' second and first moment as a pair. The tensor of
    the patches' second moment has a shape `kernel_spatial_shape + (, channels)
    + kernel_spatial_shape + (, channels)`. The tensor of the patches' first
    moment has a shape `kernel_spatial_shape + (, channels)`.
  """
  kernel_spatial_shape, strides, padding, dim_numbers = _parse_simple_args(
      inputs.shape, kernel_spatial_shape, padding=padding, strides=strides,
      data_format=data_format, dim_numbers=dim_numbers)
  _validate_inputs_lengths(inputs, kernel_spatial_shape, strides, padding)

  # Extract useful fixed integer values from the inputs
  in_spec = _ConvSpec(dim_numbers.lhs_spec)
  rhs_spec = _ConvSpec(dim_numbers.rhs_spec)
  inputs_spatial_shape = in_spec.get_spatial(inputs.shape)
  n = in_spec.get_n(inputs.shape)
  c = in_spec.get_c(inputs.shape)
  in_h, in_w = inputs_spatial_shape
  ker_h, ker_w = kernel_spatial_shape
  pad_h, pad_w = padding
  s_h, s_w = strides

  if inputs_dilation not in (None, 1, (1, 1)):
    raise ValueError("`patches_second_moment` does not support input dilation.")
  if kernel_dilation not in (None, 1, (1, 1)):
    raise ValueError("`patches_second_moment` does not support kernel "
                     "dilation.")
  if feature_group_count not in (1, in_spec.get_c(inputs.shape)):
    raise ValueError("`patches_second_moment` does not support "
                     "`feature_group_count` different from 1 or the number of "
                     "channels of the inputs.")
  if batch_group_count != 1:
    raise ValueError("PSM does not support `batch_group_count` different from "
                     "1.")
  per_channel = feature_group_count != 1

  # Sanity check
  if in_h + pad_h[0] + pad_h[1] < ker_h or in_w + pad_w[0] + pad_w[1] < ker_w:
    padded_h = in_h + pad_h[0] + pad_h[1]
    padded_w = in_w + pad_w[0] + pad_w[1]
    raise ValueError("The provided image has spatial padded shape "
                     f"({padded_h}, {padded_w}) while the kernel has a larger "
                     f"shape ({ker_h}, {ker_w}). This means a convolution is "
                     "not possible.")

  # First we calculate the maximum number of times the kernel can be applied
  # into the image, including the padding and ignoring the stride.
  ker_max_h = in_h + pad_h[0] + pad_h[1] - ker_h + 1
  ker_max_w = in_w + pad_w[0] + pad_w[1] - ker_w + 1
  # Second we calculate the size of the image that is covered when performing
  # a VALID convolution with the kernel, provided the padding.
  out_h = _ceil(ker_max_h, s_h) * s_h - s_h + ker_h
  out_w = _ceil(ker_max_w, s_w) * s_w - s_w + ker_w
  # Finally, we potentially add extra padding on the right in order to make the
  # padded image sizes divisible by their strides. This is needed so we can use
  # later reshape the image into multiples of the strides, which allows us to
  # execute a strided slice via XLA's dynamic slice.  Note that
  # in certain cases this could lead to negative padding, which is correct.
  # Example: image (9, 9), kernel (2, 2), strides (2, 2), padding (0, 0)
  # Then ker_max = 8, out_h = 8, padded_height = 8 and the padding is -1.
  padded_h = _ceil(out_h, s_h) * s_h
  padded_w = _ceil(out_w, s_w) * s_w
  # Actually pad the image (extra 0 for internal padding has to be added)
  extra_pad_h = (pad_h[0], padded_h - in_h - pad_h[0], 0)
  extra_pad_w = (pad_w[0], padded_w - in_w - pad_w[0], 0)
  spatial_padding = in_spec.create_shape(
      (0, 0, 0), (0, 0, 0), extra_pad_h, extra_pad_w)
  padded_image = lax.pad(inputs, jnp.asarray(0.0, dtype=inputs.dtype),
                         spatial_padding)

  # Reshape the input based on strides
  # rhs_shape = [n, out_h // str_h, str_h, out_w // str_w, str_w, c]
  rhs_spec = in_spec.expand_spatial_axes()
  rhs_shape = rhs_spec.create_shape(
      n, c, padded_h // s_h, s_h, padded_w // s_w, s_w)

  # sizes = (n, rhs_h, 1, rhs_w, 1, c)
  rhs_h = (padded_h - ker_h) // s_h + 1
  rhs_w = (padded_w - ker_w) // s_w + 1
  sizes = rhs_spec.create_shape(n, c, rhs_h, 1, rhs_w, 1)

  # Broadcast the weighting function
  if weighting_array is not None:
    if weighting_array.ndim == inputs.ndim:
      shape = rhs_spec.create_shape(n, c, rhs_h, 1, rhs_w, 1)
    elif weighting_array.ndim == inputs.ndim - 1:
      shape = rhs_spec.create_shape(n, 1, rhs_h, 1, rhs_w, 1)
    elif weighting_array.ndim == 1:
      shape = rhs_spec.create_shape(n, 1, 1, 1, 1, 1)
    else:
      raise ValueError(f"`weighting_array` shape {weighting_array.shape} is "
                       f"not compatible with the inputs shape {inputs.shape}"
                       ".")
    reshaped_weighting_array = jnp.reshape(weighting_array, shape)
  else:
    reshaped_weighting_array = 1

  def general_loop_body(i, image):
    reshaped_image = jnp.reshape(image, rhs_shape)

    # Slice the reshaped input
    iw = i % ker_w
    ih = i // ker_w

    # index = (0, ih // sh, ih % sh, iw // sw, iw % sw, 0)
    index = rhs_spec.create_shape(
        0, 0, ih // s_h, ih % s_h, iw // s_w, iw % s_w)
    conv_rhs = _slice_array(reshaped_image, index, sizes)
    conv_rhs = conv_rhs * reshaped_weighting_array

    # Compute the correct padding for the convolution
    dilated_bound_h = 0 if rhs_h == 0 else (rhs_h - 1) * s_h + 1
    dilated_bound_w = 0 if rhs_w == 0 else (rhs_w - 1) * s_w + 1
    conv_pad_h = ker_h - (padded_h - dilated_bound_h + 1)
    conv_pad_w = ker_w - (padded_w - dilated_bound_w + 1)

    # Compute matrix update
    matrix_update = _the_conv4d(
        lhs=image,
        lhs_spec=in_spec,
        rhs=conv_rhs,
        rhs_spec=rhs_spec,
        pad_h=conv_pad_h,
        pad_w=conv_pad_w,
        stride_h=s_h,
        stride_w=s_w,
        per_channel=per_channel,
        precision=precision,
    )

    # Compute vector update
    axis = tuple(i for i in range(len(rhs_spec)) if i != rhs_spec.c_axis)

    vector_update = jnp.sum(conv_rhs, axis=axis)
    vector_update = lax.broadcast_in_dim(vector_update, (1, 1, c), (2,))

    return ih, iw, matrix_update, vector_update

  vector_shape = kernel_spatial_shape + (c,)
  leading_shape = kernel_spatial_shape if per_channel else vector_shape
  matrix_shape = leading_shape + vector_shape

  if unroll_loop:

    matrix_results, vector_results = zip(
        *[general_loop_body(ii, padded_image)[-2:]
          for ii in range(ker_h * ker_w)])

    matrix_results = jnp.stack(matrix_results, axis=0)
    matrix_results = jnp.reshape(matrix_results, matrix_shape)

    vector_results = jnp.stack(vector_results, axis=0)
    vector_results = jnp.reshape(vector_results, vector_shape)

    return matrix_results, vector_results

  else:

    def loop_cond(args):
      return args[0] < ker_h * ker_w

    def loop_body(loop_inputs):

      i, image, matrix_result, vector_result = loop_inputs
      ih, iw, matrix_update, vector_update = general_loop_body(i, image)

      # Update matrix value
      indices = (ih, iw, 0, 0, 0) + (() if per_channel else (0,))
      matrix_result = lax.dynamic_update_slice_p.bind(
          matrix_result, matrix_update, *indices)

      # Update vector value
      vector_result = lax.dynamic_update_slice_p.bind(
          vector_result, vector_update, ih, iw, 0)

      return i + 1, image, matrix_result, vector_result

    # Initialize loop states with zeros
    matrix_init = jnp.zeros(matrix_shape, dtype=inputs.dtype)
    vector_init = jnp.zeros(vector_shape, dtype=inputs.dtype)
    init_vals = (0, padded_image, matrix_init, vector_init)

    return lax.while_loop(loop_cond, loop_body, init_vals)[-2:]


text:
@implementation UITableViewCell (LCExtension)

- (void)delayContentTouches:(BOOL)value {
    //ios7上UITableViewCell子层容器是UITableViewCellScrollView
    for (id obj in self.subviews)
    {
        if ([NSStringFromClass([obj class]) isEqualToString:@"UITableViewCellScrollView"])
        {
            UIScrollView *scroll = (UIScrollView *) obj;

            scroll.delaysContentTouches = value;
            break;
        }
    }
}

@end

redpajama_set_name: RedPajamaGithub


text:
/******************************************************************************
 * NOTE 1:  This project provides two demo applications.  A simple blinky style
 * project, and a more comprehensive test and demo application.  The
 * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting in main.c is used to select
 * between the two.  See the notes on using mainCREATE_SIMPLE_BLINKY_DEMO_ONLY
 * in main.c.  This file implements the simply blinky style version.
 *
 * NOTE 2:  This file only contains the source code that is specific to the
 * basic demo.  Generic functions, such FreeRTOS hook functions, and functions
 * required to configure the hardware, are defined in main.c.
 ******************************************************************************
 *
 * main_blinky() creates one queue, two tasks, and one software timer.  It then
 * starts the scheduler.
 *
 * The Blinky Software Timer:
 * This demonstrates an auto-reload software timer.  The timer callback function
 * does nothing but toggle an LED.
 *
 * The Queue Send Task:
 * The queue send task is implemented by the prvQueueSendTask() function in
 * this file.  prvQueueSendTask() sits in a loop that causes it to repeatedly
 * block for 200 milliseconds, before sending the value 100 to the queue that
 * was created within main_blinky().  Once the value is sent, the task loops
 * back around to block for another 200 milliseconds.
 *
 * The Queue Receive Task:
 * The queue receive task is implemented by the prvQueueReceiveTask() function
 * in this file.  prvQueueReceiveTask() sits in a loop where it repeatedly
 * blocks on attempts to read data from the queue that was created within
 * main_blinky().  When data is received, the task checks the value of the
 * data, and if the value equals the expected 100, toggles the LED.  The 'block
 * time' parameter passed to the queue receive function specifies that the
 * task should be held in the Blocked state indefinitely to wait for data to
 * be available on the queue.  The queue receive task will only leave the
 * Blocked state when the queue send task writes to the queue.  As the queue
 * send task writes to the queue every 200 milliseconds, the queue receive
 * task leaves the Blocked state every 200 milliseconds, and therefore toggles
 * the LED every 200 milliseconds.
 */

/* Standard includes. */
#include <stdio.h>

/* Kernel includes. */
#include "FreeRTOS.h"
#include "task.h"
#include "queue.h"
#include "timers.h"

/* Standard demo includes. */
#include "partest.h"

/* Priorities at which the tasks are created. */
#define mainQUEUE_RECEIVE_TASK_PRIORITY		( tskIDLE_PRIORITY + 2 )
#define	mainQUEUE_SEND_TASK_PRIORITY		( tskIDLE_PRIORITY + 1 )

/* The rate at which data is sent to the queue.  The 200ms value is converted
to ticks using the portTICK_RATE_MS constant. */
#define mainQUEUE_SEND_FREQUENCY_MS			( 200 / portTICK_RATE_MS )

/* The number of items the queue can hold.  This is 1 as the receive task
will remove items as they are added, meaning the send task should always find
the queue empty. */
#define mainQUEUE_LENGTH					( 1 )

/* Values passed to the two tasks just to check the task parameter
functionality. */
#define mainQUEUE_SEND_PARAMETER			( 0x1111UL )
#define mainQUEUE_RECEIVE_PARAMETER			( 0x22UL )

/* The period of the blinky software timer.  The period is specified in ms and
converted to ticks using the portTICK_RATE_MS constant. */
#define mainBLINKY_TIMER_PERIOD				( 50 / portTICK_RATE_MS )

/* The LED used by the communicating tasks and the blinky timer respectively. */
#define mainTASKS_LED						( 0 )
#define mainTIMER_LED						( 1 )

/* Misc. */
#define mainDONT_BLOCK						( 0 )

/*-----------------------------------------------------------*/

/*
 * The tasks as described in the comments at the top of this file.
 */
static void prvQueueReceiveTask( void *pvParameters );
static void prvQueueSendTask( void *pvParameters );

/*
 * The callback function for the blinky software timer, as described at the top
 * of this file.
 */
static void prvBlinkyTimerCallback( xTimerHandle xTimer );

/*
 * Called by main() to create the simply blinky style application if
 * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 1.
 */
void main_blinky( void );

/*-----------------------------------------------------------*/

/* The queue used by both tasks. */
static xQueueHandle xQueue = NULL;

/*-----------------------------------------------------------*/

void main_blinky( void )
{
xTimerHandle xTimer;

	/* Create the queue. */
	xQueue = xQueueCreate( mainQUEUE_LENGTH, sizeof( unsigned long ) );

	if( xQueue != NULL )
	{
		/* Create the two tasks as described in the comments at the top of this
		file. */
		xTaskCreate( prvQueueReceiveTask,					/* The function that implements the task. */
					( signed char * ) "Rx", 				/* The text name assigned to the task - for debug only as it is not used by the kernel. */
					configMINIMAL_STACK_SIZE, 				/* The size of the stack to allocate to the task. */
					( void * ) mainQUEUE_RECEIVE_PARAMETER, /* The parameter passed to the task - just to check the functionality. */
					mainQUEUE_RECEIVE_TASK_PRIORITY, 		/* The priority assigned to the task. */
					NULL );									/* The task handle is not required, so NULL is passed. */

		xTaskCreate( prvQueueSendTask, ( signed char * ) "TX", configMINIMAL_STACK_SIZE, ( void * ) mainQUEUE_SEND_PARAMETER, mainQUEUE_SEND_TASK_PRIORITY, NULL );

		/* Create the blinky software timer as described at the top of this
		file. */
		xTimer = xTimerCreate( 	( const signed char * ) "Blinky",	/* A text name, purely to help debugging. */
								( mainBLINKY_TIMER_PERIOD ),		/* The timer period. */
								pdTRUE,								/* This is an auto-reload timer, so xAutoReload is set to pdTRUE. */
								( void * ) 0,						/* The ID is not used, so can be set to anything. */
								prvBlinkyTimerCallback				/* The callback function that inspects the status of all the other tasks. */
							);

		if( xTimer != NULL )
		{
			xTimerStart( xTimer, mainDONT_BLOCK );
		}

		/* Start the tasks and timer running. */
		vTaskStartScheduler();
	}

	/* If all is well, the scheduler will now be running, and the following
	line will never be reached.  If the following line does execute, then
	there was insufficient FreeRTOS heap memory available for the idle and/or
	timer tasks	to be created.  See the memory management section on the
	FreeRTOS web site for more details. */
	for( ;; );
}
/*-----------------------------------------------------------*/

static void prvQueueSendTask( void *pvParameters )
{
portTickType xNextWakeTime;
const unsigned long ulValueToSend = 100UL;

	/* Check the task parameter is as expected. */
	configASSERT( ( ( unsigned long ) pvParameters ) == mainQUEUE_SEND_PARAMETER );

	/* Initialise xNextWakeTime - this only needs to be done once. */
	xNextWakeTime = xTaskGetTickCount();

	for( ;; )
	{
		/* Place this task in the blocked state until it is time to run again.
		The block time is specified in ticks, the constant used converts ticks
		to ms.  While in the Blocked state this task will not consume any CPU
		time. */
		vTaskDelayUntil( &xNextWakeTime, mainQUEUE_SEND_FREQUENCY_MS );

		/* Send to the queue - causing the queue receive task to unblock and
		toggle the LED.  0 is used as the block time so the sending operation
		will not block - it shouldn't need to block as the queue should always
		be empty at this point in the code. */
		xQueueSend( xQueue, &ulValueToSend, 0U );
	}
}
/*-----------------------------------------------------------*/

static void prvQueueReceiveTask( void *pvParameters )
{
unsigned long ulReceivedValue;

	/* Check the task parameter is as expected. */
	configASSERT( ( ( unsigned long ) pvParameters ) == mainQUEUE_RECEIVE_PARAMETER );

	for( ;; )
	{
		/* Wait until something arrives in the queue - this task will block
		indefinitely provided INCLUDE_vTaskSuspend is set to 1 in
		FreeRTOSConfig.h. */
		xQueueReceive( xQueue, &ulReceivedValue, portMAX_DELAY );

		/*  To get here something must have been received from the queue, but
		is it the expected value?  If it is, toggle the LED. */
		if( ulReceivedValue == 100UL )
		{
			vParTestToggleLED( mainTASKS_LED );
			ulReceivedValue = 0U;
		}
	}
}
/*-----------------------------------------------------------*/

static void prvBlinkyTimerCallback( xTimerHandle xTimer )
{
	/* This function is called when the blinky software time expires.  All the
	function does is toggle the LED.  LED mainTIMER_LED should therefore toggle
	with the period set by mainBLINKY_TIMER_PERIOD. */
	vParTestToggleLED( mainTIMER_LED );
}


text:
/**!
 * AngularJS file upload shim for angular XHR HTML5 browsers
 * @author  Danial  <danial.farid@gmail.com>
 * @version 1.1.11
 */
if (window.XMLHttpRequest) {
        if (window.FormData) {
                // allow access to Angular XHR private field: https://github.com/angular/angular.js/issues/1934
                XMLHttpRequest = (function(origXHR) {
                        return function() {
                                var xhr = new origXHR();
                                xhr.send = (function(orig) {
                                        return function() {
                                                if (arguments[0] instanceof FormData && arguments[0].__setXHR_) {
                                                        var formData = arguments[0];
                                                        formData.__setXHR_(xhr);
                                                }
                                                orig.apply(xhr, arguments);
                                        }
                                })(xhr.send);
                                return xhr;
                        }
                })(XMLHttpRequest);
        }
}


text:
@import UIKit;

#import "MDCRaisedButton.h"

@interface BPLButton : MDCRaisedButton

@end


text:
using System;
using System.Collections.Generic;
using System.Linq;

namespace EnterSentials.Framework.EmitMapper
{
    // Borrowed or adapted from: EmitMapper source code
    internal class TypeDictionary<T> where T : class
    {
        class ListElement
        {
            public Type[] types;
            public T value;
            public ListElement(Type[] types, T value)
            {
                this.types = types;
                this.value = value;
            }

            public override int GetHashCode()
            {
                return types.Sum(t => t.GetHashCode());
            }

            public override bool Equals(object obj)
            {
                var rhs = (ListElement)obj;
                for (int i = 0; i < types.Length; ++i)
                {
                    if (types[i] != rhs.types[i])
                    {
                        return false;
                    }
                }
                return true;
            }
        }

        private List<ListElement> elements = new List<ListElement>();

        public override string ToString()
        {
            return elements.Select(e => e.types.ToCSV("|") + (e.value == null ? "|" : ("|" + e.value))).ToCSV("||");
        }

        public bool IsTypesInList(Type[] types)
        {
            return FindTypes(types) != null;
        }

        public T GetValue(Type[] types)
        {
            var elem = FindTypes(types);
            return elem == null ? null : elem.value;
        }

        public void Add(Type[] types, T value)
        {
            var newElem = new ListElement(types, value);
            if (elements.Contains(newElem))
            {
                elements.Remove(newElem);
            }

            elements.Add(new ListElement(types, value));
        }

        private ListElement FindTypes(Type[] types)
        {
            foreach (var element in elements)
            {
                bool isAssignable = true;
                for (int i = 0; i < element.types.Length; ++i)
                {
                    if (!IsGeneralType(element.types[i], types[i]))
                    {
                        isAssignable = false;
                        break;
                    }
                }
                if (isAssignable)
                {
                    return element;
                }
            }
            return null;
        }

        private static bool IsGeneralType(Type generalType, Type type)
        {
            if (generalType == type)
            {
                return true;
            }
            if (generalType.IsGenericTypeDefinition)
            {
                if (generalType.IsInterface)
                {
                    return
                        (type.IsInterface ? new[] { type } : new Type[0]).Concat(type.GetInterfaces())
                        .Any(
                            i =>
                                i.IsGenericType &&
                                i.GetGenericTypeDefinition() == generalType
                        );
                }
                else
                {
                    return type.IsGenericType && (type.GetGenericTypeDefinition() == generalType || type.GetGenericTypeDefinition().IsSubclassOf(generalType));
                }
            }

            return type.IsSubclassOf(generalType);
        }
    }
}


text:
To compile all: `sh build.sh`

To run all: `sh run.sh`


text:
package io.bigio;

import io.bigio.core.member.MeMember;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.TimeUnit;
import org.junit.AfterClass;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.fail;
import org.junit.BeforeClass;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 *
 * @author atrimble
 */
public class TestTCPEncryption {

    private static final Logger LOG = LoggerFactory.getLogger(TestTCPEncryption.class);

    private static final MyMessageListener listener = new MyMessageListener();

    private static final String MESSAGE = "This is a test";

    private static final BlockingQueue<MyMessage> queue = new ArrayBlockingQueue<>(1);

    private static boolean failed = false;

    private static BigIO speaker1;
    private static BigIO speaker2;

    @BeforeClass
    public static void init() throws InterruptedException {
        Parameters.INSTANCE.setProperty(MeMember.ENCRYPTION_PROPERTY, "true");

        speaker1 = BigIO.bootstrap();
        speaker2 = BigIO.bootstrap();

        speaker2.addListener("MyTCPTopic", listener);

        Thread.sleep(1000l);
    }

    @AfterClass
    public static void shutdown() throws InterruptedException {
        speaker1.shutdown();
        speaker2.shutdown();

        Thread.sleep(1000l);

        Parameters.INSTANCE.setProperty(MeMember.ENCRYPTION_PROPERTY, "false");
    }

    @Test
    public void testMessage() throws Exception {
        failed = false;

        speaker1.send("MyTCPTopic", new MyMessage(MESSAGE + "1"));
        MyMessage m = queue.poll(2000l, TimeUnit.MILLISECONDS);
        assertNotNull(m);
        assertEquals(m.getMessage(), MESSAGE + "1");

        if (failed) {
            fail();
        }

        speaker1.send("BadTopic", new MyMessage(MESSAGE + "2"));
        m = queue.poll(500l, TimeUnit.MILLISECONDS);
        assertNull(m);

        queue.clear();

        speaker2.send("MyTCPTopic", new MyMessage(MESSAGE + "1"));
        m = queue.poll(2000l, TimeUnit.MILLISECONDS);
        assertNotNull(m);
        assertEquals(m.getMessage(), MESSAGE + "1");

        if (failed) {
            fail();
        }

        speaker2.send("BadTopic", new MyMessage(MESSAGE + "2"));
        m = queue.poll(500l, TimeUnit.MILLISECONDS);
        assertNull(m);

        queue.clear();
    }

    private static class MyMessageListener implements MessageListener<MyMessage> {

        @Override
        public void receive(MyMessage message) {
            LOG.info("Got a message " + message.getMessage());

            boolean success = queue.offer(message);

            if (!success) {
                failed = true;
            }
        }
    }

    @Message
    public static final class MyMessage {

        private String message;

        public MyMessage() {

        }

        public MyMessage(String message) {
            this.message = message;
        }

        public void setMessage(String message) {
            this.message = message;
        }

        public String getMessage() {
            return message;
        }
    }
}


text:
package com.intellij.codeInspection.varScopeCanBeNarrowed;

import com.intellij.codeInsight.daemon.GroupNames;
import com.intellij.codeInspection.*;
import com.intellij.openapi.project.Project;
import com.intellij.psi.*;
import com.intellij.psi.controlFlow.*;
import com.intellij.psi.search.searches.SuperMethodsSearch;
import com.intellij.refactoring.changeSignature.ChangeSignatureProcessor;
import com.intellij.refactoring.changeSignature.ParameterInfoImpl;
import com.intellij.usageView.UsageInfo;
import com.intellij.util.NotNullFunction;
import com.intellij.util.VisibilityUtil;
import org.jetbrains.annotations.NonNls;
import javax.annotation.Nonnull;

import java.util.*;

/**
 * @author Danila Ponomarenko
 */
public class ParameterCanBeLocalInspection extends BaseJavaLocalInspectionTool {

  @NonNls public static final String SHORT_NAME = "ParameterCanBeLocal";

  @Override
  @Nonnull
  public String getGroupDisplayName() {
    return GroupNames.CLASS_LAYOUT_GROUP_NAME;
  }

  @Override
  @Nonnull
  public String getDisplayName() {
    return InspectionsBundle.message("inspection.parameter.can.be.local.display.name");
  }

  @Override
  @Nonnull
  public String getShortName() {
    return SHORT_NAME;
  }

  @Override
  public ProblemDescriptor[] checkMethod(@Nonnull PsiMethod method, @Nonnull InspectionManager manager, boolean isOnTheFly) {
    final Collection<PsiParameter> parameters = filterFinal(method.getParameterList().getParameters());
    final PsiCodeBlock body = method.getBody();
    if (body == null || parameters.isEmpty() || isOverrides(method)) {
      return ProblemDescriptor.EMPTY_ARRAY;
    }

    final List<ProblemDescriptor> result = new ArrayList<ProblemDescriptor>();
    for (PsiParameter parameter : getWriteBeforeRead(parameters, body)) {
      final PsiIdentifier identifier = parameter.getNameIdentifier();
      if (identifier != null && identifier.isPhysical()) {
        result.add(createProblem(manager, identifier, isOnTheFly));
      }
    }
    return result.toArray(new ProblemDescriptor[result.size()]);
  }

  @Nonnull
  private static List<PsiParameter> filterFinal(PsiParameter[] parameters) {
    final List<PsiParameter> result = new ArrayList<PsiParameter>(parameters.length);
    for (PsiParameter parameter : parameters) {
      if (!parameter.hasModifierProperty(PsiModifier.FINAL)) {
        result.add(parameter);
      }
    }
    return result;
  }

  @Nonnull
  private static ProblemDescriptor createProblem(@Nonnull InspectionManager manager,
                                                 @Nonnull PsiIdentifier identifier,
                                                 boolean isOnTheFly) {
    return manager.createProblemDescriptor(
      identifier,
      InspectionsBundle.message("inspection.parameter.can.be.local.problem.descriptor"),
      true,
      ProblemHighlightType.LIKE_UNUSED_SYMBOL,
      isOnTheFly,
      new ConvertParameterToLocalQuickFix()
    );
  }

  private static Collection<PsiParameter> getWriteBeforeRead(@Nonnull Collection<PsiParameter> parameters,
                                                             @Nonnull PsiCodeBlock body) {
    final ControlFlow controlFlow = getControlFlow(body);
    if (controlFlow == null) return Collections.emptyList();

    final Set<PsiParameter> result = filterParameters(controlFlow, parameters);
    result.retainAll(ControlFlowUtil.getWrittenVariables(controlFlow, 0, controlFlow.getSize(), false));
    for (final PsiReferenceExpression readBeforeWrite : ControlFlowUtil.getReadBeforeWrite(controlFlow)) {
      final PsiElement resolved = readBeforeWrite.resolve();
      if (resolved instanceof PsiParameter) {
        result.remove((PsiParameter)resolved);
      }
    }

    return result;
  }

  private static Set<PsiParameter> filterParameters(@Nonnull ControlFlow controlFlow, @Nonnull Collection<PsiParameter> parameters) {
    final Set<PsiVariable> usedVars = new HashSet<PsiVariable>(ControlFlowUtil.getUsedVariables(controlFlow, 0, controlFlow.getSize()));

    final Set<PsiParameter> result = new HashSet<PsiParameter>();
    for (PsiParameter parameter : parameters) {
      if (usedVars.contains(parameter)) {
        result.add(parameter);
      }
    }
    return result;
  }

  private static boolean isOverrides(PsiMethod method) {
    return SuperMethodsSearch.search(method, null, true, false).findFirst() != null;
  }

  @javax.annotation.Nullable
  private static ControlFlow getControlFlow(final PsiElement context) {
    try {
      return ControlFlowFactory.getInstance(context.getProject())
        .getControlFlow(context, LocalsOrMyInstanceFieldsControlFlowPolicy.getInstance());
    }
    catch (AnalysisCanceledException e) {
      return null;
    }
  }

  public static class ConvertParameterToLocalQuickFix extends BaseConvertToLocalQuickFix<PsiParameter> {
    @Override
    protected PsiParameter getVariable(@Nonnull ProblemDescriptor descriptor) {
      return (PsiParameter)descriptor.getPsiElement().getParent();
    }

    @Override
    protected PsiElement applyChanges(@Nonnull final Project project,
                                       @Nonnull final String localName,
                                       @javax.annotation.Nullable final PsiExpression initializer,
                                       @Nonnull final PsiParameter parameter,
                                       @Nonnull final Collection<PsiReference> references,
                                       @Nonnull final NotNullFunction<PsiDeclarationStatement, PsiElement> action) {
      final PsiElement scope = parameter.getDeclarationScope();
      if (scope instanceof PsiMethod) {
        final PsiMethod method = (PsiMethod)scope;
        final PsiParameter[] parameters = method.getParameterList().getParameters();

        final List<ParameterInfoImpl> info = new ArrayList<ParameterInfoImpl>();
        for (int i = 0; i < parameters.length; i++) {
          PsiParameter psiParameter = parameters[i];
          if (psiParameter == parameter) continue;
          info.add(new ParameterInfoImpl(i, psiParameter.getName(), psiParameter.getType()));
        }
        final ParameterInfoImpl[] newParams = info.toArray(new ParameterInfoImpl[info.size()]);
        final String visibilityModifier = VisibilityUtil.getVisibilityModifier(method.getModifierList());
        final ChangeSignatureProcessor cp = new ChangeSignatureProcessor(project, method, false, visibilityModifier,
                                                                         method.getName(), method.getReturnType(), newParams) {
          @Override
          protected void performRefactoring(UsageInfo[] usages) {
            final PsiElementFactory elementFactory = JavaPsiFacade.getElementFactory(project);
            final PsiElement newDeclaration = moveDeclaration(elementFactory, localName, parameter, initializer, action, references);
            super.performRefactoring(usages);
            positionCaretToDeclaration(project, newDeclaration.getContainingFile(), newDeclaration);
          }
        };
        cp.run();
      }
      return null;
    }

    @Nonnull
    @Override
    protected String suggestLocalName(@Nonnull Project project, @Nonnull PsiParameter parameter, @Nonnull PsiCodeBlock scope) {
      return parameter.getName();
    }
  }
}


text:
/*!
 * Псевдонимы функций
 */

/**
 * @see {Collection.clone}
 * @param {?} obj
 * @return {?}
 */
$C.clone = Collection.clone;

/**
 * @see {Collection.prototype.VERSION}
 * @const
 */
Collection.VERSION = Collection.prototype.VERSION;

/**
 * @see {Collection.prototype.VERSION}
 * @const
 */
$C.VERSION = Collection.prototype.VERSION;

/**
 * @see Collection.in
 * @param {$$CollectionLink} link
 * @param {!Object} obj
 * @return {boolean}
 */
Collection.exists = Collection.in;

/**
 * @see Collection.in
 * @param {$$CollectionLink} link
 * @param {!Object} obj
 * @return {boolean}
 */
$C.in = Collection.in;

/**
 * @see Collection.in
 * @param {$$CollectionLink} link
 * @param {!Object} obj
 * @return {boolean}
 */
$C.exists = Collection.in;

/**
 * @see Collection.prototype.in
 * @param {$$CollectionLink} link
 * @param {?string=} [opt_id='active']
 * @return {boolean}
 */
Collection.prototype.exists = Collection.prototype.in;

/**
 * @see extend
 * @param {(boolean|?$$Collection_extend)} deepOrParams
 * @param {Object} target
 * @param {...Object} args
 * @return {!Object}
 */
$C.extend = Collection.extend;

/**
 * @see splitPath
 * @param {string} str
 * @param {?boolean=} [opt_withoutCut]
 * @return {(!Array)}
 */
$C.splitPath = Collection.splitPath;

/**
 * @see splitPath
 * @param {string} str
 * @param {?boolean=} [opt_withoutCut]
 * @return {(!Array)}
 */
Collection.prototype.splitPath = Collection.splitPath;

/**
 * @see Collection.toArray
 * @param {!Object} obj
 * @return {!Array}
 */
$C.toArray = Collection.toArray;

/**
 * @see NULL
 * @type {!Object}
 */
Collection.prototype.NULL = NULL;


text:
"""
Copyright (c) 2015 Red Hat, Inc
All rights reserved.

This software may be modified and distributed under the terms
of the BSD license. See the LICENSE file for details.
"""

import re
import sys

from setuptools import setup, find_packages
from atomic_reactor.constants import DESCRIPTION, HOMEPAGE

data_files = {
    "share/atomic-reactor/images/privileged-builder": [
        "images/privileged-builder/Dockerfile",
        "images/privileged-builder/docker.sh",
    ],
    "share/atomic-reactor/images/dockerhost-builder": [
        "images/dockerhost-builder/Dockerfile",
    ],
}

def _get_requirements(path):
    try:
        with open(path) as f:
            packages = f.read().splitlines()
    except (IOError, OSError) as ex:
        raise RuntimeError("Can't open file with requirements: %r", ex)
    packages = (p.strip() for p in packages if not re.match("^\s*#", p))
    packages = list(filter(None, packages))
    return packages

def _install_requirements():
    requirements = _get_requirements('requirements.txt')
    if sys.version_info[0] < 3:
        requirements += _get_requirements('requirements-py2.txt')
    return requirements

setup(
    name='atomic-reactor',
    version='1.6.27',
    description=DESCRIPTION,
    author='Red Hat, Inc.',
    author_email='atomic-devel@projectatomic.io',
    url=HOMEPAGE,
    license="BSD",
    entry_points={
        'console_scripts': ['atomic-reactor=atomic_reactor.cli.main:run'],
    },
    packages=find_packages(exclude=["*.tests", "*.tests.*", "tests.*", "tests"]),
    install_requires=_install_requirements(),
    package_data={'atomic_reactor': ['schemas/*.json']},
    data_files=data_files.items(),
)


text:
using Bam.Core;
using QtCommon.MocExtension;
using System.Linq;
namespace Qt5Test1
{
    sealed class Qt5Application :
        C.Cxx.GUIApplication
    {
        protected override void
        Init()
        {
            base.Init();

            var mocHeaders = this.CreateHeaderCollection("$(packagedir)/source/*.h");
            var source = this.CreateCxxSourceCollection("$(packagedir)/source/*.cpp");
            foreach (var mocHeader in mocHeaders.Children)
            {
                var myObjectMocTuple = source.MocHeader(mocHeader as C.HeaderFile);

                // first item in Tuple is the generated moc source file
                myObjectMocTuple.Item1.PrivatePatch(settings =>
                    {
                        var mocSettings = settings as QtCommon.IMocSettings;
                        mocSettings.PreprocessorDefinitions.Add("GENERATING_MOC");
                    });

                // second item in Tuple is the C++ compilation of that generated source
                myObjectMocTuple.Item2.PrivatePatch(settings =>
                    {
                        var preprocessor = settings as C.ICommonPreprocessorSettings;
                        preprocessor.PreprocessorDefines.Add("COMPILING_GENERATED_MOC");
                    });
            }

            source.PrivatePatch(settings =>
                {
                    if (settings is GccCommon.ICommonCompilerSettings gccCompiler)
                    {
                        // because Qt5.6.0/5.6/gcc_64/include/QtCore/qglobal.h:1090:4: error: #error "You must build your code with position independent code if Qt was built with -reduce-relocations. " "Compile your code with -fPIC (-fPIE is not enough)."
                        gccCompiler.PositionIndependentCode = true;
                    }

                    if (settings is VisualCCommon.ICommonCompilerSettings vcCompiler)
                    {
                        if (source.Compiler.Version.AtLeast(VisualCCommon.ToolchainVersion.VC2015))
                        {
                            var cxxCompiler = settings as C.ICxxOnlyCompilerSettings;
                            cxxCompiler.ExceptionHandler = C.Cxx.EExceptionHandler.Synchronous; // C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\include\iosfwd(343): warning C4577: 'noexcept' used with no exception handling mode specified; termination on exception is not guaranteed. Specify /EHsc
                        }
                    }
                });

            this.PrivatePatch(settings =>
                {
                    if (settings is GccCommon.ICommonLinkerSettings gccLinker)
                    {
                        gccLinker.CanUseOrigin = true;
                        gccLinker.RPath.AddUnique("$ORIGIN/../lib");
                    }

                    if (settings is ClangCommon.ICommonLinkerSettings clangLinker)
                    {
                        clangLinker.RPath.AddUnique("@executable_path/../Frameworks");
                    }
                });

            if (this.BuildEnvironment.Platform.Includes(Bam.Core.EPlatform.OSX))
            {
                this.CompileAndLinkAgainst<Qt.CoreFramework>(source);
                this.CompileAndLinkAgainst<Qt.WidgetsFramework>(source);
            }
            else
            {
                this.CompileAndLinkAgainst<Qt.Core>(source);
                this.CompileAndLinkAgainst<Qt.Widgets>(source);
            }

            if (this.BuildEnvironment.Platform.Includes(Bam.Core.EPlatform.Windows))
            {
                this.CreateWinResourceCollection("$(packagedir)/resources/*.rc");
            }
        }
    }

    sealed class Qt5Test1Runtime :
        Publisher.Collation
    {
        protected override void
        Init()
        {
            base.Init();

            this.SetDefaultMacrosAndMappings(EPublishingType.WindowedApplication);
            var appAnchor = this.Include<Qt5Application>(C.Cxx.GUIApplication.ExecutableKey);

            var qtPlatformPlugin = this.Find<QtCommon.PlatformPlugin>().First();
            (qtPlatformPlugin as Publisher.CollatedObject).SetPublishingDirectory("$(0)/platforms", this.PluginDir);

            if (this.BuildEnvironment.Platform.Includes(Bam.Core.EPlatform.OSX))
            {
                var collatedQtFrameworks = this.Find<QtCommon.CommonFramework>();
                collatedQtFrameworks.ToList().ForEach(collatedFramework =>
                    // must be a public patch in order for the stripping mode to inherit the settings
                    (collatedFramework as Publisher.CollatedObject).PublicPatch((settings, appliedTo) =>
                        {
                            var rsyncSettings = settings as Publisher.IRsyncSettings;
                            rsyncSettings.Exclusions = (collatedFramework.SourceModule as QtCommon.CommonFramework).PublishingExclusions;
                        }));

                this.IncludeFiles(
                    this.CreateTokenizedString("$(packagedir)/resources/osx/qt.conf"),
                    this.Macros["macOSAppBundleResourcesDir"],
                    appAnchor);
            }
            else if (this.BuildEnvironment.Platform.Includes(Bam.Core.EPlatform.Linux))
            {
                this.IncludeFiles(
                    this.CreateTokenizedString("$(packagedir)/resources/linux/qt.conf"),
                    this.ExecutableDir,
                    appAnchor);
            }
            else if (this.BuildEnvironment.Platform.Includes(Bam.Core.EPlatform.Windows))
            {
                this.IncludeFiles(
                    this.CreateTokenizedString("$(packagedir)/resources/windows/qt.conf"),
                    this.ExecutableDir,
                    appAnchor);

                var app = appAnchor.SourceModule as Qt5Application;
                if (this.BuildEnvironment.Configuration != EConfiguration.Debug &&
                    app.Linker is VisualCCommon.LinkerBase)
                {
                    var runtimeLibrary = Bam.Core.Graph.Instance.PackageMetaData<VisualCCommon.IRuntimeLibraryPathMeta>("VisualC");
                    this.IncludeFiles(runtimeLibrary.CRuntimePaths(app.BitDepth), this.ExecutableDir, appAnchor);
                    this.IncludeFiles(runtimeLibrary.CxxRuntimePaths(app.BitDepth), this.ExecutableDir, appAnchor);
                }
            }
            else
            {
                throw new Bam.Core.Exception("Unknown platform");
            }
        }
    }

    [Bam.Core.ConfigurationFilter(Bam.Core.EConfiguration.NotDebug)]
    sealed class Qt5Test1DebugSymbols :
        Publisher.DebugSymbolCollation
    {
        protected override void
        Init()
        {
            base.Init();

            this.CreateSymbolsFrom<Qt5Test1Runtime>();
        }
    }

    [Bam.Core.ConfigurationFilter(Bam.Core.EConfiguration.NotDebug)]
    sealed class Qt5Test1Stripped :
        Publisher.StrippedBinaryCollation
    {
        protected override void
        Init()
        {
            base.Init();

            this.StripBinariesFrom<Qt5Test1Runtime, Qt5Test1DebugSymbols>();
        }
    }

    [Bam.Core.ConfigurationFilter(Bam.Core.EConfiguration.NotDebug)]
    sealed class TarBallInstaller :
        Installer.TarBall
    {
        protected override void
        Init()
        {
            base.Init();

            this.SourceFolder<Qt5Test1Stripped>(Publisher.StrippedBinaryCollation.StripBinaryDirectoryKey);
        }
    }
}


text:
package com.amazonaws.services.kms.model;

import java.io.Serializable;
import com.amazonaws.AmazonWebServiceRequest;

/**
 *
 */
public class UpdateAliasRequest extends AmazonWebServiceRequest implements
        Serializable, Cloneable {

    /**
     *

     * String that contains the name of the alias to be modified. The name must
     * start with the word "alias" followed by a forward slash (alias/). Aliases
     * that begin with "alias/aws" are reserved.
     *

     */
    private String aliasName;
    /**
     *

     * Unique identifier of the customer master key to be mapped to the alias.
     * This value can be a globally unique identifier or the fully specified ARN
     * of a key.
     *

     *
Key ARN Example -
     * arn:aws:kms:us-east-1:123456789012:key/12345678-1234
     * -1234-1234-123456789012

     *
Globally Unique Key ID Example - 12345678-1234-1234-1234-123456789012
     *

     *

     *

     *

     * You can call ListAliases to verify that the alias is mapped to the
     * correct TargetKeyId.
     *

     */
    private String targetKeyId;

    /**
     *

     * String that contains the name of the alias to be modified. The name must
     * start with the word "alias" followed by a forward slash (alias/). Aliases
     * that begin with "alias/aws" are reserved.
     *

     *
     * @param aliasName
     *        String that contains the name of the alias to be modified. The
     *        name must start with the word "alias" followed by a forward slash
     *        (alias/). Aliases that begin with "alias/aws" are reserved.
     */
    public void setAliasName(String aliasName) {
        this.aliasName = aliasName;
    }

    /**
     *

     * String that contains the name of the alias to be modified. The name must
     * start with the word "alias" followed by a forward slash (alias/). Aliases
     * that begin with "alias/aws" are reserved.
     *

     *
     * @return String that contains the name of the alias to be modified. The
     *         name must start with the word "alias" followed by a forward slash
     *         (alias/). Aliases that begin with "alias/aws" are reserved.
     */
    public String getAliasName() {
        return this.aliasName;
    }

    /**
     *

     * String that contains the name of the alias to be modified. The name must
     * start with the word "alias" followed by a forward slash (alias/). Aliases
     * that begin with "alias/aws" are reserved.
     *

     *
     * @param aliasName
     *        String that contains the name of the alias to be modified. The
     *        name must start with the word "alias" followed by a forward slash
     *        (alias/). Aliases that begin with "alias/aws" are reserved.
     * @return Returns a reference to this object so that method calls can be
     *         chained together.
     */
    public UpdateAliasRequest withAliasName(String aliasName) {
        setAliasName(aliasName);
        return this;
    }

    /**
     *

     * Unique identifier of the customer master key to be mapped to the alias.
     * This value can be a globally unique identifier or the fully specified ARN
     * of a key.
     *

     *
Key ARN Example -
     * arn:aws:kms:us-east-1:123456789012:key/12345678-1234
     * -1234-1234-123456789012

     *
Globally Unique Key ID Example - 12345678-1234-1234-1234-123456789012
     *

     *

     *

     *

     * You can call ListAliases to verify that the alias is mapped to the
     * correct TargetKeyId.
     *

     *
     * @param targetKeyId
     *        Unique identifier of the customer master key to be mapped to the
     *        alias. This value can be a globally unique identifier or the fully
     *        specified ARN of a key.
     *

     *
Key ARN Example -
     *        arn:aws:kms:us-east-1:123456789012:key/12345678
     *        -1234-1234-1234-123456789012

     *
Globally Unique Key ID Example -
     *        12345678-1234-1234-1234-123456789012

     *

     *

     *

     *        You can call ListAliases to verify that the alias is mapped
     *        to the correct TargetKeyId.
     */
    public void setTargetKeyId(String targetKeyId) {
        this.targetKeyId = targetKeyId;
    }

    /**
     *

     * Unique identifier of the customer master key to be mapped to the alias.
     * This value can be a globally unique identifier or the fully specified ARN
     * of a key.
     *

     *
Key ARN Example -
     * arn:aws:kms:us-east-1:123456789012:key/12345678-1234
     * -1234-1234-123456789012

     *
Globally Unique Key ID Example - 12345678-1234-1234-1234-123456789012
     *

     *

     *

     *

     * You can call ListAliases to verify that the alias is mapped to the
     * correct TargetKeyId.
     *

     *
     * @return Unique identifier of the customer master key to be mapped to the
     *         alias. This value can be a globally unique identifier or the
     *         fully specified ARN of a key.
     *

     *
Key ARN Example -
     *         arn:aws:kms:us-east-1:123456789012:key/12345678
     *         -1234-1234-1234-123456789012

     *
Globally Unique Key ID Example -
     *         12345678-1234-1234-1234-123456789012

     *

     *

     *

     *         You can call ListAliases to verify that the alias is
     *         mapped to the correct TargetKeyId.
     */
    public String getTargetKeyId() {
        return this.targetKeyId;
    }

    /**
     *

     * Unique identifier of the customer master key to be mapped to the alias.
     * This value can be a globally unique identifier or the fully specified ARN
     * of a key.
     *

     *
Key ARN Example -
     * arn:aws:kms:us-east-1:123456789012:key/12345678-1234
     * -1234-1234-123456789012

     *
Globally Unique Key ID Example - 12345678-1234-1234-1234-123456789012
     *

     *

     *

     *

     * You can call ListAliases to verify that the alias is mapped to the
     * correct TargetKeyId.
     *

     *
     * @param targetKeyId
     *        Unique identifier of the customer master key to be mapped to the
     *        alias. This value can be a globally unique identifier or the fully
     *        specified ARN of a key.
     *

     *
Key ARN Example -
     *        arn:aws:kms:us-east-1:123456789012:key/12345678
     *        -1234-1234-1234-123456789012

     *
Globally Unique Key ID Example -
     *        12345678-1234-1234-1234-123456789012

     *

     *

     *

     *        You can call ListAliases to verify that the alias is mapped
     *        to the correct TargetKeyId.
     * @return Returns a reference to this object so that method calls can be
     *         chained together.
     */
    public UpdateAliasRequest withTargetKeyId(String targetKeyId) {
        setTargetKeyId(targetKeyId);
        return this;
    }

    /**
     * Returns a string representation of this object; useful for testing and
     * debugging.
     *
     * @return A string representation of this object.
     *
     * @see java.lang.Object#toString()
     */
    @Override
    public String toString() {
        StringBuilder sb = new StringBuilder();
        sb.append("{");
        if (getAliasName() != null)
            sb.append("AliasName: " + getAliasName() + ",");
        if (getTargetKeyId() != null)
            sb.append("TargetKeyId: " + getTargetKeyId());
        sb.append("}");
        return sb.toString();
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj)
            return true;
        if (obj == null)
            return false;

        if (obj instanceof UpdateAliasRequest == false)
            return false;
        UpdateAliasRequest other = (UpdateAliasRequest) obj;
        if (other.getAliasName() == null ^ this.getAliasName() == null)
            return false;
        if (other.getAliasName() != null
                && other.getAliasName().equals(this.getAliasName()) == false)
            return false;
        if (other.getTargetKeyId() == null ^ this.getTargetKeyId() == null)
            return false;
        if (other.getTargetKeyId() != null
                && other.getTargetKeyId().equals(this.getTargetKeyId()) == false)
            return false;
        return true;
    }

    @Override
    public int hashCode() {
        final int prime = 31;
        int hashCode = 1;

        hashCode = prime * hashCode
                + ((getAliasName() == null) ? 0 : getAliasName().hashCode());
        hashCode = prime
                * hashCode
                + ((getTargetKeyId() == null) ? 0 : getTargetKeyId().hashCode());
        return hashCode;
    }

    @Override
    public UpdateAliasRequest clone() {
        return (UpdateAliasRequest) super.clone();
    }
}


text:
using UnityEngine;
using System.Threading;
using System.Text;
using System.Collections;
using System.IO;
using System;

  //The OscMessage class is a data structure that represents an OSC address and an arbitrary number of values to be sent to that address.
  public class OscMessage
  {

   // The OSC address of the message as a string.
   public string Address;

   // The list of values to be delivered to the Address.
   public ArrayList Values;
    public OscMessage()
    {
      Values = new ArrayList();
    }
  }

  public delegate void OscMessageHandler( OscMessage oscM );

  public class Osc : MonoBehaviour
  {
      private UDPPacketIO OscPacketIO;
      Thread ReadThread;
      private bool ReaderRunning;
      private OscMessageHandler AllMessageHandler;
      Hashtable AddressTable;

    void Start() {
        //do nothing, init must be called
    }

    public void init(UDPPacketIO oscPacketIO){
      OscPacketIO = oscPacketIO;

      // Create the hashtable for the address lookup mechanism
      AddressTable = new Hashtable();

      ReadThread = new Thread(Read);
      ReaderRunning = true;
      ReadThread.IsBackground = true;
      ReadThread.Start();
    }

    // Make sure the PacketExchange is closed.
    ~Osc()
    {
        if (ReaderRunning) Cancel();
        //Debug.LogError("~Osc");
    }

    public void Cancel()
    {
        //Debug.Log("Osc Cancel start");
        if (ReaderRunning)
        {
            ReaderRunning = false;
            ReadThread.Abort();
        }
        if (OscPacketIO != null && OscPacketIO.IsOpen())
        {
            OscPacketIO.Close();
            OscPacketIO = null;
        }
        //Debug.Log("Osc Cancel finished");
    }

    // Read Thread.  Loops waiting for packets.  When a packet is received, it is
    // dispatched to any waiting All Message Handler.  Also, the address is looked up and
    // any matching handler is called.
    private void Read()
    {
        try
        {
            while (ReaderRunning)
            {
                byte[] buffer = new byte[1000];
                int length = OscPacketIO.ReceivePacket(buffer);
                //Debug.Log("received packed of len=" + length);
                if (length > 0)
                {
                    ArrayList messages = PacketToOscMessages(buffer, length);
                    foreach (OscMessage om in messages)
                    {
                        if (AllMessageHandler != null)
                            AllMessageHandler(om);
                        OscMessageHandler h = (OscMessageHandler)Hashtable.Synchronized(AddressTable)[om.Address];
                        if (h != null)
                            h(om);
                    }
                }
                else
                    Thread.Sleep(20);
            }
        }
        catch (Exception e)
        {
            //Debug.Log("ThreadAbortException"+e);
        }
        finally
        {
            //Debug.Log("terminating thread - clearing handlers");
            //Cancel();
            //Hashtable.Synchronized(AddressTable).Clear();
        }

    }

    // Send an individual OSC message.  Internally takes the OscMessage object and
    // serializes it into a byte[] suitable for sending to the PacketIO.
    public void Send( OscMessage oscMessage )
    {
      byte[] packet = new byte[1000];
      int length = OscMessageToPacket( oscMessage, packet, 1000 );
      OscPacketIO.SendPacket( packet, length);
    }

    // Sends a list of OSC Messages.  Internally takes the OscMessage objects and
    // serializes them into a byte[] suitable for sending to the PacketExchange.

    //oms - The OSC Message to send.
    public void Send(ArrayList oms)
    {
      byte[] packet = new byte[1000];
      int length = OscMessagesToPacket(oms, packet, 1000);
      OscPacketIO.SendPacket(packet, length);
    }

    // Set the method to call back on when any message is received.
    // The method needs to have the OscMessageHandler signature - i.e. void amh( OscMessage oscM )

    // amh - The method to call back on.
    public void SetAllMessageHandler(OscMessageHandler amh)
    {
      AllMessageHandler = amh;
    }

    // Set the method to call back on when a message with the specified
    // address is received.  The method needs to have the OscMessageHandler signature - i.e.
    // void amh( OscMessage oscM )

    // key - Address string to be matched
    // ah - he method to call back on.
    public void SetAddressHandler(string key, OscMessageHandler ah)
    {
      Hashtable.Synchronized(AddressTable).Add(key, ah);
    }

    // General static helper that returns a string suitable for printing representing the supplied
    // OscMessage.

    //  message - The OscMessage to be stringified
    // returns The OscMessage as a string.
    public static string OscMessageToString(OscMessage message)
    {
      StringBuilder s = new StringBuilder();
      s.Append(message.Address);
      foreach( object o in message.Values )
      {
        s.Append(" ");
        s.Append(o.ToString());
      }
      return s.ToString();
    }

    // Creates an OscMessage from a string - extracts the address and determines each of the values.

    // message - The string to be turned into an OscMessage
    // returns - The OscMessage
    public static OscMessage StringToOscMessage(string message)
    {
      OscMessage oM = new OscMessage();
      // Console.WriteLine("Splitting " + message);
      string[] ss = message.Split(new char[] { ' ' });
      IEnumerator sE = ss.GetEnumerator();
      if (sE.MoveNext())
        oM.Address = (string)sE.Current;
      while ( sE.MoveNext() )
      {
        string s = (string)sE.Current;
        // Console.WriteLine("  <" + s + ">");
        if (s.StartsWith("\""))
        {
          StringBuilder quoted = new StringBuilder();
          bool looped = false;
          if (s.Length > 1)
            quoted.Append(s.Substring(1));
          else
            looped = true;
          while (sE.MoveNext())
          {
            string a = (string)sE.Current;
            // Console.WriteLine("    q:<" + a + ">");
            if (looped)
              quoted.Append(" ");
            if (a.EndsWith("\""))
            {
              quoted.Append(a.Substring(0, a.Length - 1));
              break;
            }
            else
            {
              if (a.Length == 0)
                quoted.Append(" ");
              else
                quoted.Append(a);
            }
            looped = true;
          }
          oM.Values.Add(quoted.ToString());
        }
        else
        {
          if (s.Length > 0)
          {
            try
            {
              int i = int.Parse(s);
              // Console.WriteLine("  i:" + i);
              oM.Values.Add(i);
            }
            catch
            {
              try
              {
                float f = float.Parse(s);
                // Console.WriteLine("  f:" + f);
                oM.Values.Add(f);
              }
              catch
              {
                // Console.WriteLine("  s:" + s);
                oM.Values.Add(s);
              }
            }

          }
        }
      }
      return oM;
    }

    // Takes a packet (byte[]) and turns it into a list of OscMessages.

    //packet - The packet to be parsed
    // length - The length of the packet.
    // returns - An ArrayList of OscMessages.
    public static ArrayList PacketToOscMessages(byte[] packet, int length)
    {
      ArrayList messages = new ArrayList();
      ExtractMessages(messages, packet, 0, length);
      return messages;
    }

    // Puts an array of OscMessages into a packet (byte[]).
    public static int OscMessagesToPacket(ArrayList messages, byte[] packet, int length)
    {
      int index = 0;
      if (messages.Count == 1)
        index = OscMessageToPacket((OscMessage)messages[0], packet, 0, length);
      else
      {
        // Write the first bundle bit
        index = InsertString("#bundle", packet, index, length);
        // Write a null timestamp (another 8bytes)
        int c = 8;
        while (( c-- )>0)
          packet[index++]++;
        // Now, put each message preceded by it's length
        foreach (OscMessage oscM in messages)
        {
          int lengthIndex = index;
          index += 4;
          int packetStart = index;
          index = OscMessageToPacket(oscM, packet, index, length);
          int packetSize = index - packetStart;
          packet[lengthIndex++] = (byte)((packetSize >> 24) & 0xFF);
          packet[lengthIndex++] = (byte)((packetSize >> 16) & 0xFF);
          packet[lengthIndex++] = (byte)((packetSize >> 8) & 0xFF);
          packet[lengthIndex++] = (byte)((packetSize) & 0xFF);
        }
      }
      return index;
    }

    // Creates a packet (an array of bytes) from a single OscMessage.

    // oscM - The OscMessage to be returned as a packet.
    //packet - The packet to be populated with the OscMessage.
    //length - The usable size of the array of bytes.
    //returns - The length of the packet
    public static int OscMessageToPacket(OscMessage oscM, byte[] packet, int length)
    {
      return OscMessageToPacket(oscM, packet, 0, length);
    }

    // Creates an array of bytes from a single OscMessage.  Used internally.
    private static int OscMessageToPacket(OscMessage oscM, byte[] packet, int start, int length)
    {
      int index = start;
      index = InsertString(oscM.Address, packet, index, length);
      //if (oscM.Values.Count > 0)
      {
        StringBuilder tag = new StringBuilder();
        tag.Append(",");
        int tagIndex = index;
        index += PadSize(2 + oscM.Values.Count);

        foreach (object o in oscM.Values)
        {
          if (o is int)
          {
            int i = (int)o;
            tag.Append("i");
            packet[index++] = (byte)((i >> 24) & 0xFF);
            packet[index++] = (byte)((i >> 16) & 0xFF);
            packet[index++] = (byte)((i >> 8) & 0xFF);
            packet[index++] = (byte)((i) & 0xFF);
          }
          else
          {
            if (o is float)
            {
              float f = (float)o;
              tag.Append("f");
              byte[] buffer = new byte[4];
              MemoryStream ms = new MemoryStream(buffer);
              BinaryWriter bw = new BinaryWriter(ms);
              bw.Write(f);
              packet[index++] = buffer[3];
              packet[index++] = buffer[2];
              packet[index++] = buffer[1];
              packet[index++] = buffer[0];
            }
            else
            {
              if (o is string)
              {
                tag.Append("s");
                index = InsertString(o.ToString(), packet, index, length);
              }
              else
              {
                tag.Append("?");
              }
            }
          }
        }
        InsertString(tag.ToString(), packet, tagIndex, length);
      }
      return index;
    }

    // Receive a raw packet of bytes and extract OscMessages from it.  Used internally.
    private static int ExtractMessages(ArrayList messages, byte[] packet, int start, int length)
    {
      int index = start;
      switch ( (char)packet[ start ] )
      {
        case '/':
          index = ExtractMessage( messages, packet, index, length );
          break;
        case '#':
          string bundleString = ExtractString(packet, start, length);
          if ( bundleString == "#bundle" )
          {
            // skip the "bundle" and the timestamp
            index+=16;
            while ( index < length )
            {
              int messageSize = ( packet[index++] << 24 ) + ( packet[index++] << 16 ) + ( packet[index++] << 8 ) + packet[index++];
              /*int newIndex = */ExtractMessages( messages, packet, index, length );
              index += messageSize;
            }
          }
          break;
      }
      return index;
    }

    // Extracts a messages from a packet.
    private static int ExtractMessage(ArrayList messages, byte[] packet, int start, int length)
    {
      OscMessage oscM = new OscMessage();
      oscM.Address = ExtractString(packet, start, length);
      int index = start + PadSize(oscM.Address.Length+1);
      string typeTag = ExtractString(packet, index, length);
      index += PadSize(typeTag.Length + 1);
      //oscM.Values.Add(typeTag);
      foreach (char c in typeTag)
      {
        switch (c)
        {
          case ',':
            break;
          case 's':
            {
              string s = ExtractString(packet, index, length);
              index += PadSize(s.Length + 1);
              oscM.Values.Add(s);
              break;
            }
          case 'i':
            {
              int i = ( packet[index++] << 24 ) + ( packet[index++] << 16 ) + ( packet[index++] << 8 ) + packet[index++];
              oscM.Values.Add(i);
              break;
            }
          case 'f':
            {
              byte[] buffer = new byte[4];
              buffer[3] = packet[index++];
              buffer[2] = packet[index++];
              buffer[1] = packet[index++];
              buffer[0] = packet[index++];
              MemoryStream ms = new MemoryStream(buffer);
              BinaryReader br = new BinaryReader(ms);
              float f = br.ReadSingle();
              oscM.Values.Add(f);
              break;
            }
        }
      }
      messages.Add( oscM );
      return index;
    }

    // Removes a string from a packet.  Used internally.
    private static string ExtractString(byte[] packet, int start, int length)
    {
      StringBuilder sb = new StringBuilder();
      int index = start;
      while (packet[index] != 0 && index < length)
        sb.Append((char)packet[index++]);
      return sb.ToString();
    }

    private static string Dump(byte[] packet, int start, int length)
    {
      StringBuilder sb = new StringBuilder();
      int index = start;
      while (index < length)
        sb.Append(packet[index++]+"|");
      return sb.ToString();
    }

    // Inserts a string, correctly padded into a packet.  Used internally.
    private static int InsertString(string s, byte[] packet, int start, int length)
    {
      int index = start;
      foreach (char c in s)
      {
        packet[index++] = (byte)c;
        if (index == length)
          return index;
      }
      packet[index++] = 0;
      int pad = (s.Length+1) % 4;
      if (pad != 0)
      {
        pad = 4 - pad;
        while (pad-- > 0)
          packet[index++] = 0;
      }
      return index;
    }

    // Takes a length and returns what it would be if padded to the nearest 4 bytes.
    private static int PadSize(int rawSize)
    {
      int pad = rawSize % 4;
      if (pad == 0)
        return rawSize;
      else
        return rawSize + (4 - pad);
    }
  }