/*++

Copyright (c) Microsoft Corporation All Rights Reserved

Module Name:

    basetopo.cpp

Abstract:

    Implementation of topology miniport. This the base class for
    all SYSVAD samples

--*/

//4127: conditional expression is constant
#pragma warning (disable : 4127)

#include "VirtualAudioMicArray.h"
#include "basetopo.h"

//=============================================================================
#pragma code_seg("PAGE")
CMiniportTopologySYSVAD::CMiniportTopologySYSVAD
(
    _In_        PCFILTER_DESCRIPTOR    *FilterDesc,
    _In_        USHORT                  DeviceMaxChannels
)
/*++

Routine Description:

  Topology miniport constructor

Arguments:

  FilterDesc -

  DeviceMaxChannels -

Return Value:

  void

--*/
{
    PAGED_CODE();

    DPF_ENTER(("[%s]",__FUNCTION__));

    m_AdapterCommon     = NULL;

    ASSERT(FilterDesc != NULL);
    m_FilterDescriptor  = FilterDesc;
    m_PortEvents        = NULL;

    ASSERT(DeviceMaxChannels > 0);
    m_DeviceMaxChannels = DeviceMaxChannels;
} // CMiniportTopologySYSVAD

CMiniportTopologySYSVAD::~CMiniportTopologySYSVAD
(
    void
)
/*++

Routine Description:

  Topology miniport destructor

Arguments:

Return Value:

  void

--*/
{
    PAGED_CODE();

    DPF_ENTER(("[%s]",__FUNCTION__));

    SAFE_RELEASE(m_AdapterCommon);
    SAFE_RELEASE(m_PortEvents);
} // ~CMiniportTopologySYSVAD

//=============================================================================
#pragma code_seg("PAGE")
NTSTATUS
CMiniportTopologySYSVAD::DataRangeIntersection
(
    _In_  ULONG                 PinId,
    _In_  PKSDATARANGE          ClientDataRange,
    _In_  PKSDATARANGE          MyDataRange,
    _In_  ULONG                 OutputBufferLength,
    _Out_writes_bytes_to_opt_(OutputBufferLength, *ResultantFormatLength)
          PVOID                 ResultantFormat     OPTIONAL,
    _Out_ PULONG                ResultantFormatLength
)
/*++

Routine Description:

  The DataRangeIntersection function determines the highest
  quality intersection of two data ranges. Topology miniport does nothing.

Arguments:

  PinId - Pin for which data intersection is being determined.

  ClientDataRange - Pointer to KSDATARANGE structure which contains the data range
                    submitted by client in the data range intersection property
                    request

  MyDataRange - Pin's data range to be compared with client's data range

  OutputBufferLength - Size of the buffer pointed to by the resultant format
                       parameter

  ResultantFormat - Pointer to value where the resultant format should be
                    returned

  ResultantFormatLength - Actual length of the resultant format that is placed
                          at ResultantFormat. This should be less than or equal
                          to OutputBufferLength

Return Value:

  NT status code.

--*/
{
    UNREFERENCED_PARAMETER(PinId);
    UNREFERENCED_PARAMETER(ClientDataRange);
    UNREFERENCED_PARAMETER(MyDataRange);
    UNREFERENCED_PARAMETER(OutputBufferLength);
    UNREFERENCED_PARAMETER(ResultantFormat);
    UNREFERENCED_PARAMETER(ResultantFormatLength);

    PAGED_CODE();

    DPF_ENTER(("[%s]",__FUNCTION__));

    return (STATUS_NOT_IMPLEMENTED);
} // DataRangeIntersection

//=============================================================================
#pragma code_seg("PAGE")
NTSTATUS
CMiniportTopologySYSVAD::GetDescription
(
    _Out_ PPCFILTER_DESCRIPTOR *  OutFilterDescriptor
)
/*++

Routine Description:

  The GetDescription function gets a pointer to a filter description.
  It provides a location to deposit a pointer in miniport's description
  structure. This is the placeholder for the FromNode or ToNode fields in
  connections which describe connections to the filter's pins

Arguments:

  OutFilterDescriptor - Pointer to the filter description.

Return Value:

  NT status code.

--*/
{
    PAGED_CODE();

    ASSERT(OutFilterDescriptor);

    DPF_ENTER(("[%s]",__FUNCTION__));

    *OutFilterDescriptor = m_FilterDescriptor;

    return (STATUS_SUCCESS);
} // GetDescription

//=============================================================================
#pragma code_seg("PAGE")
NTSTATUS
CMiniportTopologySYSVAD::Init
(
    _In_  PUNKNOWN          UnknownAdapter_,
    _In_  PPORTTOPOLOGY     Port_
)
/*++

Routine Description:

  Initializes the topology miniport.

Arguments:

  UnknownAdapter -

  Port_ - Pointer to topology port

Return Value:

  NT status code.

--*/
{
    PAGED_CODE();

    ASSERT(UnknownAdapter_);
    ASSERT(Port_);

    DPF_ENTER(("[CMiniportTopologySYSVAD::Init]"));

    NTSTATUS    ntStatus;

    ntStatus =
        UnknownAdapter_->QueryInterface(
            IID_IAdapterCommon,
            (PVOID *) &m_AdapterCommon);

    if (NT_SUCCESS(ntStatus))
    {
        //
        // Get the port event interface.
        //
        ntStatus = Port_->QueryInterface(
            IID_IPortEvents,
            (PVOID *)&m_PortEvents);
    }

    if (!NT_SUCCESS(ntStatus))
    {
        // clean up AdapterCommon
        SAFE_RELEASE(m_AdapterCommon);
        SAFE_RELEASE(m_PortEvents);
    }

    return ntStatus;
} // Init

//=============================================================================
#pragma code_seg("PAGE")
NTSTATUS
CMiniportTopologySYSVAD::PropertyHandlerGeneric
(
    _In_  PPCPROPERTY_REQUEST     PropertyRequest
)
/*++

Routine Description:

  Handles all properties for this miniport.

Arguments:

  PropertyRequest - property request structure

Return Value:

  NT status code.

--*/
{
    PAGED_CODE();

    NTSTATUS                    ntStatus = STATUS_INVALID_DEVICE_REQUEST;

    switch (PropertyRequest->PropertyItem->Id)
    {

        case KSPROPERTY_AUDIO_CPU_RESOURCES:
            ntStatus = PropertyHandler_CpuResources(PropertyRequest);
            break;

        default:
            DPF(D_TERSE, ("[PropertyHandlerGeneric: Invalid Device Request]"));
    }

    return ntStatus;
} // PropertyHandlerGeneric

//=============================================================================
#pragma code_seg("PAGE")
VOID
CMiniportTopologySYSVAD::AddEventToEventList
(
    _In_  PKSEVENT_ENTRY    EventEntry
)
/*++

Routine Description:

  The AddEventToEventList method adds an event to the port driver's event list

Arguments:

  EventEntry -

--*/
{
    PAGED_CODE();
    DPF_ENTER(("[CMiniportTopology::AddEventToEventList]"));

    ASSERT(m_PortEvents != NULL);

    m_PortEvents->AddEventToEventList(EventEntry);
}

//=============================================================================
#pragma code_seg()
VOID
CMiniportTopologySYSVAD::GenerateEventList
(
    _In_opt_    GUID   *Set,
    _In_        ULONG   EventId,
    _In_        BOOL    PinEvent,
    _In_        ULONG   PinId,
    _In_        BOOL    NodeEvent,
    _In_        ULONG   NodeId
)
/*++

Routine Description:

  The GenerateEventList method notifies clients through the port driver's list
  of event entries that a particular event has occurred.

Arguments:

  Set -

  EventId -

  PinEvent -

  PinId -

  NodeEvent -

  NodeId -

--*/
{
    DPF_ENTER(("[CMiniportTopologySYSVAD::GenerateEventList]"));

    ASSERT(m_PortEvents != NULL);

    m_PortEvents->GenerateEventList(
        Set,
        EventId,
        PinEvent,
        PinId,
        NodeEvent,
        NodeId);
}

#pragma code_seg()


/*
   Copyright (c) 2012 LinkedIn Corp.

   Licensed under the Apache License, Version 2.0 (the "License");
   you may not use this file except in compliance with the License.
   You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.
*/

package com.linkedin.restli.internal.server.methods.arguments;

import com.linkedin.data.ByteString;
import com.linkedin.data.DataList;
import com.linkedin.data.DataMap;
import com.linkedin.data.schema.ArrayDataSchema;
import com.linkedin.data.schema.DataSchemaUtil;
import com.linkedin.data.template.AbstractArrayTemplate;
import com.linkedin.data.template.DataTemplate;
import com.linkedin.data.template.DataTemplateUtil;
import com.linkedin.data.template.DynamicRecordTemplate;
import com.linkedin.data.template.InvalidAlternativeKeyException;
import com.linkedin.data.template.RecordTemplate;
import com.linkedin.data.template.TemplateRuntimeException;
import com.linkedin.entitystream.EntityStreams;
import com.linkedin.entitystream.WriteHandle;
import com.linkedin.entitystream.Writer;
import com.linkedin.internal.common.util.CollectionUtils;
import com.linkedin.r2.message.rest.RestRequest;
import com.linkedin.restli.common.BatchRequest;
import com.linkedin.restli.common.ComplexKeySpec;
import com.linkedin.restli.common.ComplexResourceKey;
import com.linkedin.restli.common.CompoundKey;
import com.linkedin.restli.common.HttpStatus;
import com.linkedin.restli.common.ProtocolVersion;
import com.linkedin.restli.common.ResourceMethod;
import com.linkedin.restli.common.RestConstants;
import com.linkedin.restli.common.TypeSpec;
import com.linkedin.restli.common.validation.RestLiDataValidator;
import com.linkedin.restli.internal.common.PathSegment;
import com.linkedin.restli.internal.common.QueryParamsDataMap;
import com.linkedin.restli.internal.server.RoutingResult;
import com.linkedin.restli.internal.server.ServerResourceContext;
import com.linkedin.restli.internal.server.model.Parameter;
import com.linkedin.restli.internal.server.model.ResourceMethodDescriptor;
import com.linkedin.restli.internal.server.model.ResourceModel;
import com.linkedin.restli.internal.server.util.AlternativeKeyCoercerException;
import com.linkedin.restli.internal.server.util.ArgumentUtils;
import com.linkedin.restli.internal.server.util.DataMapUtils;
import com.linkedin.restli.internal.server.util.RestUtils;
import com.linkedin.restli.server.Key;
import com.linkedin.restli.server.PagingContext;
import com.linkedin.restli.server.ResourceConfigException;
import com.linkedin.restli.server.ResourceContext;
import com.linkedin.restli.server.RestLiServiceException;
import com.linkedin.restli.server.RoutingException;
import com.linkedin.restli.server.UnstructuredDataReactiveReader;
import com.linkedin.restli.server.UnstructuredDataWriter;
import com.linkedin.restli.server.annotations.HeaderParam;
import com.linkedin.restli.server.config.ResourceMethodConfig;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.lang.reflect.Array;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * @author Josh Walker
 * @version $Revision: $
 */
public class ArgumentBuilder
{
  /**
   * Build arguments for resource method invocation. Combines various types of arguments
   * into a single array.
   *
   * @param positionalArguments pass-through arguments coming from
   *          {@link RestLiArgumentBuilder}
   * @param resourceMethod the resource method
   * @param context {@link ResourceContext}
   * @param template {@link DynamicRecordTemplate}
   * @return array of method argument for method invocation.
   */
  @SuppressWarnings("deprecation")
  static Object[] buildArgs(final Object[] positionalArguments,
                                   final ResourceMethodDescriptor resourceMethod,
                                   final ServerResourceContext context,
                                   final DynamicRecordTemplate template,
                                   final ResourceMethodConfig resourceMethodConfig)
  {
    List<Parameter<?>> parameters = resourceMethod.getParameters();
    Object[] arguments = Arrays.copyOf(positionalArguments, parameters.size());

    fixUpComplexKeySingletonArraysInArguments(arguments);

    boolean attachmentsDesired = false;
    for (int i = positionalArguments.length; i < parameters.size(); ++i)
    {
      Parameter<?> param = parameters.get(i);
      try
      {
        if (param.getParamType() == Parameter.ParamType.KEY || param.getParamType() == Parameter.ParamType.ASSOC_KEY_PARAM)
        {
          Object value = context.getPathKeys().get(param.getName());
          if (value != null)
          {
            arguments[i] = value;
            continue;
          }
        }
        else if (param.getParamType() == Parameter.ParamType.CALLBACK)
        {
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.PARSEQ_CONTEXT_PARAM || param.getParamType() == Parameter.ParamType.PARSEQ_CONTEXT)
        {
          continue; // don't know what to fill in yet
        }
        else if (param.getParamType() == Parameter.ParamType.HEADER)
        {
          HeaderParam headerParam = param.getAnnotations().get(HeaderParam.class);
          String value = context.getRequestHeaders().get(headerParam.value());
          arguments[i] = value;
          continue;
        }
        //Since we have multiple different types of MaskTrees that can be passed into resource methods,
        //we must evaluate based on the param type (annotation used)
        else if (param.getParamType() == Parameter.ParamType.PROJECTION || param.getParamType() == Parameter.ParamType.PROJECTION_PARAM)
        {
          arguments[i] = context.getProjectionMask();
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.METADATA_PROJECTION_PARAM)
        {
          arguments[i] = context.getMetadataProjectionMask();
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.PAGING_PROJECTION_PARAM)
        {
          arguments[i] = context.getPagingProjectionMask();
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.CONTEXT || param.getParamType() == Parameter.ParamType.PAGING_CONTEXT_PARAM)
        {
          PagingContext ctx = RestUtils.getPagingContext(context, (PagingContext) param.getDefaultValue());
          arguments[i] = ctx;
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.PATH_KEYS || param.getParamType() == Parameter.ParamType.PATH_KEYS_PARAM)
        {
          arguments[i] = context.getPathKeys();
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.PATH_KEY_PARAM) {
          Object value = context.getPathKeys().get(param.getName());

          if (value != null)
          {
            arguments[i] = value;
            continue;
          }
        }
        else if (param.getParamType() == Parameter.ParamType.RESOURCE_CONTEXT || param.getParamType() == Parameter.ParamType.RESOURCE_CONTEXT_PARAM)
        {
          arguments[i] = context;
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.VALIDATOR_PARAM)
        {
          RestLiDataValidator validator = new RestLiDataValidator(resourceMethod.getResourceModel().getResourceClass().getAnnotations(),
                                                                  resourceMethod.getResourceModel().getValueClass(), resourceMethod.getMethodType());
          arguments[i] = validator;
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.RESTLI_ATTACHMENTS_PARAM)
        {
          arguments[i] = context.getRequestAttachmentReader();
          attachmentsDesired = true;
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.UNSTRUCTURED_DATA_WRITER_PARAM)
        {
          // The OutputStream is passed to the resource implementation in a synchronous call. Upon return of the
          // resource method, all the bytes would haven't written to the OutputStream. The EntityStream would have
          // contained all the bytes by the time data is requested. The ownership of the OutputStream is passed to
          // the ByteArrayOutputStreamWriter, which is responsible of closing the OutputStream if necessary.
          ByteArrayOutputStream out = new ByteArrayOutputStream();
          context.setResponseEntityStream(EntityStreams.newEntityStream(new ByteArrayOutputStreamWriter(out)));

          arguments[i] = new UnstructuredDataWriter(out, context);
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.UNSTRUCTURED_DATA_REACTIVE_READER_PARAM)
        {
          arguments[i] = new UnstructuredDataReactiveReader(context.getRequestEntityStream(), context.getRawRequest().getHeader(RestConstants.HEADER_CONTENT_TYPE));
          continue;
        }
        else if (param.getParamType() == Parameter.ParamType.POST)
        {
          // handle action parameters
          if (template != null)
          {
            DataMap data = template.data();
            if (data.containsKey(param.getName()))
            {
              arguments[i] = template.getValue(param);
              continue;
            }
          }
        }
        else if (param.getParamType() == Parameter.ParamType.QUERY)
        {
          Object value;
          if (DataTemplate.class.isAssignableFrom(param.getType()))
          {
            value = buildDataTemplateArgument(context.getStructuredParameter(param.getName()), param,
                resourceMethodConfig.shouldValidateQueryParams());
          }
          else
          {
            value = buildRegularArgument(context, param, resourceMethodConfig.shouldValidateQueryParams());
          }

          if (value != null)
          {
            arguments[i] = value;
            continue;
          }
        }
        else if (param.getParamType() == Parameter.ParamType.BATCH || param.getParamType() == Parameter.ParamType.RESOURCE_KEY)
        {
          // should not come to this routine since it should be handled by passing in positionalArguments
          throw new RoutingException("Parameter '" + param.getName() + "' should be passed in as a positional argument",
              HttpStatus.S_400_BAD_REQUEST.getCode());
        }
        else
        {
          // unknown param type
          throw new RoutingException(
              "Parameter '" + param.getName() + "' has an unknown parameter type '" + param.getParamType().name() + "'",
              HttpStatus.S_400_BAD_REQUEST.getCode());
        }
      }
      catch (TemplateRuntimeException e)
      {
        throw new RoutingException("Parameter '" + param.getName() + "' is invalid", HttpStatus.S_400_BAD_REQUEST.getCode());
      }

      try
      {
        // Handling null-valued parameters not provided in resource context or entity body
        // check if it is optional parameter
        if (param.isOptional() && param.hasDefaultValue())
        {
          arguments[i] = param.getDefaultValue();
        }
        else if (param.isOptional() && !param.getType().isPrimitive())
        {
          // optional primitive parameter must have default value or provided
          arguments[i] = null;
        }
        else
        {
          throw new RoutingException("Parameter '" + param.getName() + "' is required", HttpStatus.S_400_BAD_REQUEST.getCode());
        }
      }
      catch (ResourceConfigException e)
      {
        // Parameter default value format exception should result in server error code 500.
        throw new RestLiServiceException(HttpStatus.S_500_INTERNAL_SERVER_ERROR,
            "Parameter '" + param.getName() + "' default value is invalid", e);
      }
    }

    //Verify that if the resource method did not expect attachments, and attachments were present, that we drain all
    //incoming attachments and send back a bad request. We must take precaution here since simply ignoring the request
    //attachments is not correct behavior here. Ignoring other request level constructs such as headers or query parameters
    //that were not needed is safe, but not for request attachments.
    if (!attachmentsDesired && context.getRequestAttachmentReader() != null)
    {
      throw new RestLiServiceException(HttpStatus.S_400_BAD_REQUEST,
                                       "Resource method endpoint invoked does not accept any request attachments.");
    }
    return arguments;
  }

  /**
   * Because of backwards compatibility concerns, array fields of the key component of a
   * {@link ComplexResourceKey}s in a get request will be represented in the request url in the old
   * style.  That is, if an array field has the name "a", and contains [1,2] the part of the url
   * representing the serialized array will look like  "a=1&a=2".  However, if the array is a
   * singleton it will just be represented by "a=1". Therefore it is not possible to distinguish
   * between a single value itself and an array containing a single value.
   *
   * The purpose of this function is to fix up the singleton array problem by checking to see if the
   * request is a ComplexKey, whether that ComplexKey's key part has an array component, and, if so
   * and the data for that field is NOT a dataList, placing the data into a dataList.
   *
   * @param arguments the final list of all the arguments.
   */
  private static void fixUpComplexKeySingletonArraysInArguments(Object[] arguments)
  {
    for(int i=0; i < arguments.length; i++)
    {
      Object k = arguments[i];
      if (k instanceof ComplexResourceKey)
      {
        ComplexResourceKey<?, ?> complexResourceKey = (ComplexResourceKey<?, ?>)k;
        ComplexResourceKey<?, ?> newKey = QueryParamsDataMap.fixUpComplexKeySingletonArray(complexResourceKey);
        arguments[i] = newKey;
      }
    }
  }

  /**
   * Build a method argument from a request parameter that is an array
   *
   * @param context {@link ResourceContext}
   * @param param {@link Parameter}
   * @return argument value in the correct type
   */
  private static Object buildArrayArgument(final ResourceContext context,
                                           final Parameter<?> param,
                                           boolean validateParam)
  {
    final Object convertedValue;
    if (DataTemplate.class.isAssignableFrom(param.getItemType()))
    {
      final DataList itemsList = (DataList) context.getStructuredParameter(param.getName());
      convertedValue = Array.newInstance(param.getItemType(), itemsList.size());
      int j = 0;
      for (Object paramData: itemsList)
      {
        final DataTemplate<?> itemsElem = DataTemplateUtil.wrap(paramData, param.getItemType().asSubclass(DataTemplate.class));
        ArgumentUtils.validateDataAgainstSchema(itemsElem.data(), itemsElem.schema(), validateParam);
        Array.set(convertedValue, j++, itemsElem);
      }
    }
    else
    {
      final List<String> itemStringValues = context.getParameterValues(param.getName());
      ArrayDataSchema parameterSchema;
      if (param.getDataSchema() instanceof ArrayDataSchema)
      {
        parameterSchema = (ArrayDataSchema)param.getDataSchema();
      }
      else
      {
        throw new RoutingException("An array schema is expected.",
                                   HttpStatus.S_400_BAD_REQUEST.getCode());
      }

      convertedValue = Array.newInstance(param.getItemType(), itemStringValues.size());
      int j = 0;
      for (String itemStringValue : itemStringValues)
      {
        if (itemStringValue == null)
        {
          throw new RoutingException("Parameter '" + param.getName()
                                         + "' cannot contain null values", HttpStatus.S_400_BAD_REQUEST.getCode());
        }
        try
        {
          Array.set(convertedValue,
                    j++,
                    ArgumentUtils.convertSimpleValue(itemStringValue, parameterSchema.getItems(), param.getItemType(), false));
        }
        catch (NumberFormatException e)
        {
          Class<?> targetClass = DataSchemaUtil.dataSchemaTypeToPrimitiveDataSchemaClass(parameterSchema.getItems().getDereferencedType());
          // thrown from Integer.valueOf or Long.valueOf
          throw new RoutingException(String.format("Array parameter '%s' value '%s' must be of type '%s'",
                                                   param.getName(),
                                                   itemStringValue,
                                                   targetClass.getName()),
                                     HttpStatus.S_400_BAD_REQUEST.getCode());
        }
        catch (IllegalArgumentException e)
        {
          // thrown from Enum.valueOf
          throw new RoutingException(String.format("Array parameter '%s' value '%s' is invalid",
                                                   param.getName(),
                                                   itemStringValue),
                                     HttpStatus.S_400_BAD_REQUEST.getCode());
        }
        catch (TemplateRuntimeException e)
        {
          // thrown from DataTemplateUtil.coerceOutput
          throw new RoutingException(String.format("Array parameter '%s' value '%s' is invalid. Reason: %s",
                                                   param.getName(),
                                                   itemStringValue, e.getMessage()),
                                     HttpStatus.S_400_BAD_REQUEST.getCode());
        }
      }
    }

    return convertedValue;
  }

  /**
   * Build a method argument from a request parameter that is NOT backed by a schema, i.e.
   * a primitive or an array
   *
   * @param context {@link ResourceContext}
   * @param param {@link Parameter}
   * @return argument value in the correct type
   */
  private static Object buildRegularArgument(final ResourceContext context,
                                             final Parameter<?> param,
                                             boolean validateParam)
  {
    if (!context.hasParameter(param.getName()))
    {
      return null;
    }

    final Object convertedValue;
    if (param.isArray())
    {
      convertedValue = buildArrayArgument(context, param, validateParam);
    }
    else
    {
      String value = context.getParameter(param.getName());

      if (value == null)
      {
        return null;
      }
      else
      {
        try
        {
          convertedValue =
              ArgumentUtils.convertSimpleValue(value, param.getDataSchema(), param.getType(), validateParam);
        }
        catch (NumberFormatException e)
        {
          Class<?> targetClass = DataSchemaUtil.dataSchemaTypeToPrimitiveDataSchemaClass(param.getDataSchema().getDereferencedType());
          // thrown from Integer.valueOf or Long.valueOf
          throw new RoutingException(String.format("Argument parameter '%s' value '%s' must be of type '%s'",
                                                   param.getName(),
                                                   value,
                                                   targetClass.getName()),
                                     HttpStatus.S_400_BAD_REQUEST.getCode());
        }
        catch (IllegalArgumentException e)
        {
          // thrown from Enum.valueOf
          throw new RoutingException(String.format("Argument parameter '%s' value '%s' is invalid",
                                                   param.getName(),
                                                   value),
                                     HttpStatus.S_400_BAD_REQUEST.getCode());
        }
        catch (TemplateRuntimeException e)
        {
          // thrown from DataTemplateUtil.coerceOutput
          throw new RoutingException(String.format("Argument parameter '%s' value '%s' is invalid. Reason: %s",
                                                   param.getName(),
                                                   value, e.getMessage()),
                                     HttpStatus.S_400_BAD_REQUEST.getCode());
        }
      }
    }

    return convertedValue;
  }

  private static DataTemplate<?> buildDataTemplateArgument(final Object paramValue,
                                                           final Parameter<?> param,
                                                           final boolean validateParams)

  {
    DataTemplate<?> paramRecordTemplate;

    if (paramValue == null)
    {
      return null;
    }
    else
    {
      @SuppressWarnings("unchecked")
      final Class<? extends RecordTemplate> paramType = (Class<? extends RecordTemplate>) param.getType();
      /*
       * It is possible for the paramValue provided by ResourceContext to be coerced to the wrong type.
       * If a query param is a single value param for example www.domain.com/resource?foo=1.
       * Then ResourceContext will parse foo as a String with value = 1.
       * However if a query param contains many values for example www.domain.com/resource?foo=1&foo=2&foo=3
       * Then ResourceContext will parse foo as an DataList with value [1,2,3]
       *
       * So this means if the 'final' type of a query param is an Array and the paramValue we received from
       * ResourceContext is not a DataList we will have to wrap the paramValue inside a DataList
       */
      if (AbstractArrayTemplate.class.isAssignableFrom(paramType) && paramValue.getClass() != DataList.class)
      {
        paramRecordTemplate = DataTemplateUtil.wrap(new DataList(Collections.singletonList(paramValue)), paramType);
      }
      else
      {
        paramRecordTemplate = DataTemplateUtil.wrap(paramValue, paramType);
      }

      ArgumentUtils.validateDataAgainstSchema(paramRecordTemplate.data(), paramRecordTemplate.schema(), validateParams);
      return paramRecordTemplate;
    }
  }

  /**
   * @param request {@link com.linkedin.r2.message.rest.RestRequest}
   * @param recordClass resource value class
   * @param <V> resource value type which is a subclass of {@link RecordTemplate}
   * @return resource value
   */
  public static <V extends RecordTemplate> V extractEntity(final RestRequest request,
                                                           final Class<V> recordClass)
  {
    try
    {
      return DataMapUtils.read(request, recordClass);
    }
    catch (IOException e)
    {
      throw new RoutingException("Error parsing entity body: " + e.getMessage(),
                                 HttpStatus.S_400_BAD_REQUEST.getCode());
    }
  }

  /**
   * Convert a DataMap representation of a BatchRequest (string->record) into a Java Map
   * appropriate for passing into application code. Note that compound/complex keys are
   * represented as their string encoding in the DataMap. This method will parse the string
   * encoded keys to compare with the passed in keys from query parameters. During mismatch or
   * duplication of keys in the DataMap, an error will be thrown.
   *
   * @param routingResult {@link RoutingResult} instance for the current request
   * @param data The input DataMap to be converted
   * @param valueClass The RecordTemplate type of the values
   * @param ids The parsed batch ids from the request URI
   * @return A map using appropriate key and value classes, or null if ids is null
   */
  static <R extends RecordTemplate> Map<Object, R> buildBatchRequestMap(RoutingResult routingResult,
      DataMap data,
      Class<R> valueClass,
      Set<?> ids)
  {
    if (ids == null)
    {
      return null;
    }

    BatchRequest<R> batchRequest = new BatchRequest<>(data, new TypeSpec<R>(valueClass));

    Map<Object, R> result =
        new HashMap<>(CollectionUtils.getMapInitialCapacity(batchRequest.getEntities().size(), 0.75f), 0.75f);
    for (Map.Entry<String, R> entry : batchRequest.getEntities().entrySet())
    {
      Object typedKey = parseEntityStringKey(entry.getKey(), routingResult);

      if (result.containsKey(typedKey))
      {
        throw new RoutingException(
            String.format("Duplicate key in batch request body: '%s'", typedKey),
            HttpStatus.S_400_BAD_REQUEST.getCode());
      }

      if (!ids.contains(typedKey))
      {
        throw new RoutingException(
          String.format("Batch request mismatch. Entity key '%s' not found in the query parameter.", typedKey),
          HttpStatus.S_400_BAD_REQUEST.getCode());
      }

      R value = DataTemplateUtil.wrap(entry.getValue().data(), valueClass);
      result.put(typedKey, value);
    }

    if (!ids.equals(result.keySet()))
    {
      throw new RoutingException(
        String.format("Batch request mismatch. URI keys: '%s' Entity keys: '%s'",
                      ids.toString(),
                      result.keySet().toString()),
        HttpStatus.S_400_BAD_REQUEST.getCode());
    }
    return result;
  }

  /**
   * Parses the provided string key value and returns its corresponding typed key instance. This method should only be
   * used to parse keys which appear in the request body.
   *
   * @param stringKey Key string from the entity body
   * @param routingResult {@link RoutingResult} instance for the current request
   * @return An instance of key's corresponding type
   */
  private static Object parseEntityStringKey(final String stringKey, final RoutingResult routingResult)
  {
    ResourceModel resourceModel = routingResult.getResourceMethod().getResourceModel();
    ServerResourceContext resourceContext = routingResult.getContext();
    ProtocolVersion version = resourceContext.getRestliProtocolVersion();

    try
    {
      Key primaryKey = resourceModel.getPrimaryKey();
      String altKeyName = resourceContext.getParameter(RestConstants.ALT_KEY_PARAM);

      if (altKeyName != null)
      {
        return ArgumentUtils.translateFromAlternativeKey(
            ArgumentUtils.parseAlternativeKey(stringKey, altKeyName, resourceModel, version,
                routingResult.getResourceMethodConfig().shouldValidateResourceKeys()),
            altKeyName, resourceModel);
      }
      else if (ComplexResourceKey.class.equals(primaryKey.getType()))
      {
        ComplexResourceKey<RecordTemplate, RecordTemplate> complexKey = ComplexResourceKey.parseString(stringKey,
            ComplexKeySpec.forClassesMaybeNull(resourceModel.getKeyKeyClass(), resourceModel.getKeyParamsClass()),
            version);
        if (routingResult.getResourceMethodConfig().shouldValidateResourceKeys())
        {
          complexKey.validate();
        }
        return complexKey;
      }
      else if (CompoundKey.class.equals(primaryKey.getType()))
      {
        return ArgumentUtils.parseCompoundKey(stringKey, resourceModel.getKeys(), version,
            routingResult.getResourceMethodConfig().shouldValidateResourceKeys());
      }
      else
      {
        // The conversion of simple keys doesn't include URL decoding as the current version of Rest.li clients don't
        // encode simple keys which appear in the request body for BATCH UPDATE and BATCH PATCH requests.
        Key key = resourceModel.getPrimaryKey();
        return ArgumentUtils.convertSimpleValue(stringKey, key.getDataSchema(), key.getType(),
            routingResult.getResourceMethodConfig().shouldValidateResourceKeys());
      }
    }
    catch (InvalidAlternativeKeyException | AlternativeKeyCoercerException | PathSegment.PathSegmentSyntaxException | IllegalArgumentException e)
    {
      throw new RoutingException(String.format("Invalid key: '%s'", stringKey),
          HttpStatus.S_400_BAD_REQUEST.getCode());
    }
  }

  /**
   * A reactive Writer that writes out all the bytes written to a ByteArrayOutputStream as one data chunk.
   */
  private static class ByteArrayOutputStreamWriter implements Writer<ByteString>
  {
    private final ByteArrayOutputStream _out;
    private WriteHandle<? super ByteString> _wh;

    ByteArrayOutputStreamWriter(ByteArrayOutputStream out)
    {
      _out = out;
    }

    @Override
    public void onInit(WriteHandle<? super ByteString> wh)
    {
      _wh = wh;
    }

    @Override
    public void onWritePossible()
    {
      if (_wh.remaining() > 0)
      {
        _wh.write(ByteString.unsafeWrap(_out.toByteArray()));
        _wh.done();
      }
    }

    @Override
    public void onAbort(Throwable ex)
    {
      // Closing ByteArrayOutputStream is unnecessary because it doesn't hold any internal resource that needs to
      // be released. However, if the implementation changes to use a different backing OutputStream, this needs to be
      // re-evaluated. OutputStream may need to be called here, after _wh.done(), and in finalize().
    }
  }

  static void checkEntityNotNull(DataMap dataMap, ResourceMethod method) {
    if (dataMap == null) {
      throw new RoutingException(
          String.format("Empty entity body is not allowed for %s method request", method),
          HttpStatus.S_400_BAD_REQUEST.getCode());
    }
  }
}


/*
 * Created on Dec 12, 2008
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
 * the License. You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
 * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
 * specific language governing permissions and limitations under the License.
 *
 * Copyright @2008-2013 the original author or authors.
 */
package org.fest.swing.edt;

import static org.fest.assertions.Assertions.assertThat;
import static org.fest.swing.edt.GuiActionRunner.execute;
import static org.fest.swing.test.core.CommonAssertions.failWhenExpectingException;
import static org.fest.util.Strings.concat;

import org.junit.Test;

/**
 * Tests for Bug 247.
 *
 * @author Alex Ruiz
 */
public class Bug247_NotEnoughInfoInFailureInEDT_Test {
  private static String TEST_NAME = Bug247_NotEnoughInfoInFailureInEDT_Test.class.getName();

  @Test
  public void should_show_method_call_in_current_thread_when_failing_in_EDT() {
    boolean testClassInStackTrace = false;
    try {
      execute(new GuiTask() {
        @Override
        protected void executeInEDT() {
          throw new RuntimeException("Thrown on purpose");
        }
      });
      failWhenExpectingException();
    } catch (RuntimeException e) {
      StackTraceElement[] stackTrace = e.getStackTrace();
      StackTraceElement first = stackTrace[0];
      assertThat(first.getClassName()).isEqualTo(concat(TEST_NAME, "$1"));
      assertThat(first.getMethodName()).isEqualTo("executeInEDT");
      String expected = Bug247_NotEnoughInfoInFailureInEDT_Test.class.getName();
      for (StackTraceElement element : e.getStackTrace()) {
        if (!expected.equals(element.getClassName())) {
          continue;
        }
        testClassInStackTrace = true;
        break;
      }
    }
    assertThat(testClassInStackTrace).as("test class in stack trace").isTrue();
  }
}


---
# required metadata

title: Create and post depreciation for a fixed asset group by using depreciation books
description: This topic walks you through the process of creating and posting depreciation for a fixed asset group by using depreciation books for India in Microsoft Dynamics 365 Finance.
author: AdamTrukawka
manager: AnnBe
ms.date: 01/05/2018
ms.topic: article
ms.prod:
ms.service: dynamics-ax-applications
ms.technology:

# optional metadata

# ms.search.form:
audience: Application User
# ms.devlang:
ms.reviewer: kfend
ms.search.scope: Core, Operations
# ms.tgt_pltfrm:
# ms.custom:
ms.search.region: India
# ms.search.industry:
ms.author: atrukawk
ms.search.validFrom: 2017-12-31
ms.dyn365.ops.version: 7.3

---

# Create and post depreciation for a fixed asset group by using depreciation books

[!include [banner](../includes/banner.md)]

You can calculate depreciation for a group of fixed assets. The calculation is based on the number of days that is defined in the **Asset group depreciation threshold** field on the **Fixed assets parameters** page. The following table shows the various formulas that are used to calculate depreciation for asset groups.

| Type of proposal   | Number of days that the asset is used                                                        | Formula |
|--------------------|----------------------------------------------------------------------------------------------|---------|
| Depreciation       | Equal to or more than the number of days in the **Asset group depreciation threshold** field | (Net book value of the fixed asset group on the date of depreciation) × (Rate of depreciation that is defined for the depreciation profile) |
| Depreciation       | Less than the number of days in the **Asset group depreciation threshold** field             | (Net book value of the fixed asset) × (Depreciation threshold percentage that is defined in the parameters) × (Rate of depreciation that is defined for the depreciation profile) |
| Bonus depreciation | Equal to or more than the number of days in the **Asset group depreciation threshold** field | (Cost of acquisition) × (Rate of depreciation that is defined in the depreciation profile) |
| Bonus depreciation | Less than the number of days in the **Asset group depreciation threshold** field             | (Cost of acquisition) × (Depreciation threshold percentage that is defined on the **General ledger parameters** page) × (Rate of depreciation that is defined in the depreciation profile) |

## Example

On April 1, 2008, you own three fixed assets: Machinery A, Machinery B, and Machinery C. The written-down value of Machinery A is INR 70,000, the written-down value of Machinery B is INR 1,64,000, and the written-down value of Machinery C is INR 84,000. The rate of depreciation is 15 percent. On November 2, 2008, you purchase Machinery D for INR 60,000. Then, on March 15, 2009, you sell Machinery B for INR 1,80,000 and Machinery C for INR 40,000.

The calculated written-down value of the asset group on March 31, 2009, is INR 1,58,000 (INR 3,18,000 + INR 60,000 – INR 2,20,000). This value is calculated by adding the amount of the new machinery to the sum of the written-down value of Machinery A, Machinery B, and Machinery C, and then deducting the proceeds from the sale of Machinery B and Machinery C.

You must calculate depreciation on the asset that is used for fewer than 180 days at a rate of 7.5 percent. In this case, the depreciation is INR 4,500 (INR 60,000 × 7.5%). The depreciation on the remaining amount of the written-down value of the asset group is calculated at a rate of 15 percent. In this case, the depreciation is INR 14,700.

On March 31, 2009, you must deduct the amount of depreciation from the written-down value of the group of assets (INR 1,58,000 – INR 60,000 = INR 98,000) to calculate the written-down value of the asset group on April 1, 2008. In this case, the written-down value is INR 1,38,800 (INR 1,58,000 – INR 19,200).

Depreciation isn't calculated for an asset group that has a written-down value of 0 (zero). If the sale amount of all or some assets in a fixed asset group exceeds the net book value of the group during a year, this situation is considered a short-term capital gain. Therefore, the asset group will have a written-down value of 0 (zero). If the sale amount of all assets in a fixed asset group is less than the net book value of the fixed asset group, this situation is considered a short-term capital loss. Therefore, the asset group will have a written-down value of 0 (zero).

If a positive or negative amount is entered in the **Debit** field on a journal line, the same amount is updated on the **Fixed asset balances** page. However, if a positive amount is entered in the **Credit** field, the amount is updated as a negative amount. This negative amount is then updated as a positive amount on the **Fixed asset balances** page.

## Create and post fixed asset depreciation in journal

1. Create a new **Fixed asset journal** to post depreciation transaction.
2. In the **Name** field, select journal for posting depreciation.
3. Select **Lines** and add new line.
4. In the **Transaction type** field, select **Depreciation** transaction type.
5. In the **Account** field, select a fixed asset.

    > [!NOTE]
    > The **Fixed asset number** field isn't available in a journal line if the **Asset group depreciation** is set to **Yes** in fixed asset book.

6. In the **Fixed asset group** field, select a fixed asset group.
7. Enter depreciation amount in the **Credit** field.
8. Select **Post** to post the journal.
9. Click **Fixed assets** > **Fixed assets** > Select a fixed asset > **Books** tab on Action Pane.
10. Click **Transactions** and notice that the depreciation amount was posted for the fixed asset group without the specification of an asset.
11. Close the **Fixed assets transactions** page.
12. Click **Inquiry** > **Asset group balances** and notice that the total depreciation amount was posted for the asset group in the selected book.

    > [!NOTE]
    > In the journal you can use the **Proposal** function for various proposal types to create transactions for fixed asset groups. Asset group depreciation doesn't apply to proposals of the **Consumption depreciation**, **Revenue recognition of reserves**, or **Extraordinary depreciation** type.


/*
 * Created by Michael Carrara <michael.carrara@breadwallet.com> on 7/1/19.
 * Copyright (c) 2019 Breadwinner AG.  All right reserved.
*
 * See the LICENSE file at the project root for license information.
 * See the CONTRIBUTORS file at the project root for a list of contributors.
 */
package com.breadwallet.crypto.blockchaindb.errors;

// Could not convert JSON to model
public class QueryModelError extends QueryError {

    public QueryModelError(String message) {
        super(message);
    }
}


using System.Collections.Generic;
using Microsoft.AspNetCore.Mvc;

namespace Basic.Controllers
{
    [Route("/stores")]
    [Produces("application/json")]
    public class UnboundParamsController
    {

        [HttpPost]
        public int Create(Store store)
        {
            return 1;
        }

        [HttpGet]
        public IEnumerable<Store> Search(string[] locations = null)
        {
            return new[]
            {
                new Store { Id = 1, Location = "Boston" },
                new Store { Id = 1, Location = "Seattle" }
            };
        }

        [HttpGet("{id}")]
        public Store GetById(int id)
        {
            return new Store { Id = 1, Location = "Boston" };
        }

        [HttpPut("{id}")]
        public void Update(int id, Store store)
        {
        }

        [HttpDelete("{id}")]
        public void Delete(int id)
        {
        }
    }

    public class Store
    {
        public int Id { get; set; }

        public string Location { get; set; }
    }
}


% Generated by roxygen2: do not edit by hand
% Please edit documentation in R/econ-sans.R
\name{theme_ipsum_es}
\alias{theme_ipsum_es}
\title{A precise & pristine \link{ggplot2} theme with opinionated defaults and an emphasis on typoghraphy}
\usage{
theme_ipsum_es(
  base_family = "EconSansCndReg",
  base_size = 11.5,
  plot_title_family = "EconSansCndBol",
  plot_title_size = 18,
  plot_title_face = "bold",
  plot_title_margin = 10,
  subtitle_family = if (.Platform$OS.type == "windows") "EconSansCndLig" else
    "EconSansCndLig",
  subtitle_size = 13,
  subtitle_face = "plain",
  subtitle_margin = 15,
  strip_text_family = base_family,
  strip_text_size = 12,
  strip_text_face = "plain",
  caption_family = if (.Platform$OS.type == "windows") "EconSansCndLig" else
    "EconSansCndLig",
  caption_size = 9,
  caption_face = "plain",
  caption_margin = 10,
  axis_text_size = base_size,
  axis_title_family = base_family,
  axis_title_size = 9,
  axis_title_face = "plain",
  axis_title_just = "rt",
  plot_margin = margin(30, 30, 30, 30),
  panel_spacing = grid::unit(2, "lines"),
  grid_col = "#cccccc",
  grid = TRUE,
  axis_col = "#cccccc",
  axis = FALSE,
  ticks = FALSE
)
}
\arguments{
\item{base_family, base_size}{base font family and size}

\item{plot_title_family, plot_title_face, plot_title_size, plot_title_margin}{plot tilte family, face, size and margin}

\item{subtitle_family, subtitle_face, subtitle_size}{plot subtitle family, face and size}

\item{subtitle_margin}{plot subtitle margin bottom (single numeric value)}

\item{strip_text_family, strip_text_face, strip_text_size}{facet label font family, face and size}

\item{caption_family, caption_face, caption_size, caption_margin}{plot caption family, face, size and margin}

\item{axis_text_size}{font size of axis text}

\item{axis_title_family, axis_title_face, axis_title_size}{axis title font family, face and size}

\item{axis_title_just}{axis title font justificationk one of \verb{[blmcrt]}}

\item{plot_margin}{plot margin (specify with \link[ggplot2:margin]{ggplot2::margin})}

\item{panel_spacing}{panel spacing (use \code{unit()})}

\item{grid_col}{grid color}

\item{grid}{panel grid (\code{TRUE}, \code{FALSE}, or a combination of \code{X}, \code{x}, \code{Y}, \code{y})}

\item{axis_col}{axis color}

\item{axis}{add x or y axes? \code{TRUE}, \code{FALSE}, "\code{xy}"}

\item{ticks}{ticks if \code{TRUE} add ticks}
}
\description{
You should \code{\link[=import_econ_sans]{import_econ_sans()}} first and also install the fonts on your
system before trying to use this theme.
}
\details{
There is an option \code{hrbrthemes.loadfonts} which -- if set to \code{TRUE} -- will
call \code{extrafont::loadfonts()} to register non-core fonts with R PDF & PostScript
devices. If you are running under Windows, the package calls the same function
to register non-core fonts with the Windows graphics device.
}
\section{Why Econ Sans Condensed?}{

It's free, has tolerable kerning pairs and multiple weights. It's also different
than Arial Narrow and the fonts most folks use in ggplot2 charts.
}

\examples{
\dontrun{
library(ggplot2)
library(dplyr)

# seminal scatterplot
ggplot(mtcars, aes(mpg, wt)) +
  geom_point() +
  labs(x="Fuel efficiency (mpg)", y="Weight (tons)",
       title="Seminal ggplot2 scatterplot example",
       subtitle="A plot that is only useful for demonstration purposes",
       caption="Brought to you by the letter 'g'") +
  theme_ipsum_es()

# seminal bar chart

# note: may need to make this font_es on Windows
update_geom_font_defaults(family=font_es_light)

count(mpg, class) \%>\%
  ggplot(aes(class, n)) +
  geom_col() +
  geom_text(aes(label=n), nudge_y=3) +
  labs(x="Fuel efficiency (mpg)", y="Weight (tons)",
       title="Seminal ggplot2 bar chart example",
       subtitle="A plot that is only useful for demonstration purposes",
       caption="Brought to you by the letter 'g'") +
  theme_ipsum_es(grid="Y") +
  theme(axis.text.y=element_blank())
}
}


/* IllegalComponentStateException.java -- bad component state
   Copyright (C) 1999, 2002, 2005  Free Software Foundation, Inc.

This file is part of GNU Classpath.

GNU Classpath is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.

GNU Classpath is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
General Public License for more details.

You should have received a copy of the GNU General Public License
along with GNU Classpath; see the file COPYING.  If not, write to the
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301 USA.

Linking this library statically or dynamically with other modules is
making a combined work based on this library.  Thus, the terms and
conditions of the GNU General Public License cover the whole
combination.

As a special exception, the copyright holders of this library give you
permission to link this library with independent modules to produce an
executable, regardless of the license terms of these independent
modules, and to copy and distribute the resulting executable under
terms of your choice, provided that you also meet, for each linked
independent module, the terms and conditions of the license of that
module.  An independent module is a module which is not derived from
or based on this library.  If you modify this library, you may extend
this exception to your version of the library, but you are not
obligated to do so.  If you do not wish to do so, delete this
exception statement from your version. */

package java.awt;

/**
 * This exception is thrown when the requested operation failed because
 * a component was not in the proper state.
 *
 * @author Aaron M. Renn (arenn@urbanophile.com)
 * @status updated to 1.4
 */
public class IllegalComponentStateException extends IllegalStateException
{
  /**
   * Compatible with JDK 1.0+.
   */
  private static final long serialVersionUID = -1889339587208144238L;

  /**
   * Create a new instance with no detailed error message.
   */
  public IllegalComponentStateException()
  {
  }

  /**
   * Create a new instance with the specified detailed error message.
   *
   * @param message the detailed error message
   */
  public IllegalComponentStateException(String message)
  {
    super(message);
  }
} // class IllegalComponentStateException


/* pngtrans.c - transforms the data in a row (used by both readers and writers)
 *
 * Last changed in libpng 1.2.17 May 15, 2007
 * For conditions of distribution and use, see copyright notice in png.h
 * Copyright (c) 1998-2007 Glenn Randers-Pehrson
 * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger)
 * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.)
 */

#define PNG_INTERNAL
#include "png.h"

#if defined(PNG_READ_SUPPORTED) || defined(PNG_WRITE_SUPPORTED)
#if defined(PNG_READ_BGR_SUPPORTED) || defined(PNG_WRITE_BGR_SUPPORTED)
/* turn on BGR-to-RGB mapping */
void PNGAPI
png_set_bgr(png_structp png_ptr)
{
   png_debug(1, "in png_set_bgr\n");
   if(png_ptr == NULL) return;
   png_ptr->transformations |= PNG_BGR;
}
#endif

#if defined(PNG_READ_SWAP_SUPPORTED) || defined(PNG_WRITE_SWAP_SUPPORTED)
/* turn on 16 bit byte swapping */
void PNGAPI
png_set_swap(png_structp png_ptr)
{
   png_debug(1, "in png_set_swap\n");
   if(png_ptr == NULL) return;
   if (png_ptr->bit_depth == 16)
      png_ptr->transformations |= PNG_SWAP_BYTES;
}
#endif

#if defined(PNG_READ_PACK_SUPPORTED) || defined(PNG_WRITE_PACK_SUPPORTED)
/* turn on pixel packing */
void PNGAPI
png_set_packing(png_structp png_ptr)
{
   png_debug(1, "in png_set_packing\n");
   if(png_ptr == NULL) return;
   if (png_ptr->bit_depth < 8)
   {
      png_ptr->transformations |= PNG_PACK;
      png_ptr->usr_bit_depth = 8;
   }
}
#endif

#if defined(PNG_READ_PACKSWAP_SUPPORTED)||defined(PNG_WRITE_PACKSWAP_SUPPORTED)
/* turn on packed pixel swapping */
void PNGAPI
png_set_packswap(png_structp png_ptr)
{
   png_debug(1, "in png_set_packswap\n");
   if(png_ptr == NULL) return;
   if (png_ptr->bit_depth < 8)
      png_ptr->transformations |= PNG_PACKSWAP;
}
#endif

#if defined(PNG_READ_SHIFT_SUPPORTED) || defined(PNG_WRITE_SHIFT_SUPPORTED)
void PNGAPI
png_set_shift(png_structp png_ptr, png_color_8p true_bits)
{
   png_debug(1, "in png_set_shift\n");
   if(png_ptr == NULL) return;
   png_ptr->transformations |= PNG_SHIFT;
   png_ptr->shift = *true_bits;
}
#endif

#if defined(PNG_READ_INTERLACING_SUPPORTED) || \
    defined(PNG_WRITE_INTERLACING_SUPPORTED)
int PNGAPI
png_set_interlace_handling(png_structp png_ptr)
{
   png_debug(1, "in png_set_interlace handling\n");
   if (png_ptr && png_ptr->interlaced)
   {
      png_ptr->transformations |= PNG_INTERLACE;
      return (7);
   }

   return (1);
}
#endif

#if defined(PNG_READ_FILLER_SUPPORTED) || defined(PNG_WRITE_FILLER_SUPPORTED)
/* Add a filler byte on read, or remove a filler or alpha byte on write.
 * The filler type has changed in v0.95 to allow future 2-byte fillers
 * for 48-bit input data, as well as to avoid problems with some compilers
 * that don't like bytes as parameters.
 */
void PNGAPI
png_set_filler(png_structp png_ptr, png_uint_32 filler, int filler_loc)
{
   png_debug(1, "in png_set_filler\n");
   if(png_ptr == NULL) return;
   png_ptr->transformations |= PNG_FILLER;
   png_ptr->filler = (png_byte)filler;
   if (filler_loc == PNG_FILLER_AFTER)
      png_ptr->flags |= PNG_FLAG_FILLER_AFTER;
   else
      png_ptr->flags &= ~PNG_FLAG_FILLER_AFTER;

   /* This should probably go in the "do_read_filler" routine.
    * I attempted to do that in libpng-1.0.1a but that caused problems
    * so I restored it in libpng-1.0.2a
   */

   if (png_ptr->color_type == PNG_COLOR_TYPE_RGB)
   {
      png_ptr->usr_channels = 4;
   }

   /* Also I added this in libpng-1.0.2a (what happens when we expand
    * a less-than-8-bit grayscale to GA? */

   if (png_ptr->color_type == PNG_COLOR_TYPE_GRAY && png_ptr->bit_depth >= 8)
   {
      png_ptr->usr_channels = 2;
   }
}

#if !defined(PNG_1_0_X)
/* Added to libpng-1.2.7 */
void PNGAPI
png_set_add_alpha(png_structp png_ptr, png_uint_32 filler, int filler_loc)
{
   png_debug(1, "in png_set_add_alpha\n");
   if(png_ptr == NULL) return;
   png_set_filler(png_ptr, filler, filler_loc);
   png_ptr->transformations |= PNG_ADD_ALPHA;
}
#endif

#endif

#if defined(PNG_READ_SWAP_ALPHA_SUPPORTED) || \
    defined(PNG_WRITE_SWAP_ALPHA_SUPPORTED)
void PNGAPI
png_set_swap_alpha(png_structp png_ptr)
{
   png_debug(1, "in png_set_swap_alpha\n");
   if(png_ptr == NULL) return;
   png_ptr->transformations |= PNG_SWAP_ALPHA;
}
#endif

#if defined(PNG_READ_INVERT_ALPHA_SUPPORTED) || \
    defined(PNG_WRITE_INVERT_ALPHA_SUPPORTED)
void PNGAPI
png_set_invert_alpha(png_structp png_ptr)
{
   png_debug(1, "in png_set_invert_alpha\n");
   if(png_ptr == NULL) return;
   png_ptr->transformations |= PNG_INVERT_ALPHA;
}
#endif

#if defined(PNG_READ_INVERT_SUPPORTED) || defined(PNG_WRITE_INVERT_SUPPORTED)
void PNGAPI
png_set_invert_mono(png_structp png_ptr)
{
   png_debug(1, "in png_set_invert_mono\n");
   if(png_ptr == NULL) return;
   png_ptr->transformations |= PNG_INVERT_MONO;
}

/* invert monochrome grayscale data */
void /* PRIVATE */
png_do_invert(png_row_infop row_info, png_bytep row)
{
   png_debug(1, "in png_do_invert\n");
  /* This test removed from libpng version 1.0.13 and 1.2.0:
   *   if (row_info->bit_depth == 1 &&
   */
#if defined(PNG_USELESS_TESTS_SUPPORTED)
   if (row == NULL || row_info == NULL)
     return;
#endif
   if (row_info->color_type == PNG_COLOR_TYPE_GRAY)
   {
      png_bytep rp = row;
      png_uint_32 i;
      png_uint_32 istop = row_info->rowbytes;

      for (i = 0; i < istop; i++)
      {
         *rp = (png_byte)(~(*rp));
         rp++;
      }
   }
   else if (row_info->color_type == PNG_COLOR_TYPE_GRAY_ALPHA &&
      row_info->bit_depth == 8)
   {
      png_bytep rp = row;
      png_uint_32 i;
      png_uint_32 istop = row_info->rowbytes;

      for (i = 0; i < istop; i+=2)
      {
         *rp = (png_byte)(~(*rp));
         rp+=2;
      }
   }
   else if (row_info->color_type == PNG_COLOR_TYPE_GRAY_ALPHA &&
      row_info->bit_depth == 16)
   {
      png_bytep rp = row;
      png_uint_32 i;
      png_uint_32 istop = row_info->rowbytes;

      for (i = 0; i < istop; i+=4)
      {
         *rp = (png_byte)(~(*rp));
         *(rp+1) = (png_byte)(~(*(rp+1)));
         rp+=4;
      }
   }
}
#endif

#if defined(PNG_READ_SWAP_SUPPORTED) || defined(PNG_WRITE_SWAP_SUPPORTED)
/* swaps byte order on 16 bit depth images */
void /* PRIVATE */
png_do_swap(png_row_infop row_info, png_bytep row)
{
   png_debug(1, "in png_do_swap\n");
   if (
#if defined(PNG_USELESS_TESTS_SUPPORTED)
       row != NULL && row_info != NULL &&
#endif
       row_info->bit_depth == 16)
   {
      png_bytep rp = row;
      png_uint_32 i;
      png_uint_32 istop= row_info->width * row_info->channels;

      for (i = 0; i < istop; i++, rp += 2)
      {
         png_byte t = *rp;
         *rp = *(rp + 1);
         *(rp + 1) = t;
      }
   }
}
#endif

#if defined(PNG_READ_PACKSWAP_SUPPORTED)||defined(PNG_WRITE_PACKSWAP_SUPPORTED)
static PNG_CONST png_byte onebppswaptable[256] = {
   0x00, 0x80, 0x40, 0xC0, 0x20, 0xA0, 0x60, 0xE0,
   0x10, 0x90, 0x50, 0xD0, 0x30, 0xB0, 0x70, 0xF0,
   0x08, 0x88, 0x48, 0xC8, 0x28, 0xA8, 0x68, 0xE8,
   0x18, 0x98, 0x58, 0xD8, 0x38, 0xB8, 0x78, 0xF8,
   0x04, 0x84, 0x44, 0xC4, 0x24, 0xA4, 0x64, 0xE4,
   0x14, 0x94, 0x54, 0xD4, 0x34, 0xB4, 0x74, 0xF4,
   0x0C, 0x8C, 0x4C, 0xCC, 0x2C, 0xAC, 0x6C, 0xEC,
   0x1C, 0x9C, 0x5C, 0xDC, 0x3C, 0xBC, 0x7C, 0xFC,
   0x02, 0x82, 0x42, 0xC2, 0x22, 0xA2, 0x62, 0xE2,
   0x12, 0x92, 0x52, 0xD2, 0x32, 0xB2, 0x72, 0xF2,
   0x0A, 0x8A, 0x4A, 0xCA, 0x2A, 0xAA, 0x6A, 0xEA,
   0x1A, 0x9A, 0x5A, 0xDA, 0x3A, 0xBA, 0x7A, 0xFA,
   0x06, 0x86, 0x46, 0xC6, 0x26, 0xA6, 0x66, 0xE6,
   0x16, 0x96, 0x56, 0xD6, 0x36, 0xB6, 0x76, 0xF6,
   0x0E, 0x8E, 0x4E, 0xCE, 0x2E, 0xAE, 0x6E, 0xEE,
   0x1E, 0x9E, 0x5E, 0xDE, 0x3E, 0xBE, 0x7E, 0xFE,
   0x01, 0x81, 0x41, 0xC1, 0x21, 0xA1, 0x61, 0xE1,
   0x11, 0x91, 0x51, 0xD1, 0x31, 0xB1, 0x71, 0xF1,
   0x09, 0x89, 0x49, 0xC9, 0x29, 0xA9, 0x69, 0xE9,
   0x19, 0x99, 0x59, 0xD9, 0x39, 0xB9, 0x79, 0xF9,
   0x05, 0x85, 0x45, 0xC5, 0x25, 0xA5, 0x65, 0xE5,
   0x15, 0x95, 0x55, 0xD5, 0x35, 0xB5, 0x75, 0xF5,
   0x0D, 0x8D, 0x4D, 0xCD, 0x2D, 0xAD, 0x6D, 0xED,
   0x1D, 0x9D, 0x5D, 0xDD, 0x3D, 0xBD, 0x7D, 0xFD,
   0x03, 0x83, 0x43, 0xC3, 0x23, 0xA3, 0x63, 0xE3,
   0x13, 0x93, 0x53, 0xD3, 0x33, 0xB3, 0x73, 0xF3,
   0x0B, 0x8B, 0x4B, 0xCB, 0x2B, 0xAB, 0x6B, 0xEB,
   0x1B, 0x9B, 0x5B, 0xDB, 0x3B, 0xBB, 0x7B, 0xFB,
   0x07, 0x87, 0x47, 0xC7, 0x27, 0xA7, 0x67, 0xE7,
   0x17, 0x97, 0x57, 0xD7, 0x37, 0xB7, 0x77, 0xF7,
   0x0F, 0x8F, 0x4F, 0xCF, 0x2F, 0xAF, 0x6F, 0xEF,
   0x1F, 0x9F, 0x5F, 0xDF, 0x3F, 0xBF, 0x7F, 0xFF
};

static PNG_CONST png_byte twobppswaptable[256] = {
   0x00, 0x40, 0x80, 0xC0, 0x10, 0x50, 0x90, 0xD0,
   0x20, 0x60, 0xA0, 0xE0, 0x30, 0x70, 0xB0, 0xF0,
   0x04, 0x44, 0x84, 0xC4, 0x14, 0x54, 0x94, 0xD4,
   0x24, 0x64, 0xA4, 0xE4, 0x34, 0x74, 0xB4, 0xF4,
   0x08, 0x48, 0x88, 0xC8, 0x18, 0x58, 0x98, 0xD8,
   0x28, 0x68, 0xA8, 0xE8, 0x38, 0x78, 0xB8, 0xF8,
   0x0C, 0x4C, 0x8C, 0xCC, 0x1C, 0x5C, 0x9C, 0xDC,
   0x2C, 0x6C, 0xAC, 0xEC, 0x3C, 0x7C, 0xBC, 0xFC,
   0x01, 0x41, 0x81, 0xC1, 0x11, 0x51, 0x91, 0xD1,
   0x21, 0x61, 0xA1, 0xE1, 0x31, 0x71, 0xB1, 0xF1,
   0x05, 0x45, 0x85, 0xC5, 0x15, 0x55, 0x95, 0xD5,
   0x25, 0x65, 0xA5, 0xE5, 0x35, 0x75, 0xB5, 0xF5,
   0x09, 0x49, 0x89, 0xC9, 0x19, 0x59, 0x99, 0xD9,
   0x29, 0x69, 0xA9, 0xE9, 0x39, 0x79, 0xB9, 0xF9,
   0x0D, 0x4D, 0x8D, 0xCD, 0x1D, 0x5D, 0x9D, 0xDD,
   0x2D, 0x6D, 0xAD, 0xED, 0x3D, 0x7D, 0xBD, 0xFD,
   0x02, 0x42, 0x82, 0xC2, 0x12, 0x52, 0x92, 0xD2,
   0x22, 0x62, 0xA2, 0xE2, 0x32, 0x72, 0xB2, 0xF2,
   0x06, 0x46, 0x86, 0xC6, 0x16, 0x56, 0x96, 0xD6,
   0x26, 0x66, 0xA6, 0xE6, 0x36, 0x76, 0xB6, 0xF6,
   0x0A, 0x4A, 0x8A, 0xCA, 0x1A, 0x5A, 0x9A, 0xDA,
   0x2A, 0x6A, 0xAA, 0xEA, 0x3A, 0x7A, 0xBA, 0xFA,
   0x0E, 0x4E, 0x8E, 0xCE, 0x1E, 0x5E, 0x9E, 0xDE,
   0x2E, 0x6E, 0xAE, 0xEE, 0x3E, 0x7E, 0xBE, 0xFE,
   0x03, 0x43, 0x83, 0xC3, 0x13, 0x53, 0x93, 0xD3,
   0x23, 0x63, 0xA3, 0xE3, 0x33, 0x73, 0xB3, 0xF3,
   0x07, 0x47, 0x87, 0xC7, 0x17, 0x57, 0x97, 0xD7,
   0x27, 0x67, 0xA7, 0xE7, 0x37, 0x77, 0xB7, 0xF7,
   0x0B, 0x4B, 0x8B, 0xCB, 0x1B, 0x5B, 0x9B, 0xDB,
   0x2B, 0x6B, 0xAB, 0xEB, 0x3B, 0x7B, 0xBB, 0xFB,
   0x0F, 0x4F, 0x8F, 0xCF, 0x1F, 0x5F, 0x9F, 0xDF,
   0x2F, 0x6F, 0xAF, 0xEF, 0x3F, 0x7F, 0xBF, 0xFF
};

static PNG_CONST png_byte fourbppswaptable[256] = {
   0x00, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70,
   0x80, 0x90, 0xA0, 0xB0, 0xC0, 0xD0, 0xE0, 0xF0,
   0x01, 0x11, 0x21, 0x31, 0x41, 0x51, 0x61, 0x71,
   0x81, 0x91, 0xA1, 0xB1, 0xC1, 0xD1, 0xE1, 0xF1,
   0x02, 0x12, 0x22, 0x32, 0x42, 0x52, 0x62, 0x72,
   0x82, 0x92, 0xA2, 0xB2, 0xC2, 0xD2, 0xE2, 0xF2,
   0x03, 0x13, 0x23, 0x33, 0x43, 0x53, 0x63, 0x73,
   0x83, 0x93, 0xA3, 0xB3, 0xC3, 0xD3, 0xE3, 0xF3,
   0x04, 0x14, 0x24, 0x34, 0x44, 0x54, 0x64, 0x74,
   0x84, 0x94, 0xA4, 0xB4, 0xC4, 0xD4, 0xE4, 0xF4,
   0x05, 0x15, 0x25, 0x35, 0x45, 0x55, 0x65, 0x75,
   0x85, 0x95, 0xA5, 0xB5, 0xC5, 0xD5, 0xE5, 0xF5,
   0x06, 0x16, 0x26, 0x36, 0x46, 0x56, 0x66, 0x76,
   0x86, 0x96, 0xA6, 0xB6, 0xC6, 0xD6, 0xE6, 0xF6,
   0x07, 0x17, 0x27, 0x37, 0x47, 0x57, 0x67, 0x77,
   0x87, 0x97, 0xA7, 0xB7, 0xC7, 0xD7, 0xE7, 0xF7,
   0x08, 0x18, 0x28, 0x38, 0x48, 0x58, 0x68, 0x78,
   0x88, 0x98, 0xA8, 0xB8, 0xC8, 0xD8, 0xE8, 0xF8,
   0x09, 0x19, 0x29, 0x39, 0x49, 0x59, 0x69, 0x79,
   0x89, 0x99, 0xA9, 0xB9, 0xC9, 0xD9, 0xE9, 0xF9,
   0x0A, 0x1A, 0x2A, 0x3A, 0x4A, 0x5A, 0x6A, 0x7A,
   0x8A, 0x9A, 0xAA, 0xBA, 0xCA, 0xDA, 0xEA, 0xFA,
   0x0B, 0x1B, 0x2B, 0x3B, 0x4B, 0x5B, 0x6B, 0x7B,
   0x8B, 0x9B, 0xAB, 0xBB, 0xCB, 0xDB, 0xEB, 0xFB,
   0x0C, 0x1C, 0x2C, 0x3C, 0x4C, 0x5C, 0x6C, 0x7C,
   0x8C, 0x9C, 0xAC, 0xBC, 0xCC, 0xDC, 0xEC, 0xFC,
   0x0D, 0x1D, 0x2D, 0x3D, 0x4D, 0x5D, 0x6D, 0x7D,
   0x8D, 0x9D, 0xAD, 0xBD, 0xCD, 0xDD, 0xED, 0xFD,
   0x0E, 0x1E, 0x2E, 0x3E, 0x4E, 0x5E, 0x6E, 0x7E,
   0x8E, 0x9E, 0xAE, 0xBE, 0xCE, 0xDE, 0xEE, 0xFE,
   0x0F, 0x1F, 0x2F, 0x3F, 0x4F, 0x5F, 0x6F, 0x7F,
   0x8F, 0x9F, 0xAF, 0xBF, 0xCF, 0xDF, 0xEF, 0xFF
};

/* swaps pixel packing order within bytes */
void /* PRIVATE */
png_do_packswap(png_row_infop row_info, png_bytep row)
{
   png_debug(1, "in png_do_packswap\n");
   if (
#if defined(PNG_USELESS_TESTS_SUPPORTED)
       row != NULL && row_info != NULL &&
#endif
       row_info->bit_depth < 8)
   {
      png_bytep rp, end, table;

      end = row + row_info->rowbytes;

      if (row_info->bit_depth == 1)
         table = (png_bytep)onebppswaptable;
      else if (row_info->bit_depth == 2)
         table = (png_bytep)twobppswaptable;
      else if (row_info->bit_depth == 4)
         table = (png_bytep)fourbppswaptable;
      else
         return;

      for (rp = row; rp < end; rp++)
         *rp = table[*rp];
   }
}
#endif /* PNG_READ_PACKSWAP_SUPPORTED or PNG_WRITE_PACKSWAP_SUPPORTED */

#if defined(PNG_WRITE_FILLER_SUPPORTED) || \
    defined(PNG_READ_STRIP_ALPHA_SUPPORTED)
/* remove filler or alpha byte(s) */
void /* PRIVATE */
png_do_strip_filler(png_row_infop row_info, png_bytep row, png_uint_32 flags)
{
   png_debug(1, "in png_do_strip_filler\n");
#if defined(PNG_USELESS_TESTS_SUPPORTED)
   if (row != NULL && row_info != NULL)
#endif
   {
      png_bytep sp=row;
      png_bytep dp=row;
      png_uint_32 row_width=row_info->width;
      png_uint_32 i;

      if ((row_info->color_type == PNG_COLOR_TYPE_RGB ||
         (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA &&
         (flags & PNG_FLAG_STRIP_ALPHA))) &&
         row_info->channels == 4)
      {
         if (row_info->bit_depth == 8)
         {
            /* This converts from RGBX or RGBA to RGB */
            if (flags & PNG_FLAG_FILLER_AFTER)
            {
               dp+=3; sp+=4;
               for (i = 1; i < row_width; i++)
               {
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  sp++;
               }
            }
            /* This converts from XRGB or ARGB to RGB */
            else
            {
               for (i = 0; i < row_width; i++)
               {
                  sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
               }
            }
            row_info->pixel_depth = 24;
            row_info->rowbytes = row_width * 3;
         }
         else /* if (row_info->bit_depth == 16) */
         {
            if (flags & PNG_FLAG_FILLER_AFTER)
            {
               /* This converts from RRGGBBXX or RRGGBBAA to RRGGBB */
               sp += 8; dp += 6;
               for (i = 1; i < row_width; i++)
               {
                  /* This could be (although png_memcpy is probably slower):
                  png_memcpy(dp, sp, 6);
                  sp += 8;
                  dp += 6;
                  */

                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  sp += 2;
               }
            }
            else
            {
               /* This converts from XXRRGGBB or AARRGGBB to RRGGBB */
               for (i = 0; i < row_width; i++)
               {
                  /* This could be (although png_memcpy is probably slower):
                  png_memcpy(dp, sp, 6);
                  sp += 8;
                  dp += 6;
                  */

                  sp+=2;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
               }
            }
            row_info->pixel_depth = 48;
            row_info->rowbytes = row_width * 6;
         }
         row_info->channels = 3;
      }
      else if ((row_info->color_type == PNG_COLOR_TYPE_GRAY ||
         (row_info->color_type == PNG_COLOR_TYPE_GRAY_ALPHA &&
         (flags & PNG_FLAG_STRIP_ALPHA))) &&
          row_info->channels == 2)
      {
         if (row_info->bit_depth == 8)
         {
            /* This converts from GX or GA to G */
            if (flags & PNG_FLAG_FILLER_AFTER)
            {
               for (i = 0; i < row_width; i++)
               {
                  *dp++ = *sp++;
                  sp++;
               }
            }
            /* This converts from XG or AG to G */
            else
            {
               for (i = 0; i < row_width; i++)
               {
                  sp++;
                  *dp++ = *sp++;
               }
            }
            row_info->pixel_depth = 8;
            row_info->rowbytes = row_width;
         }
         else /* if (row_info->bit_depth == 16) */
         {
            if (flags & PNG_FLAG_FILLER_AFTER)
            {
               /* This converts from GGXX or GGAA to GG */
               sp += 4; dp += 2;
               for (i = 1; i < row_width; i++)
               {
                  *dp++ = *sp++;
                  *dp++ = *sp++;
                  sp += 2;
               }
            }
            else
            {
               /* This converts from XXGG or AAGG to GG */
               for (i = 0; i < row_width; i++)
               {
                  sp += 2;
                  *dp++ = *sp++;
                  *dp++ = *sp++;
               }
            }
            row_info->pixel_depth = 16;
            row_info->rowbytes = row_width * 2;
         }
         row_info->channels = 1;
      }
      if (flags & PNG_FLAG_STRIP_ALPHA)
        row_info->color_type &= ~PNG_COLOR_MASK_ALPHA;
   }
}
#endif

#if defined(PNG_READ_BGR_SUPPORTED) || defined(PNG_WRITE_BGR_SUPPORTED)
/* swaps red and blue bytes within a pixel */
void /* PRIVATE */
png_do_bgr(png_row_infop row_info, png_bytep row)
{
   png_debug(1, "in png_do_bgr\n");
   if (
#if defined(PNG_USELESS_TESTS_SUPPORTED)
       row != NULL && row_info != NULL &&
#endif
       (row_info->color_type & PNG_COLOR_MASK_COLOR))
   {
      png_uint_32 row_width = row_info->width;
      if (row_info->bit_depth == 8)
      {
         if (row_info->color_type == PNG_COLOR_TYPE_RGB)
         {
            png_bytep rp;
            png_uint_32 i;

            for (i = 0, rp = row; i < row_width; i++, rp += 3)
            {
               png_byte save = *rp;
               *rp = *(rp + 2);
               *(rp + 2) = save;
            }
         }
         else if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
         {
            png_bytep rp;
            png_uint_32 i;

            for (i = 0, rp = row; i < row_width; i++, rp += 4)
            {
               png_byte save = *rp;
               *rp = *(rp + 2);
               *(rp + 2) = save;
            }
         }
      }
      else if (row_info->bit_depth == 16)
      {
         if (row_info->color_type == PNG_COLOR_TYPE_RGB)
         {
            png_bytep rp;
            png_uint_32 i;

            for (i = 0, rp = row; i < row_width; i++, rp += 6)
            {
               png_byte save = *rp;
               *rp = *(rp + 4);
               *(rp + 4) = save;
               save = *(rp + 1);
               *(rp + 1) = *(rp + 5);
               *(rp + 5) = save;
            }
         }
         else if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
         {
            png_bytep rp;
            png_uint_32 i;

            for (i = 0, rp = row; i < row_width; i++, rp += 8)
            {
               png_byte save = *rp;
               *rp = *(rp + 4);
               *(rp + 4) = save;
               save = *(rp + 1);
               *(rp + 1) = *(rp + 5);
               *(rp + 5) = save;
            }
         }
      }
   }
}
#endif /* PNG_READ_BGR_SUPPORTED or PNG_WRITE_BGR_SUPPORTED */

#if defined(PNG_READ_USER_TRANSFORM_SUPPORTED) || \
    defined(PNG_WRITE_USER_TRANSFORM_SUPPORTED) || \
    defined(PNG_LEGACY_SUPPORTED)
void PNGAPI
png_set_user_transform_info(png_structp png_ptr, png_voidp
   user_transform_ptr, int user_transform_depth, int user_transform_channels)
{
   png_debug(1, "in png_set_user_transform_info\n");
   if(png_ptr == NULL) return;
#if defined(PNG_USER_TRANSFORM_PTR_SUPPORTED)
   png_ptr->user_transform_ptr = user_transform_ptr;
   png_ptr->user_transform_depth = (png_byte)user_transform_depth;
   png_ptr->user_transform_channels = (png_byte)user_transform_channels;
#else
   if(user_transform_ptr || user_transform_depth || user_transform_channels)
      png_warning(png_ptr,
        "This version of libpng does not support user transform info");
#endif
}
#endif

/* This function returns a pointer to the user_transform_ptr associated with
 * the user transform functions.  The application should free any memory
 * associated with this pointer before png_write_destroy and png_read_destroy
 * are called.
 */
png_voidp PNGAPI
png_get_user_transform_ptr(png_structp png_ptr)
{
#if defined(PNG_USER_TRANSFORM_PTR_SUPPORTED)
   if (png_ptr == NULL) return (NULL);
   return ((png_voidp)png_ptr->user_transform_ptr);
#else
   return (NULL);
#endif
}
#endif /* PNG_READ_SUPPORTED || PNG_WRITE_SUPPORTED */


#include "CommonTools/RecoAlgos/src/MassiveCandidateConverter.h"
#include "FWCore/ParameterSet/interface/ParameterSet.h"
#include "HepPDT/ParticleData.hh"
#include "FWCore/Framework/interface/ESHandle.h"
#include <algorithm>
using namespace edm;
using namespace std;
using namespace converter;

MassiveCandidateConverter::MassiveCandidateConverter(const edm::ParameterSet& cfg)
    : massSqr_(0), particle_(cfg.getParameter<PdtEntry>("particleType")) {}

void MassiveCandidateConverter::beginFirstRun(const EventSetup& es) {
  particle_.setup(es);
  massSqr_ = particle_.data().mass();
  massSqr_ *= massSqr_;
}


/*
 * CoreShop.
 *
 * This source file is subject to the GNU General Public License version 3 (GPLv3)
 * For the full copyright and license information, please view the LICENSE.md and gpl-3.0.txt
 * files that are distributed with this source code.
 *
 * @copyright  Copyright (c) 2015-2020 Dominik Pfaffenbauer (https://www.pfaffenbauer.at)
 * @license    https://www.coreshop.org/license     GNU General Public License version 3 (GPLv3)
 *
 */

pimcore.registerNS('coreshop.product.pricerule.conditions.quantity');
coreshop.product.pricerule.conditions.quantity = Class.create(coreshop.rules.conditions.abstract, {
    type: 'quantity',

    getForm: function () {

        var minQuantityValue = null;
        var maxQuantityValue = 0;
        var currencyValue = null;
        var me = this;

        if (this.data && this.data.minQuantity) {
            minQuantityValue = this.data.minQuantity;
        }

        if (this.data && this.data.maxQuantity) {
            maxQuantityValue = this.data.maxQuantity;
        }

        var minQuantity = new Ext.form.NumberField({
            fieldLabel: t('coreshop_condition_quantity_minQuantity'),
            name: 'minQuantity',
            value: minQuantityValue,
            minValue: 0,
            decimalPrecision: 0,
            step: 1
        });

        var maxQuantity = new Ext.form.NumberField({
            fieldLabel: t('coreshop_condition_quantity_maxQuantity'),
            name: 'maxQuantity',
            value: maxQuantityValue,
            minValue: 0,
            decimalPrecision: 0,
            step: 1
        });

        this.form = Ext.create('Ext.form.Panel', {
            items: [
                minQuantity, maxQuantity
            ]
        });

        return this.form;
    }
});


<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
	<key>BuildMachineOSBuild</key>
	<string>16G29</string>
	<key>CFBundleDevelopmentRegion</key>
	<string>en</string>
	<key>CFBundleExecutable</key>
	<string>Lilu</string>
	<key>CFBundleIdentifier</key>
	<string>as.vit9696.Lilu</string>
	<key>CFBundleInfoDictionaryVersion</key>
	<string>6.0</string>
	<key>CFBundleName</key>
	<string>Lilu</string>
	<key>CFBundlePackageType</key>
	<string>KEXT</string>
	<key>CFBundleShortVersionString</key>
	<string>1.1.7</string>
	<key>CFBundleSignature</key>
	<string>????</string>
	<key>CFBundleSupportedPlatforms</key>
	<array>
		<string>MacOSX</string>
	</array>
	<key>CFBundleVersion</key>
	<string>1.1.7</string>
	<key>DTCompiler</key>
	<string>com.apple.compilers.llvm.clang.1_0</string>
	<key>DTPlatformBuild</key>
	<string>8E3004b</string>
	<key>DTPlatformVersion</key>
	<string>GM</string>
	<key>DTSDKBuild</key>
	<string>16E185</string>
	<key>DTSDKName</key>
	<string>macosx10.12</string>
	<key>DTXcode</key>
	<string>0833</string>
	<key>DTXcodeBuild</key>
	<string>8E3004b</string>
	<key>IOKitPersonalities</key>
	<dict>
		<key>as.vit9696.Lilu</key>
		<dict>
			<key>CFBundleIdentifier</key>
			<string>as.vit9696.Lilu</string>
			<key>IOClass</key>
			<string>Lilu</string>
			<key>IOMatchCategory</key>
			<string>Lilu</string>
			<key>IOProviderClass</key>
			<string>IOResources</string>
			<key>IOResourceMatch</key>
			<string>IOKit</string>
		</dict>
	</dict>
	<key>NSHumanReadableCopyright</key>
	<string>Copyright © 2016-2017 vit9696. All rights reserved.</string>
	<key>OSBundleCompatibleVersion</key>
	<string>1.1.0</string>
	<key>OSBundleLibraries</key>
	<dict>
		<key>com.apple.kpi.bsd</key>
		<string>12.0.0</string>
		<key>com.apple.kpi.dsep</key>
		<string>12.0.0</string>
		<key>com.apple.kpi.iokit</key>
		<string>12.0.0</string>
		<key>com.apple.kpi.libkern</key>
		<string>12.0.0</string>
		<key>com.apple.kpi.mach</key>
		<string>12.0.0</string>
		<key>com.apple.kpi.unsupported</key>
		<string>12.0.0</string>
	</dict>
	<key>OSBundleRequired</key>
	<string>Root</string>
</dict>
</plist>


/*Package sql2struct ...
@Time : 2020/1/7 11:04
@Software: GoLand
@File : xorm_tag
@Author : Bingo <airplayx@gmail.com>
*/
package sql2struct

import (
	"github.com/xormplus/xorm/schemas"
	"sort"
	"strings"

	"github.com/xormplus/core"
)

var created = []string{"created_at"}
var updated = []string{"updated_at"}
var deleted = []string{"deleted_at"}

//GetXormTag ...
func GetXormTag(table *schemas.Table, col *schemas.Column) string {
	isNameID := col.Name == table.AutoIncrement
	isIDPk := isNameID && sqlType2TypeString(col.SQLType) == "int64"

	var res []string
	if !col.Nullable {
		if !isIDPk {
			res = append(res, "not null")
		}
	}

	if col.IsPrimaryKey {
		res = append(res, "pk")
	}

	if len(col.Default) >= 4 && strings.HasPrefix(col.Default, "''") && strings.HasSuffix(col.Default, "''") {
		col.Default = col.Default[1 : len(col.Default)-1]
	}
	if col.Default != "" {
		res = append(res, "default "+col.Default)
	}

	if col.IsAutoIncrement {
		res = append(res, "autoincr")
	}

	if col.SQLType.IsTime() && inStringSlice(col.Name, created) {
		res = append(res, "created")
	}

	if col.SQLType.IsTime() && inStringSlice(col.Name, updated) {
		res = append(res, "updated")
	}

	if col.SQLType.IsTime() && inStringSlice(col.Name, deleted) {
		res = append(res, "deleted")
	}

	names := make([]string, 0, len(col.Indexes))
	for name := range col.Indexes {
		names = append(names, name)
	}
	sort.Strings(names)

	for _, name := range names {
		index := table.Indexes[name]
		var uistr string
		if index.Type == core.UniqueType {
			uistr = "unique"
		} else if index.Type == core.IndexType {
			uistr = "index"
		}
		if len(index.Cols) > 1 {
			uistr += "(" + index.Name + ")"
		}
		res = append(res, uistr)
	}

	res = append(res, Engine.SQLType(col))

	if len(res) > 0 {
		return "xorm:\"" + strings.Join(res, " ") + "\""
	}

	return ""
}


extern crate raylib;
use raylib::prelude::*;
use std::{thread, time};
use structopt::StructOpt;

mod options;

fn main() {
    let opt = options::Opt::from_args();
    test_shader_dropping(&opt);
    test_model_dropping(&opt);
    test_audio_dropping(&opt);
    test_font_dropping(&opt);
}

/// Checks that shader files are droppable after window is closed
fn test_shader_dropping(opt: &options::Opt) {
    let _ten_millis = time::Duration::from_millis(10);
    let _v = {
        let (mut rl, thread) = opt.open_window("Drop Shader");
        rl.load_shader(&thread, None, Some("static/shader/pbr.fs"))
            .expect("shader didn't load")
    };
}

/// Checks that model files are droppable after window is closed
fn test_model_dropping(opt: &options::Opt) {
    let ten_millis = time::Duration::from_millis(10);
    let _m = {
        let (mut rl, thread) = opt.open_window("Drop Model");
        rl.load_model(&thread, "static/pbr/trooper.obj")
            .expect("couldn't load model");
    };
    thread::sleep(ten_millis);
    // Uncomment when we have actual meshes to unload
    // let mesh = {
    //     let (_rl, thread) = opt.open_window("Drop Mesh");
    //     Mesh::load_meshes(&thread, "static/pbr/trooper.obj").expect("couldn't load mesh");
    // };
    let _anim = {
        let (mut rl, thread) = opt.open_window("Drop Anim");
        rl.load_model_animations(&thread, "static/guy/guy.iqm")
            .expect("couldn't load model");
    };

    thread::sleep(ten_millis);
}

/// Checks that audio files are droppable after window is closed
fn test_audio_dropping(opt: &options::Opt) {
    let ten_millis = time::Duration::from_millis(10);
    let _w = {
        let (_, _thread) = raylib::init()
            .size(opt.width, opt.height)
            .title("Drop")
            .build();
        Wave::load_wave("static/wave.ogg").expect("couldn't load wave");
    };
    thread::sleep(ten_millis);
    let _s = {
        let (_rl, _thread) = opt.open_window("Drop Sound");
        Sound::load_sound("static/wave.ogg").expect("couldn't load wave");
    };
    thread::sleep(ten_millis);
    // Broken on mac
    // let m = {
    //     let (_rl, thread) = opt.open_window("Drop Sound");
    //     // let m = Music::load_music_stream(&thread, "static/wave.ogg");
    //     let m = Music::load_music_stream(&thread, "static/wave.ogg").expect("couldn't load music");
    //     println!("music {:?}", m);
    //     drop(m);
    //     ()
    // };
    // thread::sleep(ten_millis);
}

/// checks that fonts can be dropped after window is closed
fn test_font_dropping(opt: &options::Opt) {
    let _f = {
        let (mut rl, thread) = raylib::init()
            .size(opt.width, opt.height)
            .title("Drop")
            .build();
        rl.load_font(&thread, "static/alagard.png")
            .expect("couldn't load font");
    };
    let ten_millis = time::Duration::from_millis(10);
    thread::sleep(ten_millis);
}


<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

    <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
	<title>How Do I?</title>
	<link rel="stylesheet" href="../shared/helpstyle.css" type="text/css"/>

  How Do I?

Below are some of the more common questions asked about Vienna while it was being pre-release tested.
See the Official Vienna FAQ Page for these
and the latest hints and tips for using Vienna.

Where do I get
the Vienna source code?

I
found a problem with Vienna. How do I report it?

How do I create my own
styles?

How do I create my own
scripts?

How can I see what happened when my subscriptions are refreshed?

How do
I move my Vienna database to another folder?

One of my subscriptions reports "Error parsing XML data in feed".
What does this mean?

Is there a shortcut key for going to the next article, marking read,
etc?

What do the green dots mean in the list of articles?

How do I use
Auto Expire and what does it do?

How do I
request an enhancement in Vienna?

Where do I get the
Vienna source code?

See the Development page for
instructions for getting the source code for Vienna. The source code is
freely available if you're interested in learning how Vienna works, if
you want to build your own copy of Vienna from scratch on your own
machine or if you want to borrow portions for inclusion in your own
project. The source is provided under the
Apache 2.0
license.

I found
a problem with Vienna. How do I report it?

Post a message over in the
Support forum and somebody will
investigate. Provide as much information about the problem as you can
including: the build of Vienna (obtained from the About Vienna panel),
repro steps and what you expected to happen. There is a sticky note in
the forum with tips on how to write a good bug report.

Make sure you're always running the most recent build of Vienna. The
Check for Updates command will report if there's a newer build available
than the one you have.

Fixes for bugs take priority over new features so if your problem is
confirmed to be a bug with high impact and no simple workaround then
I'll look at making a fix available as soon as reasonably possible.

How do I create my own
styles?

See the Custom Styles page for
instructions.

How do I create my own
scripts?

Vienna's scripts are written using AppleScript. See the

Apple resource page for more details.

One way to get started is to download one of the existing scripts
from the Vienna Downloads page and view
it in the AppleScript editor.

To submit your own script, send it to
steve@opencommunity.co.uk
and after it has been reviewed, it will be made available on the
Downloads page.

How can I see what happened when my subscriptions are refreshed?

Open the Activity Window from the Window menu. The activity window
shows all subscriptions and the status of the last time they were
refreshed in that session. The bottom of the activity window shows more
details include the HTTP headers and may be useful for debugging. (If
the details pane is not visible, grab the split bar at the bottom of the
Activity Window and drag it up to uncover the pane).

How do
I move my Vienna database to another folder?

By default, your Vienna database is the messages.db file which is
located at ~/Library/Application Support/Vienna. You can move this to
another folder if you wish. The following steps show how:

Shut down Vienna.

Open a console window and enter:

defaults write uk.co.opencommunity.vienna2
"DefaultDatabase" '<path to new messages.db>'

where <path to new messages.db> is the name of the folder that
contains the messages.db file. The path itself should have the
messages.db filename at the end. For example:

defaults write uk.co.opencommunity.vienna2
"DefaultDatabase" '/Users/steve/mydata/messages.db'

Restart Vienna.

One of my subscriptions reports "Error parsing XML data in feed". What
does this mean?

It means that Vienna got a feed back from the subscription that it
couldn't interpret. There are several reasons for this:

The URL of the feed may not be pointing to an RSS or Atom feed
but to a web page. Check the URL of the offending feed carefully.

The feed itself may contain malformed XML. Some subscriptions
make a mistake in putting together the XML that makes up the feed
and Vienna cannot interpret malformed XML. Use the Validate Feed
command on the File menu to see if this is the case. Unfortunately
you cannot do much about this in Vienna except wait for the feed
itself to be corrected by the site.

The feed may be incomplete. If the refresh was interrupted then
the XML data will be incomplete and will appear malformed in Vienna.
A second refresh may correct this problem.

If none of the above explain the problem, post a message on the
support forum with the URL of the feed exhibiting the problem.

Is there a shortcut key for going to the next article, marking read,
etc?

Probably. There are single key equivalents for some of the menu
commands such as:

Spacebar - goes to the next unread article. If the current article is
several pages long, it will scroll through that article first. If you're
at the end of the current article it will then go to the next unread
article. By contrast the Next Unread command (Cmd+U) always goes
straight to the next unread article.

R - marks the current article read if it is unread, or unread if it
is read.

F - flags the current article if it isn't already flagged, or removes
the existing flag if it is not.

Look in the Vienna Help file for more shortcuts.

What do
the green dots mean in the list of articles?

The blue dots are for new articles, and the green dots are for updated articles:
articles whose text has changed since they were last downloaded.

How do I use
Auto Expire and what does it do?

Auto-expire moves articles older than a certain number of days to the
Trash folder. It allows you to keep your folders manageable by only
retaining articles that are recent. The auto-expire runs both when
Vienna starts and after you have refreshed any subscriptions. To control
the age of articles to auto-expire, change the
"Move articles to Trash" option in Preferences.

Auto-expire will NOT remove unread or flagged articles. It assumes
that you haven't read these articles and thus leaves them alone.

How do I request
an enhancement in Vienna?

Post a message over at the
support forum. All
requested enhancements are logged in the TODO file that is included with
the source code as a guidance for future developers.


package info.nightscout.androidaps.events

class EventReloadTempBasalData : Event()


/* Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.activiti.engine.impl.cmd;

import java.io.Serializable;

import org.activiti.engine.ActivitiIllegalArgumentException;
import org.activiti.engine.impl.interceptor.Command;
import org.activiti.engine.impl.interceptor.CommandContext;

/**
 * @author Joram Barrez
 */
public class DeleteProcessInstanceCmd implements Command<Void>, Serializable {

    private static final long serialVersionUID = 1L;
    protected String processInstanceId;
    protected String deleteReason;

    public DeleteProcessInstanceCmd(String processInstanceId, String deleteReason) {
        this.processInstanceId = processInstanceId;
        this.deleteReason = deleteReason;
    }

    @Override
    public Void execute(CommandContext commandContext) {
        if (processInstanceId == null) {
            throw new ActivitiIllegalArgumentException("processInstanceId is null");
        }

        commandContext
                .getExecutionEntityManager()
                .deleteProcessInstance(processInstanceId, deleteReason);
        return null;
    }

}


jQuery.ajaxPrefilter(function( options, originalOptions, jqXHR ) {
	if ( options.retry ) {
		var url = options.url,
			oldPromise = jqXHR.promise();
		if ( options._retried ) {
			options.success = options.error = options.complete = undefined;
		} else {
			originalOptions = jQuery.extend( {}, originalOptions, { _retried: true } );
		}
		jqXHR.pipe( null, function() {
			if ( options.retry.call( options.context || options, originalOptions, jqXHR ) ) {
				return jQuery.ajax( originalOptions.url || url, originalOptions );
			}
			return oldPromise;
		}).promise( jqXHR );
		if ( jqXHR.success ) {
			jqXHR.success = jqXHR.done;
			jqXHR.error = jqXHR.fail;
			jqXHR.complete = (function( callbacks ) {
				jqXHR.always(function( error, statusText, success ) {
					callbacks.fireWith( this, [ jqXHR.state() === "resolved" ? success : error ] );
				});
				return callbacks.add;
			})( jQuery.Callbacks( "once memory" ) );
		}
	}
});


/**
 * Copyright (c) 2015-present, Facebook, Inc.
 * All rights reserved.
 *
 * This source code is licensed under the BSD-style license found in the
 * LICENSE file in the root directory of this source tree. An additional grant
 * of patent rights can be found in the PATENTS file in the same directory.
 *
 * @providesModule StyleSheetValidation
 * @flow
 */
'use strict';

var ImageStylePropTypes = require('ImageStylePropTypes');
var TextStylePropTypes = require('TextStylePropTypes');
var ViewStylePropTypes = require('ViewStylePropTypes');

var invariant = require('fbjs/lib/invariant');

// Hardcoded because this is a legit case but we don't want to load it from
// a private API. We might likely want to unify style sheet creation with how it
// is done in the DOM so this might move into React. I know what I'm doing so
// plz don't fire me.
const ReactPropTypesSecret = 'SECRET_DO_NOT_PASS_THIS_OR_YOU_WILL_BE_FIRED';

class StyleSheetValidation {
  static validateStyleProp(prop: string, style: Object, caller: string) {
    if (!__DEV__) {
      return;
    }
    if (allStylePropTypes[prop] === undefined) {
      var message1 = '"' + prop + '" is not a valid style property.';
      var message2 = '\nValid style props: ' +
        JSON.stringify(Object.keys(allStylePropTypes).sort(), null, '  ');
      styleError(message1, style, caller, message2);
    }
    var error = allStylePropTypes[prop](
      style,
      prop,
      caller,
      'prop',
      null,
      ReactPropTypesSecret,
    );
    if (error) {
      styleError(error.message, style, caller);
    }
  }

  static validateStyle(name: string, styles: Object) {
    if (!__DEV__) {
      return;
    }
    for (var prop in styles[name]) {
      StyleSheetValidation.validateStyleProp(prop, styles[name], 'StyleSheet ' + name);
    }
  }

  static addValidStylePropTypes(stylePropTypes) {
    for (var key in stylePropTypes) {
      allStylePropTypes[key] = stylePropTypes[key];
    }
  }
}

var styleError = function(message1, style, caller?, message2?) {
  invariant(
    false,
    message1 + '\n' + (caller || '<<unknown>>') + ': ' +
    JSON.stringify(style, null, '  ') + (message2 || '')
  );
};

var allStylePropTypes = {};

StyleSheetValidation.addValidStylePropTypes(ImageStylePropTypes);
StyleSheetValidation.addValidStylePropTypes(TextStylePropTypes);
StyleSheetValidation.addValidStylePropTypes(ViewStylePropTypes);

module.exports = StyleSheetValidation;


//
//     Generated by class-dump 3.5 (64 bit) (Debug version compiled Jun  9 2015 22:53:21).
//
//     class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2014 by Steve Nygard.
//

#import <objc/NSObject.h>

#import "QLPreviewViewDelegate-Protocol.h"

@class NSMutableArray, NSMutableDictionary, NSString, SPWebPreviewCacheItem;
@protocol OS_dispatch_queue;

@interface SPWebPreviewCache : NSObject <QLPreviewViewDelegate>
{
    int _generation;
    int _lastRow;
    id _delegate;
    NSMutableDictionary *_cachedPreviewItems;
    NSMutableArray *_reuseableCacheItems;
    NSMutableArray *_livePreviewCacheItems;
    SPWebPreviewCacheItem *_currentLoadItem;
    NSObject<OS_dispatch_queue> *_preheatQueue;
    NSObject<OS_dispatch_queue> *_submissionQueue;
}

@property int lastRow; // @synthesize lastRow=_lastRow;
@property(retain) NSObject<OS_dispatch_queue> *submissionQueue; // @synthesize submissionQueue=_submissionQueue;
@property(retain) NSObject<OS_dispatch_queue> *preheatQueue; // @synthesize preheatQueue=_preheatQueue;
@property(retain) SPWebPreviewCacheItem *currentLoadItem; // @synthesize currentLoadItem=_currentLoadItem;
@property(retain) NSMutableArray *livePreviewCacheItems; // @synthesize livePreviewCacheItems=_livePreviewCacheItems;
@property(retain) NSMutableArray *reuseableCacheItems; // @synthesize reuseableCacheItems=_reuseableCacheItems;
@property(retain) NSMutableDictionary *cachedPreviewItems; // @synthesize cachedPreviewItems=_cachedPreviewItems;
@property __weak id delegate; // @synthesize delegate=_delegate;
- (void).cxx_destruct;
- (BOOL)forceLoadItem:(id)arg1;
- (id)previewForItem:(id)arg1;
- (void)previewView:(id)arg1 didLoadPreviewItem:(id)arg2;
- (void)preheat:(id)arg1 row:(int)arg2 generation:(int)arg3;
- (void)submit:(id)arg1;
- (id)cachelookup:(id)arg1;
- (void)addPreviewItem:(id)arg1;
- (void)cacheinsert:(id)arg1;
- (id)getPreviewView;
- (void)clearCache:(int)arg1 forcePreserve:(id)arg2;
- (id)init;

// Remaining properties
@property(readonly, copy) NSString *debugDescription;
@property(readonly, copy) NSString *description;
@property(readonly) unsigned long long hash;
@property(readonly) Class superclass;

@end


#!/usr/bin/env node

var argv = require('optimist')
    .usage('Usage: $0 -x [num] -y [num]')
    .demand(['x','y'])
    .argv;

console.log(argv.x / argv.y);