// mojo/public/interfaces/bindings/tests/test_native_types.mojom.js is auto generated by mojom_bindings_generator.py, do not edit

// Copyright 2014 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

'use strict';

(function() {
  var mojomId = 'mojo/public/interfaces/bindings/tests/test_native_types.mojom';
  if (mojo.internal.isMojomLoaded(mojomId)) {
    console.warn('The following mojom is loaded multiple times: ' + mojomId);
    return;
  }
  mojo.internal.markMojomLoaded(mojomId);
  var bindings = mojo;
  var associatedBindings = mojo;
  var codec = mojo.internal;
  var validator = mojo.internal;

  var exports = mojo.internal.exposeNamespace('mojo.test');
  var rect$ =
      mojo.internal.exposeNamespace('mojo.test');
  if (mojo.config.autoLoadMojomDeps) {
    mojo.internal.loadMojomIfNecessary(
        'mojo/public/interfaces/bindings/tests/rect.mojom', 'rect.mojom.js');
  }


  var PickledEnum = {};

  PickledEnum.isKnownEnumValue = function(value) {
    return false;
  };

  PickledEnum.toKnownEnumValue = function(value) {
    return value;
  };

  PickledEnum.validate = function(enumValue) {
    const isExtensible = false;
    if (isExtensible || this.isKnownEnumValue(enumValue))
      return validator.validationError.NONE;

    return validator.validationError.UNKNOWN_ENUM_VALUE;
  };

  function PickledStruct(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PickledStruct.prototype.initDefaults_ = function() {
  };
  PickledStruct.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PickledStruct.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 8}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PickledStruct.encodedSize = codec.kStructHeaderSize + 0;

  PickledStruct.decode = function(decoder) {
    var packed;
    var val = new PickledStruct();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    return val;
  };

  PickledStruct.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PickledStruct.encodedSize);
    encoder.writeUint32(0);
  };
  function PickleContainer(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PickleContainer.prototype.initDefaults_ = function() {
    this.fStruct = null;
    this.fEnum = 0;
  };
  PickleContainer.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PickleContainer.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 24}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PickleContainer.fStruct
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, PickledStruct, false);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PickleContainer.fEnum
    err = messageValidator.validateEnum(offset + codec.kStructHeaderSize + 8, PickledEnum);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PickleContainer.encodedSize = codec.kStructHeaderSize + 16;

  PickleContainer.decode = function(decoder) {
    var packed;
    var val = new PickleContainer();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.fStruct =
        decoder.decodeStructPointer(PickledStruct);
    val.fEnum =
        decoder.decodeStruct(new codec.Enum(PickledEnum));
    decoder.skip(1);
    decoder.skip(1);
    decoder.skip(1);
    decoder.skip(1);
    return val;
  };

  PickleContainer.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PickleContainer.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(PickledStruct, val.fStruct);
    encoder.encodeStruct(codec.Int32, val.fEnum);
    encoder.skip(1);
    encoder.skip(1);
    encoder.skip(1);
    encoder.skip(1);
  };
  function TestNativeStructMojom(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  TestNativeStructMojom.prototype.initDefaults_ = function() {
  };
  TestNativeStructMojom.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  TestNativeStructMojom.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 8}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  TestNativeStructMojom.encodedSize = codec.kStructHeaderSize + 0;

  TestNativeStructMojom.decode = function(decoder) {
    var packed;
    var val = new TestNativeStructMojom();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    return val;
  };

  TestNativeStructMojom.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(TestNativeStructMojom.encodedSize);
    encoder.writeUint32(0);
  };
  function TestNativeStructWithAttachmentsMojom(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  TestNativeStructWithAttachmentsMojom.prototype.initDefaults_ = function() {
  };
  TestNativeStructWithAttachmentsMojom.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  TestNativeStructWithAttachmentsMojom.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 8}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  TestNativeStructWithAttachmentsMojom.encodedSize = codec.kStructHeaderSize + 0;

  TestNativeStructWithAttachmentsMojom.decode = function(decoder) {
    var packed;
    var val = new TestNativeStructWithAttachmentsMojom();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    return val;
  };

  TestNativeStructWithAttachmentsMojom.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(TestNativeStructWithAttachmentsMojom.encodedSize);
    encoder.writeUint32(0);
  };
  function PicklePasser_PassPickledStruct_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickledStruct_Params.prototype.initDefaults_ = function() {
    this.pickle = null;
  };
  PicklePasser_PassPickledStruct_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickledStruct_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickledStruct_Params.pickle
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, PickledStruct, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickledStruct_Params.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickledStruct_Params.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickledStruct_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.pickle =
        decoder.decodeStructPointer(PickledStruct);
    return val;
  };

  PicklePasser_PassPickledStruct_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickledStruct_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(PickledStruct, val.pickle);
  };
  function PicklePasser_PassPickledStruct_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickledStruct_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = null;
  };
  PicklePasser_PassPickledStruct_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickledStruct_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickledStruct_ResponseParams.passed
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, PickledStruct, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickledStruct_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickledStruct_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickledStruct_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeStructPointer(PickledStruct);
    return val;
  };

  PicklePasser_PassPickledStruct_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickledStruct_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(PickledStruct, val.passed);
  };
  function PicklePasser_PassPickledEnum_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickledEnum_Params.prototype.initDefaults_ = function() {
    this.pickle = 0;
  };
  PicklePasser_PassPickledEnum_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickledEnum_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickledEnum_Params.pickle
    err = messageValidator.validateEnum(offset + codec.kStructHeaderSize + 0, PickledEnum);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickledEnum_Params.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickledEnum_Params.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickledEnum_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.pickle =
        decoder.decodeStruct(new codec.Enum(PickledEnum));
    decoder.skip(1);
    decoder.skip(1);
    decoder.skip(1);
    decoder.skip(1);
    return val;
  };

  PicklePasser_PassPickledEnum_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickledEnum_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStruct(codec.Int32, val.pickle);
    encoder.skip(1);
    encoder.skip(1);
    encoder.skip(1);
    encoder.skip(1);
  };
  function PicklePasser_PassPickledEnum_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickledEnum_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = 0;
  };
  PicklePasser_PassPickledEnum_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickledEnum_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickledEnum_ResponseParams.passed
    err = messageValidator.validateEnum(offset + codec.kStructHeaderSize + 0, PickledEnum);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickledEnum_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickledEnum_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickledEnum_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeStruct(new codec.Enum(PickledEnum));
    decoder.skip(1);
    decoder.skip(1);
    decoder.skip(1);
    decoder.skip(1);
    return val;
  };

  PicklePasser_PassPickledEnum_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickledEnum_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStruct(codec.Int32, val.passed);
    encoder.skip(1);
    encoder.skip(1);
    encoder.skip(1);
    encoder.skip(1);
  };
  function PicklePasser_PassPickleContainer_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickleContainer_Params.prototype.initDefaults_ = function() {
    this.container = null;
  };
  PicklePasser_PassPickleContainer_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickleContainer_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickleContainer_Params.container
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, PickleContainer, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickleContainer_Params.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickleContainer_Params.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickleContainer_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.container =
        decoder.decodeStructPointer(PickleContainer);
    return val;
  };

  PicklePasser_PassPickleContainer_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickleContainer_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(PickleContainer, val.container);
  };
  function PicklePasser_PassPickleContainer_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickleContainer_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = null;
  };
  PicklePasser_PassPickleContainer_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickleContainer_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickleContainer_ResponseParams.passed
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, PickleContainer, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickleContainer_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickleContainer_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickleContainer_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeStructPointer(PickleContainer);
    return val;
  };

  PicklePasser_PassPickleContainer_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickleContainer_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(PickleContainer, val.passed);
  };
  function PicklePasser_PassPickles_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickles_Params.prototype.initDefaults_ = function() {
    this.pickles = null;
  };
  PicklePasser_PassPickles_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickles_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickles_Params.pickles
    err = messageValidator.validateArrayPointer(offset + codec.kStructHeaderSize + 0, 8, new codec.PointerTo(PickledStruct), false, [0], 0);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickles_Params.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickles_Params.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickles_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.pickles =
        decoder.decodeArrayPointer(new codec.PointerTo(PickledStruct));
    return val;
  };

  PicklePasser_PassPickles_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickles_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeArrayPointer(new codec.PointerTo(PickledStruct), val.pickles);
  };
  function PicklePasser_PassPickles_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickles_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = null;
  };
  PicklePasser_PassPickles_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickles_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickles_ResponseParams.passed
    err = messageValidator.validateArrayPointer(offset + codec.kStructHeaderSize + 0, 8, new codec.PointerTo(PickledStruct), false, [0], 0);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickles_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickles_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickles_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeArrayPointer(new codec.PointerTo(PickledStruct));
    return val;
  };

  PicklePasser_PassPickles_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickles_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeArrayPointer(new codec.PointerTo(PickledStruct), val.passed);
  };
  function PicklePasser_PassPickleArrays_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickleArrays_Params.prototype.initDefaults_ = function() {
    this.pickleArrays = null;
  };
  PicklePasser_PassPickleArrays_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickleArrays_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickleArrays_Params.pickleArrays
    err = messageValidator.validateArrayPointer(offset + codec.kStructHeaderSize + 0, 8, new codec.ArrayOf(new codec.PointerTo(PickledStruct)), false, [0, 0], 0);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickleArrays_Params.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickleArrays_Params.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickleArrays_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.pickleArrays =
        decoder.decodeArrayPointer(new codec.ArrayOf(new codec.PointerTo(PickledStruct)));
    return val;
  };

  PicklePasser_PassPickleArrays_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickleArrays_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeArrayPointer(new codec.ArrayOf(new codec.PointerTo(PickledStruct)), val.pickleArrays);
  };
  function PicklePasser_PassPickleArrays_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  PicklePasser_PassPickleArrays_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = null;
  };
  PicklePasser_PassPickleArrays_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  PicklePasser_PassPickleArrays_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate PicklePasser_PassPickleArrays_ResponseParams.passed
    err = messageValidator.validateArrayPointer(offset + codec.kStructHeaderSize + 0, 8, new codec.ArrayOf(new codec.PointerTo(PickledStruct)), false, [0, 0], 0);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  PicklePasser_PassPickleArrays_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  PicklePasser_PassPickleArrays_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new PicklePasser_PassPickleArrays_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeArrayPointer(new codec.ArrayOf(new codec.PointerTo(PickledStruct)));
    return val;
  };

  PicklePasser_PassPickleArrays_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(PicklePasser_PassPickleArrays_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeArrayPointer(new codec.ArrayOf(new codec.PointerTo(PickledStruct)), val.passed);
  };
  function RectService_AddRect_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  RectService_AddRect_Params.prototype.initDefaults_ = function() {
    this.r = null;
  };
  RectService_AddRect_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  RectService_AddRect_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate RectService_AddRect_Params.r
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, rect$.TypemappedRect, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  RectService_AddRect_Params.encodedSize = codec.kStructHeaderSize + 8;

  RectService_AddRect_Params.decode = function(decoder) {
    var packed;
    var val = new RectService_AddRect_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.r =
        decoder.decodeStructPointer(rect$.TypemappedRect);
    return val;
  };

  RectService_AddRect_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(RectService_AddRect_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(rect$.TypemappedRect, val.r);
  };
  function RectService_GetLargestRect_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  RectService_GetLargestRect_Params.prototype.initDefaults_ = function() {
  };
  RectService_GetLargestRect_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  RectService_GetLargestRect_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 8}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  RectService_GetLargestRect_Params.encodedSize = codec.kStructHeaderSize + 0;

  RectService_GetLargestRect_Params.decode = function(decoder) {
    var packed;
    var val = new RectService_GetLargestRect_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    return val;
  };

  RectService_GetLargestRect_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(RectService_GetLargestRect_Params.encodedSize);
    encoder.writeUint32(0);
  };
  function RectService_GetLargestRect_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  RectService_GetLargestRect_ResponseParams.prototype.initDefaults_ = function() {
    this.largest = null;
  };
  RectService_GetLargestRect_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  RectService_GetLargestRect_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate RectService_GetLargestRect_ResponseParams.largest
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, rect$.TypemappedRect, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  RectService_GetLargestRect_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  RectService_GetLargestRect_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new RectService_GetLargestRect_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.largest =
        decoder.decodeStructPointer(rect$.TypemappedRect);
    return val;
  };

  RectService_GetLargestRect_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(RectService_GetLargestRect_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(rect$.TypemappedRect, val.largest);
  };
  function RectService_PassSharedRect_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  RectService_PassSharedRect_Params.prototype.initDefaults_ = function() {
    this.r = null;
  };
  RectService_PassSharedRect_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  RectService_PassSharedRect_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate RectService_PassSharedRect_Params.r
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, rect$.SharedTypemappedRect, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  RectService_PassSharedRect_Params.encodedSize = codec.kStructHeaderSize + 8;

  RectService_PassSharedRect_Params.decode = function(decoder) {
    var packed;
    var val = new RectService_PassSharedRect_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.r =
        decoder.decodeStructPointer(rect$.SharedTypemappedRect);
    return val;
  };

  RectService_PassSharedRect_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(RectService_PassSharedRect_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(rect$.SharedTypemappedRect, val.r);
  };
  function RectService_PassSharedRect_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  RectService_PassSharedRect_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = null;
  };
  RectService_PassSharedRect_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  RectService_PassSharedRect_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate RectService_PassSharedRect_ResponseParams.passed
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, rect$.SharedTypemappedRect, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  RectService_PassSharedRect_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  RectService_PassSharedRect_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new RectService_PassSharedRect_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeStructPointer(rect$.SharedTypemappedRect);
    return val;
  };

  RectService_PassSharedRect_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(RectService_PassSharedRect_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(rect$.SharedTypemappedRect, val.passed);
  };
  function NativeTypeTester_PassNativeStruct_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  NativeTypeTester_PassNativeStruct_Params.prototype.initDefaults_ = function() {
    this.s = null;
  };
  NativeTypeTester_PassNativeStruct_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  NativeTypeTester_PassNativeStruct_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate NativeTypeTester_PassNativeStruct_Params.s
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, TestNativeStructMojom, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  NativeTypeTester_PassNativeStruct_Params.encodedSize = codec.kStructHeaderSize + 8;

  NativeTypeTester_PassNativeStruct_Params.decode = function(decoder) {
    var packed;
    var val = new NativeTypeTester_PassNativeStruct_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.s =
        decoder.decodeStructPointer(TestNativeStructMojom);
    return val;
  };

  NativeTypeTester_PassNativeStruct_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(NativeTypeTester_PassNativeStruct_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(TestNativeStructMojom, val.s);
  };
  function NativeTypeTester_PassNativeStruct_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  NativeTypeTester_PassNativeStruct_ResponseParams.prototype.initDefaults_ = function() {
    this.passed = null;
  };
  NativeTypeTester_PassNativeStruct_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  NativeTypeTester_PassNativeStruct_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate NativeTypeTester_PassNativeStruct_ResponseParams.passed
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, TestNativeStructMojom, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  NativeTypeTester_PassNativeStruct_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  NativeTypeTester_PassNativeStruct_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new NativeTypeTester_PassNativeStruct_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.passed =
        decoder.decodeStructPointer(TestNativeStructMojom);
    return val;
  };

  NativeTypeTester_PassNativeStruct_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(NativeTypeTester_PassNativeStruct_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(TestNativeStructMojom, val.passed);
  };
  function NativeTypeTester_PassNativeStructWithAttachments_Params(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  NativeTypeTester_PassNativeStructWithAttachments_Params.prototype.initDefaults_ = function() {
    this.s = null;
  };
  NativeTypeTester_PassNativeStructWithAttachments_Params.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  NativeTypeTester_PassNativeStructWithAttachments_Params.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate NativeTypeTester_PassNativeStructWithAttachments_Params.s
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, TestNativeStructWithAttachmentsMojom, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  NativeTypeTester_PassNativeStructWithAttachments_Params.encodedSize = codec.kStructHeaderSize + 8;

  NativeTypeTester_PassNativeStructWithAttachments_Params.decode = function(decoder) {
    var packed;
    var val = new NativeTypeTester_PassNativeStructWithAttachments_Params();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.s =
        decoder.decodeStructPointer(TestNativeStructWithAttachmentsMojom);
    return val;
  };

  NativeTypeTester_PassNativeStructWithAttachments_Params.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(NativeTypeTester_PassNativeStructWithAttachments_Params.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(TestNativeStructWithAttachmentsMojom, val.s);
  };
  function NativeTypeTester_PassNativeStructWithAttachments_ResponseParams(values) {
    this.initDefaults_();
    this.initFields_(values);
  }


  NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.prototype.initDefaults_ = function() {
    this.s = null;
  };
  NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.prototype.initFields_ = function(fields) {
    for(var field in fields) {
        if (this.hasOwnProperty(field))
          this[field] = fields[field];
    }
  };

  NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.validate = function(messageValidator, offset) {
    var err;
    err = messageValidator.validateStructHeader(offset, codec.kStructHeaderSize);
    if (err !== validator.validationError.NONE)
        return err;

    var kVersionSizes = [
      {version: 0, numBytes: 16}
    ];
    err = messageValidator.validateStructVersion(offset, kVersionSizes);
    if (err !== validator.validationError.NONE)
        return err;


    // validate NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.s
    err = messageValidator.validateStructPointer(offset + codec.kStructHeaderSize + 0, TestNativeStructWithAttachmentsMojom, false);
    if (err !== validator.validationError.NONE)
        return err;

    return validator.validationError.NONE;
  };

  NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.encodedSize = codec.kStructHeaderSize + 8;

  NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.decode = function(decoder) {
    var packed;
    var val = new NativeTypeTester_PassNativeStructWithAttachments_ResponseParams();
    var numberOfBytes = decoder.readUint32();
    var version = decoder.readUint32();
    val.s =
        decoder.decodeStructPointer(TestNativeStructWithAttachmentsMojom);
    return val;
  };

  NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.encode = function(encoder, val) {
    var packed;
    encoder.writeUint32(NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.encodedSize);
    encoder.writeUint32(0);
    encoder.encodeStructPointer(TestNativeStructWithAttachmentsMojom, val.s);
  };
  var kPicklePasser_PassPickledStruct_Name = 0;
  var kPicklePasser_PassPickledEnum_Name = 1;
  var kPicklePasser_PassPickleContainer_Name = 2;
  var kPicklePasser_PassPickles_Name = 3;
  var kPicklePasser_PassPickleArrays_Name = 4;

  function PicklePasserPtr(handleOrPtrInfo) {
    this.ptr = new bindings.InterfacePtrController(PicklePasser,
                                                   handleOrPtrInfo);
  }

  function PicklePasserAssociatedPtr(associatedInterfacePtrInfo) {
    this.ptr = new associatedBindings.AssociatedInterfacePtrController(
        PicklePasser, associatedInterfacePtrInfo);
  }

  PicklePasserAssociatedPtr.prototype =
      Object.create(PicklePasserPtr.prototype);
  PicklePasserAssociatedPtr.prototype.constructor =
      PicklePasserAssociatedPtr;

  function PicklePasserProxy(receiver) {
    this.receiver_ = receiver;
  }
  PicklePasserPtr.prototype.passPickledStruct = function() {
    return PicklePasserProxy.prototype.passPickledStruct
        .apply(this.ptr.getProxy(), arguments);
  };

  PicklePasserProxy.prototype.passPickledStruct = function(pickle) {
    var params_ = new PicklePasser_PassPickledStruct_Params();
    params_.pickle = pickle;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kPicklePasser_PassPickledStruct_Name,
          codec.align(PicklePasser_PassPickledStruct_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(PicklePasser_PassPickledStruct_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(PicklePasser_PassPickledStruct_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };
  PicklePasserPtr.prototype.passPickledEnum = function() {
    return PicklePasserProxy.prototype.passPickledEnum
        .apply(this.ptr.getProxy(), arguments);
  };

  PicklePasserProxy.prototype.passPickledEnum = function(pickle) {
    var params_ = new PicklePasser_PassPickledEnum_Params();
    params_.pickle = pickle;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kPicklePasser_PassPickledEnum_Name,
          codec.align(PicklePasser_PassPickledEnum_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(PicklePasser_PassPickledEnum_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(PicklePasser_PassPickledEnum_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };
  PicklePasserPtr.prototype.passPickleContainer = function() {
    return PicklePasserProxy.prototype.passPickleContainer
        .apply(this.ptr.getProxy(), arguments);
  };

  PicklePasserProxy.prototype.passPickleContainer = function(container) {
    var params_ = new PicklePasser_PassPickleContainer_Params();
    params_.container = container;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kPicklePasser_PassPickleContainer_Name,
          codec.align(PicklePasser_PassPickleContainer_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(PicklePasser_PassPickleContainer_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(PicklePasser_PassPickleContainer_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };
  PicklePasserPtr.prototype.passPickles = function() {
    return PicklePasserProxy.prototype.passPickles
        .apply(this.ptr.getProxy(), arguments);
  };

  PicklePasserProxy.prototype.passPickles = function(pickles) {
    var params_ = new PicklePasser_PassPickles_Params();
    params_.pickles = pickles;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kPicklePasser_PassPickles_Name,
          codec.align(PicklePasser_PassPickles_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(PicklePasser_PassPickles_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(PicklePasser_PassPickles_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };
  PicklePasserPtr.prototype.passPickleArrays = function() {
    return PicklePasserProxy.prototype.passPickleArrays
        .apply(this.ptr.getProxy(), arguments);
  };

  PicklePasserProxy.prototype.passPickleArrays = function(pickleArrays) {
    var params_ = new PicklePasser_PassPickleArrays_Params();
    params_.pickleArrays = pickleArrays;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kPicklePasser_PassPickleArrays_Name,
          codec.align(PicklePasser_PassPickleArrays_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(PicklePasser_PassPickleArrays_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(PicklePasser_PassPickleArrays_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };

  function PicklePasserStub(delegate) {
    this.delegate_ = delegate;
  }
  PicklePasserStub.prototype.passPickledStruct = function(pickle) {
    return this.delegate_ && this.delegate_.passPickledStruct && this.delegate_.passPickledStruct(pickle);
  }
  PicklePasserStub.prototype.passPickledEnum = function(pickle) {
    return this.delegate_ && this.delegate_.passPickledEnum && this.delegate_.passPickledEnum(pickle);
  }
  PicklePasserStub.prototype.passPickleContainer = function(container) {
    return this.delegate_ && this.delegate_.passPickleContainer && this.delegate_.passPickleContainer(container);
  }
  PicklePasserStub.prototype.passPickles = function(pickles) {
    return this.delegate_ && this.delegate_.passPickles && this.delegate_.passPickles(pickles);
  }
  PicklePasserStub.prototype.passPickleArrays = function(pickleArrays) {
    return this.delegate_ && this.delegate_.passPickleArrays && this.delegate_.passPickleArrays(pickleArrays);
  }

  PicklePasserStub.prototype.accept = function(message) {
    var reader = new codec.MessageReader(message);
    switch (reader.messageName) {
    default:
      return false;
    }
  };

  PicklePasserStub.prototype.acceptWithResponder =
      function(message, responder) {
    var reader = new codec.MessageReader(message);
    switch (reader.messageName) {
    case kPicklePasser_PassPickledStruct_Name:
      var params = reader.decodeStruct(PicklePasser_PassPickledStruct_Params);
      this.passPickledStruct(params.pickle).then(function(response) {
        var responseParams =
            new PicklePasser_PassPickledStruct_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kPicklePasser_PassPickledStruct_Name,
            codec.align(PicklePasser_PassPickledStruct_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(PicklePasser_PassPickledStruct_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    case kPicklePasser_PassPickledEnum_Name:
      var params = reader.decodeStruct(PicklePasser_PassPickledEnum_Params);
      this.passPickledEnum(params.pickle).then(function(response) {
        var responseParams =
            new PicklePasser_PassPickledEnum_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kPicklePasser_PassPickledEnum_Name,
            codec.align(PicklePasser_PassPickledEnum_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(PicklePasser_PassPickledEnum_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    case kPicklePasser_PassPickleContainer_Name:
      var params = reader.decodeStruct(PicklePasser_PassPickleContainer_Params);
      this.passPickleContainer(params.container).then(function(response) {
        var responseParams =
            new PicklePasser_PassPickleContainer_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kPicklePasser_PassPickleContainer_Name,
            codec.align(PicklePasser_PassPickleContainer_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(PicklePasser_PassPickleContainer_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    case kPicklePasser_PassPickles_Name:
      var params = reader.decodeStruct(PicklePasser_PassPickles_Params);
      this.passPickles(params.pickles).then(function(response) {
        var responseParams =
            new PicklePasser_PassPickles_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kPicklePasser_PassPickles_Name,
            codec.align(PicklePasser_PassPickles_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(PicklePasser_PassPickles_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    case kPicklePasser_PassPickleArrays_Name:
      var params = reader.decodeStruct(PicklePasser_PassPickleArrays_Params);
      this.passPickleArrays(params.pickleArrays).then(function(response) {
        var responseParams =
            new PicklePasser_PassPickleArrays_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kPicklePasser_PassPickleArrays_Name,
            codec.align(PicklePasser_PassPickleArrays_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(PicklePasser_PassPickleArrays_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    default:
      return false;
    }
  };

  function validatePicklePasserRequest(messageValidator) {
    var message = messageValidator.message;
    var paramsClass = null;
    switch (message.getName()) {
      case kPicklePasser_PassPickledStruct_Name:
        if (message.expectsResponse())
          paramsClass = PicklePasser_PassPickledStruct_Params;
      break;
      case kPicklePasser_PassPickledEnum_Name:
        if (message.expectsResponse())
          paramsClass = PicklePasser_PassPickledEnum_Params;
      break;
      case kPicklePasser_PassPickleContainer_Name:
        if (message.expectsResponse())
          paramsClass = PicklePasser_PassPickleContainer_Params;
      break;
      case kPicklePasser_PassPickles_Name:
        if (message.expectsResponse())
          paramsClass = PicklePasser_PassPickles_Params;
      break;
      case kPicklePasser_PassPickleArrays_Name:
        if (message.expectsResponse())
          paramsClass = PicklePasser_PassPickleArrays_Params;
      break;
    }
    if (paramsClass === null)
      return validator.validationError.NONE;
    return paramsClass.validate(messageValidator, messageValidator.message.getHeaderNumBytes());
  }

  function validatePicklePasserResponse(messageValidator) {
   var message = messageValidator.message;
   var paramsClass = null;
   switch (message.getName()) {
      case kPicklePasser_PassPickledStruct_Name:
        if (message.isResponse())
          paramsClass = PicklePasser_PassPickledStruct_ResponseParams;
        break;
      case kPicklePasser_PassPickledEnum_Name:
        if (message.isResponse())
          paramsClass = PicklePasser_PassPickledEnum_ResponseParams;
        break;
      case kPicklePasser_PassPickleContainer_Name:
        if (message.isResponse())
          paramsClass = PicklePasser_PassPickleContainer_ResponseParams;
        break;
      case kPicklePasser_PassPickles_Name:
        if (message.isResponse())
          paramsClass = PicklePasser_PassPickles_ResponseParams;
        break;
      case kPicklePasser_PassPickleArrays_Name:
        if (message.isResponse())
          paramsClass = PicklePasser_PassPickleArrays_ResponseParams;
        break;
    }
    if (paramsClass === null)
      return validator.validationError.NONE;
    return paramsClass.validate(messageValidator, messageValidator.message.getHeaderNumBytes());
  }

  var PicklePasser = {
    name: 'mojo.test.PicklePasser',
    kVersion: 0,
    ptrClass: PicklePasserPtr,
    proxyClass: PicklePasserProxy,
    stubClass: PicklePasserStub,
    validateRequest: validatePicklePasserRequest,
    validateResponse: validatePicklePasserResponse,
  };
  PicklePasserStub.prototype.validator = validatePicklePasserRequest;
  PicklePasserProxy.prototype.validator = validatePicklePasserResponse;
  var kRectService_AddRect_Name = 0;
  var kRectService_GetLargestRect_Name = 1;
  var kRectService_PassSharedRect_Name = 2;

  function RectServicePtr(handleOrPtrInfo) {
    this.ptr = new bindings.InterfacePtrController(RectService,
                                                   handleOrPtrInfo);
  }

  function RectServiceAssociatedPtr(associatedInterfacePtrInfo) {
    this.ptr = new associatedBindings.AssociatedInterfacePtrController(
        RectService, associatedInterfacePtrInfo);
  }

  RectServiceAssociatedPtr.prototype =
      Object.create(RectServicePtr.prototype);
  RectServiceAssociatedPtr.prototype.constructor =
      RectServiceAssociatedPtr;

  function RectServiceProxy(receiver) {
    this.receiver_ = receiver;
  }
  RectServicePtr.prototype.addRect = function() {
    return RectServiceProxy.prototype.addRect
        .apply(this.ptr.getProxy(), arguments);
  };

  RectServiceProxy.prototype.addRect = function(r) {
    var params_ = new RectService_AddRect_Params();
    params_.r = r;
    var builder = new codec.MessageV0Builder(
        kRectService_AddRect_Name,
        codec.align(RectService_AddRect_Params.encodedSize));
    builder.encodeStruct(RectService_AddRect_Params, params_);
    var message = builder.finish();
    this.receiver_.accept(message);
  };
  RectServicePtr.prototype.getLargestRect = function() {
    return RectServiceProxy.prototype.getLargestRect
        .apply(this.ptr.getProxy(), arguments);
  };

  RectServiceProxy.prototype.getLargestRect = function() {
    var params_ = new RectService_GetLargestRect_Params();
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kRectService_GetLargestRect_Name,
          codec.align(RectService_GetLargestRect_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(RectService_GetLargestRect_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(RectService_GetLargestRect_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };
  RectServicePtr.prototype.passSharedRect = function() {
    return RectServiceProxy.prototype.passSharedRect
        .apply(this.ptr.getProxy(), arguments);
  };

  RectServiceProxy.prototype.passSharedRect = function(r) {
    var params_ = new RectService_PassSharedRect_Params();
    params_.r = r;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kRectService_PassSharedRect_Name,
          codec.align(RectService_PassSharedRect_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(RectService_PassSharedRect_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(RectService_PassSharedRect_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };

  function RectServiceStub(delegate) {
    this.delegate_ = delegate;
  }
  RectServiceStub.prototype.addRect = function(r) {
    return this.delegate_ && this.delegate_.addRect && this.delegate_.addRect(r);
  }
  RectServiceStub.prototype.getLargestRect = function() {
    return this.delegate_ && this.delegate_.getLargestRect && this.delegate_.getLargestRect();
  }
  RectServiceStub.prototype.passSharedRect = function(r) {
    return this.delegate_ && this.delegate_.passSharedRect && this.delegate_.passSharedRect(r);
  }

  RectServiceStub.prototype.accept = function(message) {
    var reader = new codec.MessageReader(message);
    switch (reader.messageName) {
    case kRectService_AddRect_Name:
      var params = reader.decodeStruct(RectService_AddRect_Params);
      this.addRect(params.r);
      return true;
    default:
      return false;
    }
  };

  RectServiceStub.prototype.acceptWithResponder =
      function(message, responder) {
    var reader = new codec.MessageReader(message);
    switch (reader.messageName) {
    case kRectService_GetLargestRect_Name:
      var params = reader.decodeStruct(RectService_GetLargestRect_Params);
      this.getLargestRect().then(function(response) {
        var responseParams =
            new RectService_GetLargestRect_ResponseParams();
        responseParams.largest = response.largest;
        var builder = new codec.MessageV1Builder(
            kRectService_GetLargestRect_Name,
            codec.align(RectService_GetLargestRect_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(RectService_GetLargestRect_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    case kRectService_PassSharedRect_Name:
      var params = reader.decodeStruct(RectService_PassSharedRect_Params);
      this.passSharedRect(params.r).then(function(response) {
        var responseParams =
            new RectService_PassSharedRect_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kRectService_PassSharedRect_Name,
            codec.align(RectService_PassSharedRect_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(RectService_PassSharedRect_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    default:
      return false;
    }
  };

  function validateRectServiceRequest(messageValidator) {
    var message = messageValidator.message;
    var paramsClass = null;
    switch (message.getName()) {
      case kRectService_AddRect_Name:
        if (!message.expectsResponse() && !message.isResponse())
          paramsClass = RectService_AddRect_Params;
      break;
      case kRectService_GetLargestRect_Name:
        if (message.expectsResponse())
          paramsClass = RectService_GetLargestRect_Params;
      break;
      case kRectService_PassSharedRect_Name:
        if (message.expectsResponse())
          paramsClass = RectService_PassSharedRect_Params;
      break;
    }
    if (paramsClass === null)
      return validator.validationError.NONE;
    return paramsClass.validate(messageValidator, messageValidator.message.getHeaderNumBytes());
  }

  function validateRectServiceResponse(messageValidator) {
   var message = messageValidator.message;
   var paramsClass = null;
   switch (message.getName()) {
      case kRectService_GetLargestRect_Name:
        if (message.isResponse())
          paramsClass = RectService_GetLargestRect_ResponseParams;
        break;
      case kRectService_PassSharedRect_Name:
        if (message.isResponse())
          paramsClass = RectService_PassSharedRect_ResponseParams;
        break;
    }
    if (paramsClass === null)
      return validator.validationError.NONE;
    return paramsClass.validate(messageValidator, messageValidator.message.getHeaderNumBytes());
  }

  var RectService = {
    name: 'mojo.test.RectService',
    kVersion: 0,
    ptrClass: RectServicePtr,
    proxyClass: RectServiceProxy,
    stubClass: RectServiceStub,
    validateRequest: validateRectServiceRequest,
    validateResponse: validateRectServiceResponse,
  };
  RectServiceStub.prototype.validator = validateRectServiceRequest;
  RectServiceProxy.prototype.validator = validateRectServiceResponse;
  var kNativeTypeTester_PassNativeStruct_Name = 0;
  var kNativeTypeTester_PassNativeStructWithAttachments_Name = 1;

  function NativeTypeTesterPtr(handleOrPtrInfo) {
    this.ptr = new bindings.InterfacePtrController(NativeTypeTester,
                                                   handleOrPtrInfo);
  }

  function NativeTypeTesterAssociatedPtr(associatedInterfacePtrInfo) {
    this.ptr = new associatedBindings.AssociatedInterfacePtrController(
        NativeTypeTester, associatedInterfacePtrInfo);
  }

  NativeTypeTesterAssociatedPtr.prototype =
      Object.create(NativeTypeTesterPtr.prototype);
  NativeTypeTesterAssociatedPtr.prototype.constructor =
      NativeTypeTesterAssociatedPtr;

  function NativeTypeTesterProxy(receiver) {
    this.receiver_ = receiver;
  }
  NativeTypeTesterPtr.prototype.passNativeStruct = function() {
    return NativeTypeTesterProxy.prototype.passNativeStruct
        .apply(this.ptr.getProxy(), arguments);
  };

  NativeTypeTesterProxy.prototype.passNativeStruct = function(s) {
    var params_ = new NativeTypeTester_PassNativeStruct_Params();
    params_.s = s;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kNativeTypeTester_PassNativeStruct_Name,
          codec.align(NativeTypeTester_PassNativeStruct_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(NativeTypeTester_PassNativeStruct_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(NativeTypeTester_PassNativeStruct_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };
  NativeTypeTesterPtr.prototype.passNativeStructWithAttachments = function() {
    return NativeTypeTesterProxy.prototype.passNativeStructWithAttachments
        .apply(this.ptr.getProxy(), arguments);
  };

  NativeTypeTesterProxy.prototype.passNativeStructWithAttachments = function(s) {
    var params_ = new NativeTypeTester_PassNativeStructWithAttachments_Params();
    params_.s = s;
    return new Promise(function(resolve, reject) {
      var builder = new codec.MessageV1Builder(
          kNativeTypeTester_PassNativeStructWithAttachments_Name,
          codec.align(NativeTypeTester_PassNativeStructWithAttachments_Params.encodedSize),
          codec.kMessageExpectsResponse, 0);
      builder.encodeStruct(NativeTypeTester_PassNativeStructWithAttachments_Params, params_);
      var message = builder.finish();
      this.receiver_.acceptAndExpectResponse(message).then(function(message) {
        var reader = new codec.MessageReader(message);
        var responseParams =
            reader.decodeStruct(NativeTypeTester_PassNativeStructWithAttachments_ResponseParams);
        resolve(responseParams);
      }).catch(function(result) {
        reject(Error("Connection error: " + result));
      });
    }.bind(this));
  };

  function NativeTypeTesterStub(delegate) {
    this.delegate_ = delegate;
  }
  NativeTypeTesterStub.prototype.passNativeStruct = function(s) {
    return this.delegate_ && this.delegate_.passNativeStruct && this.delegate_.passNativeStruct(s);
  }
  NativeTypeTesterStub.prototype.passNativeStructWithAttachments = function(s) {
    return this.delegate_ && this.delegate_.passNativeStructWithAttachments && this.delegate_.passNativeStructWithAttachments(s);
  }

  NativeTypeTesterStub.prototype.accept = function(message) {
    var reader = new codec.MessageReader(message);
    switch (reader.messageName) {
    default:
      return false;
    }
  };

  NativeTypeTesterStub.prototype.acceptWithResponder =
      function(message, responder) {
    var reader = new codec.MessageReader(message);
    switch (reader.messageName) {
    case kNativeTypeTester_PassNativeStruct_Name:
      var params = reader.decodeStruct(NativeTypeTester_PassNativeStruct_Params);
      this.passNativeStruct(params.s).then(function(response) {
        var responseParams =
            new NativeTypeTester_PassNativeStruct_ResponseParams();
        responseParams.passed = response.passed;
        var builder = new codec.MessageV1Builder(
            kNativeTypeTester_PassNativeStruct_Name,
            codec.align(NativeTypeTester_PassNativeStruct_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(NativeTypeTester_PassNativeStruct_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    case kNativeTypeTester_PassNativeStructWithAttachments_Name:
      var params = reader.decodeStruct(NativeTypeTester_PassNativeStructWithAttachments_Params);
      this.passNativeStructWithAttachments(params.s).then(function(response) {
        var responseParams =
            new NativeTypeTester_PassNativeStructWithAttachments_ResponseParams();
        responseParams.s = response.s;
        var builder = new codec.MessageV1Builder(
            kNativeTypeTester_PassNativeStructWithAttachments_Name,
            codec.align(NativeTypeTester_PassNativeStructWithAttachments_ResponseParams.encodedSize),
            codec.kMessageIsResponse, reader.requestID);
        builder.encodeStruct(NativeTypeTester_PassNativeStructWithAttachments_ResponseParams,
                             responseParams);
        var message = builder.finish();
        responder.accept(message);
      });
      return true;
    default:
      return false;
    }
  };

  function validateNativeTypeTesterRequest(messageValidator) {
    var message = messageValidator.message;
    var paramsClass = null;
    switch (message.getName()) {
      case kNativeTypeTester_PassNativeStruct_Name:
        if (message.expectsResponse())
          paramsClass = NativeTypeTester_PassNativeStruct_Params;
      break;
      case kNativeTypeTester_PassNativeStructWithAttachments_Name:
        if (message.expectsResponse())
          paramsClass = NativeTypeTester_PassNativeStructWithAttachments_Params;
      break;
    }
    if (paramsClass === null)
      return validator.validationError.NONE;
    return paramsClass.validate(messageValidator, messageValidator.message.getHeaderNumBytes());
  }

  function validateNativeTypeTesterResponse(messageValidator) {
   var message = messageValidator.message;
   var paramsClass = null;
   switch (message.getName()) {
      case kNativeTypeTester_PassNativeStruct_Name:
        if (message.isResponse())
          paramsClass = NativeTypeTester_PassNativeStruct_ResponseParams;
        break;
      case kNativeTypeTester_PassNativeStructWithAttachments_Name:
        if (message.isResponse())
          paramsClass = NativeTypeTester_PassNativeStructWithAttachments_ResponseParams;
        break;
    }
    if (paramsClass === null)
      return validator.validationError.NONE;
    return paramsClass.validate(messageValidator, messageValidator.message.getHeaderNumBytes());
  }

  var NativeTypeTester = {
    name: 'mojo.test.NativeTypeTester',
    kVersion: 0,
    ptrClass: NativeTypeTesterPtr,
    proxyClass: NativeTypeTesterProxy,
    stubClass: NativeTypeTesterStub,
    validateRequest: validateNativeTypeTesterRequest,
    validateResponse: validateNativeTypeTesterResponse,
  };
  NativeTypeTesterStub.prototype.validator = validateNativeTypeTesterRequest;
  NativeTypeTesterProxy.prototype.validator = validateNativeTypeTesterResponse;
  exports.PickledEnum = PickledEnum;
  exports.PickledStruct = PickledStruct;
  exports.PickleContainer = PickleContainer;
  exports.TestNativeStructMojom = TestNativeStructMojom;
  exports.TestNativeStructWithAttachmentsMojom = TestNativeStructWithAttachmentsMojom;
  exports.PicklePasser = PicklePasser;
  exports.PicklePasserPtr = PicklePasserPtr;
  exports.PicklePasserAssociatedPtr = PicklePasserAssociatedPtr;
  exports.RectService = RectService;
  exports.RectServicePtr = RectServicePtr;
  exports.RectServiceAssociatedPtr = RectServiceAssociatedPtr;
  exports.NativeTypeTester = NativeTypeTester;
  exports.NativeTypeTesterPtr = NativeTypeTesterPtr;
  exports.NativeTypeTesterAssociatedPtr = NativeTypeTesterAssociatedPtr;
})();