text:
// Generated by the protocol buffer compiler.  DO NOT EDIT!
// source: CalculatorMsg.proto

package org.tao.pbtest.proto;

public final class CalculatorMsg {
  private CalculatorMsg() {}
  public static void registerAllExtensions(
      com.google.protobuf.ExtensionRegistry registry) {
  }
  public interface RequestProtoOrBuilder
      extends com.google.protobuf.MessageOrBuilder {

    // required string methodName = 1;
    /**
     * required string methodName = 1;
     */
    boolean hasMethodName();
    /**
     * required string methodName = 1;
     */
    java.lang.String getMethodName();
    /**
     * required string methodName = 1;
     */
    com.google.protobuf.ByteString
        getMethodNameBytes();

    // required int32 num1 = 2;
    /**
     * required int32 num1 = 2;
     */
    boolean hasNum1();
    /**
     * required int32 num1 = 2;
     */
    int getNum1();

    // required int32 num2 = 3;
    /**
     * required int32 num2 = 3;
     */
    boolean hasNum2();
    /**
     * required int32 num2 = 3;
     */
    int getNum2();
  }
  /**
   * Protobuf type {@code RequestProto}
   */
  public static final class RequestProto extends
      com.google.protobuf.GeneratedMessage
      implements RequestProtoOrBuilder {
    // Use RequestProto.newBuilder() to construct.
    private RequestProto(com.google.protobuf.GeneratedMessage.Builder<?> builder) {
      super(builder);
      this.unknownFields = builder.getUnknownFields();
    }
    private RequestProto(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); }

    private static final RequestProto defaultInstance;
    public static RequestProto getDefaultInstance() {
      return defaultInstance;
    }

    public RequestProto getDefaultInstanceForType() {
      return defaultInstance;
    }

    private final com.google.protobuf.UnknownFieldSet unknownFields;
    @java.lang.Override
    public final com.google.protobuf.UnknownFieldSet
        getUnknownFields() {
      return this.unknownFields;
    }
    private RequestProto(
        com.google.protobuf.CodedInputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws com.google.protobuf.InvalidProtocolBufferException {
      initFields();
      int mutable_bitField0_ = 0;
      com.google.protobuf.UnknownFieldSet.Builder unknownFields =
          com.google.protobuf.UnknownFieldSet.newBuilder();
      try {
        boolean done = false;
        while (!done) {
          int tag = input.readTag();
          switch (tag) {
            case 0:
              done = true;
              break;
            default: {
              if (!parseUnknownField(input, unknownFields,
                                     extensionRegistry, tag)) {
                done = true;
              }
              break;
            }
            case 10: {
              bitField0_ |= 0x00000001;
              methodName_ = input.readBytes();
              break;
            }
            case 16: {
              bitField0_ |= 0x00000002;
              num1_ = input.readInt32();
              break;
            }
            case 24: {
              bitField0_ |= 0x00000004;
              num2_ = input.readInt32();
              break;
            }
          }
        }
      } catch (com.google.protobuf.InvalidProtocolBufferException e) {
        throw e.setUnfinishedMessage(this);
      } catch (java.io.IOException e) {
        throw new com.google.protobuf.InvalidProtocolBufferException(
            e.getMessage()).setUnfinishedMessage(this);
      } finally {
        this.unknownFields = unknownFields.build();
        makeExtensionsImmutable();
      }
    }
    public static final com.google.protobuf.Descriptors.Descriptor
        getDescriptor() {
      return org.tao.pbtest.proto.CalculatorMsg.internal_static_RequestProto_descriptor;
    }

    protected com.google.protobuf.GeneratedMessage.FieldAccessorTable
        internalGetFieldAccessorTable() {
      return org.tao.pbtest.proto.CalculatorMsg.internal_static_RequestProto_fieldAccessorTable
          .ensureFieldAccessorsInitialized(
              org.tao.pbtest.proto.CalculatorMsg.RequestProto.class, org.tao.pbtest.proto.CalculatorMsg.RequestProto.Builder.class);
    }

    public static com.google.protobuf.Parser<RequestProto> PARSER =
        new com.google.protobuf.AbstractParser<RequestProto>() {
      public RequestProto parsePartialFrom(
          com.google.protobuf.CodedInputStream input,
          com.google.protobuf.ExtensionRegistryLite extensionRegistry)
          throws com.google.protobuf.InvalidProtocolBufferException {
        return new RequestProto(input, extensionRegistry);
      }
    };

    @java.lang.Override
    public com.google.protobuf.Parser<RequestProto> getParserForType() {
      return PARSER;
    }

    private int bitField0_;
    // required string methodName = 1;
    public static final int METHODNAME_FIELD_NUMBER = 1;
    private java.lang.Object methodName_;
    /**
     * required string methodName = 1;
     */
    public boolean hasMethodName() {
      return ((bitField0_ & 0x00000001) == 0x00000001);
    }
    /**
     * required string methodName = 1;
     */
    public java.lang.String getMethodName() {
      java.lang.Object ref = methodName_;
      if (ref instanceof java.lang.String) {
        return (java.lang.String) ref;
      } else {
        com.google.protobuf.ByteString bs =
            (com.google.protobuf.ByteString) ref;
        java.lang.String s = bs.toStringUtf8();
        if (bs.isValidUtf8()) {
          methodName_ = s;
        }
        return s;
      }
    }
    /**
     * required string methodName = 1;
     */
    public com.google.protobuf.ByteString
        getMethodNameBytes() {
      java.lang.Object ref = methodName_;
      if (ref instanceof java.lang.String) {
        com.google.protobuf.ByteString b =
            com.google.protobuf.ByteString.copyFromUtf8(
                (java.lang.String) ref);
        methodName_ = b;
        return b;
      } else {
        return (com.google.protobuf.ByteString) ref;
      }
    }

    // required int32 num1 = 2;
    public static final int NUM1_FIELD_NUMBER = 2;
    private int num1_;
    /**
     * required int32 num1 = 2;
     */
    public boolean hasNum1() {
      return ((bitField0_ & 0x00000002) == 0x00000002);
    }
    /**
     * required int32 num1 = 2;
     */
    public int getNum1() {
      return num1_;
    }

    // required int32 num2 = 3;
    public static final int NUM2_FIELD_NUMBER = 3;
    private int num2_;
    /**
     * required int32 num2 = 3;
     */
    public boolean hasNum2() {
      return ((bitField0_ & 0x00000004) == 0x00000004);
    }
    /**
     * required int32 num2 = 3;
     */
    public int getNum2() {
      return num2_;
    }

    private void initFields() {
      methodName_ = "";
      num1_ = 0;
      num2_ = 0;
    }
    private byte memoizedIsInitialized = -1;
    public final boolean isInitialized() {
      byte isInitialized = memoizedIsInitialized;
      if (isInitialized != -1) return isInitialized == 1;

      if (!hasMethodName()) {
        memoizedIsInitialized = 0;
        return false;
      }
      if (!hasNum1()) {
        memoizedIsInitialized = 0;
        return false;
      }
      if (!hasNum2()) {
        memoizedIsInitialized = 0;
        return false;
      }
      memoizedIsInitialized = 1;
      return true;
    }

    public void writeTo(com.google.protobuf.CodedOutputStream output)
                        throws java.io.IOException {
      getSerializedSize();
      if (((bitField0_ & 0x00000001) == 0x00000001)) {
        output.writeBytes(1, getMethodNameBytes());
      }
      if (((bitField0_ & 0x00000002) == 0x00000002)) {
        output.writeInt32(2, num1_);
      }
      if (((bitField0_ & 0x00000004) == 0x00000004)) {
        output.writeInt32(3, num2_);
      }
      getUnknownFields().writeTo(output);
    }

    private int memoizedSerializedSize = -1;
    public int getSerializedSize() {
      int size = memoizedSerializedSize;
      if (size != -1) return size;

      size = 0;
      if (((bitField0_ & 0x00000001) == 0x00000001)) {
        size += com.google.protobuf.CodedOutputStream
          .computeBytesSize(1, getMethodNameBytes());
      }
      if (((bitField0_ & 0x00000002) == 0x00000002)) {
        size += com.google.protobuf.CodedOutputStream
          .computeInt32Size(2, num1_);
      }
      if (((bitField0_ & 0x00000004) == 0x00000004)) {
        size += com.google.protobuf.CodedOutputStream
          .computeInt32Size(3, num2_);
      }
      size += getUnknownFields().getSerializedSize();
      memoizedSerializedSize = size;
      return size;
    }

    private static final long serialVersionUID = 0L;
    @java.lang.Override
    protected java.lang.Object writeReplace()
        throws java.io.ObjectStreamException {
      return super.writeReplace();
    }

    @java.lang.Override
    public boolean equals(final java.lang.Object obj) {
      if (obj == this) {
       return true;
      }
      if (!(obj instanceof org.tao.pbtest.proto.CalculatorMsg.RequestProto)) {
        return super.equals(obj);
      }
      org.tao.pbtest.proto.CalculatorMsg.RequestProto other = (org.tao.pbtest.proto.CalculatorMsg.RequestProto) obj;

      boolean result = true;
      result = result && (hasMethodName() == other.hasMethodName());
      if (hasMethodName()) {
        result = result && getMethodName()
            .equals(other.getMethodName());
      }
      result = result && (hasNum1() == other.hasNum1());
      if (hasNum1()) {
        result = result && (getNum1()
            == other.getNum1());
      }
      result = result && (hasNum2() == other.hasNum2());
      if (hasNum2()) {
        result = result && (getNum2()
            == other.getNum2());
      }
      result = result &&
          getUnknownFields().equals(other.getUnknownFields());
      return result;
    }

    private int memoizedHashCode = 0;
    @java.lang.Override
    public int hashCode() {
      if (memoizedHashCode != 0) {
        return memoizedHashCode;
      }
      int hash = 41;
      hash = (19 * hash) + getDescriptorForType().hashCode();
      if (hasMethodName()) {
        hash = (37 * hash) + METHODNAME_FIELD_NUMBER;
        hash = (53 * hash) + getMethodName().hashCode();
      }
      if (hasNum1()) {
        hash = (37 * hash) + NUM1_FIELD_NUMBER;
        hash = (53 * hash) + getNum1();
      }
      if (hasNum2()) {
        hash = (37 * hash) + NUM2_FIELD_NUMBER;
        hash = (53 * hash) + getNum2();
      }
      hash = (29 * hash) + getUnknownFields().hashCode();
      memoizedHashCode = hash;
      return hash;
    }

    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(
        com.google.protobuf.ByteString data)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(
        com.google.protobuf.ByteString data,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(byte[] data)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(
        byte[] data,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(java.io.InputStream input)
        throws java.io.IOException {
      return PARSER.parseFrom(input);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(
        java.io.InputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws java.io.IOException {
      return PARSER.parseFrom(input, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseDelimitedFrom(java.io.InputStream input)
        throws java.io.IOException {
      return PARSER.parseDelimitedFrom(input);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseDelimitedFrom(
        java.io.InputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws java.io.IOException {
      return PARSER.parseDelimitedFrom(input, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(
        com.google.protobuf.CodedInputStream input)
        throws java.io.IOException {
      return PARSER.parseFrom(input);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.RequestProto parseFrom(
        com.google.protobuf.CodedInputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws java.io.IOException {
      return PARSER.parseFrom(input, extensionRegistry);
    }

    public static Builder newBuilder() { return Builder.create(); }
    public Builder newBuilderForType() { return newBuilder(); }
    public static Builder newBuilder(org.tao.pbtest.proto.CalculatorMsg.RequestProto prototype) {
      return newBuilder().mergeFrom(prototype);
    }
    public Builder toBuilder() { return newBuilder(this); }

    @java.lang.Override
    protected Builder newBuilderForType(
        com.google.protobuf.GeneratedMessage.BuilderParent parent) {
      Builder builder = new Builder(parent);
      return builder;
    }
    /**
     * Protobuf type {@code RequestProto}
     */
    public static final class Builder extends
        com.google.protobuf.GeneratedMessage.Builder<Builder>
       implements org.tao.pbtest.proto.CalculatorMsg.RequestProtoOrBuilder {
      public static final com.google.protobuf.Descriptors.Descriptor
          getDescriptor() {
        return org.tao.pbtest.proto.CalculatorMsg.internal_static_RequestProto_descriptor;
      }

      protected com.google.protobuf.GeneratedMessage.FieldAccessorTable
          internalGetFieldAccessorTable() {
        return org.tao.pbtest.proto.CalculatorMsg.internal_static_RequestProto_fieldAccessorTable
            .ensureFieldAccessorsInitialized(
                org.tao.pbtest.proto.CalculatorMsg.RequestProto.class, org.tao.pbtest.proto.CalculatorMsg.RequestProto.Builder.class);
      }

      // Construct using org.tao.pbtest.proto.CalculatorMsg.RequestProto.newBuilder()
      private Builder() {
        maybeForceBuilderInitialization();
      }

      private Builder(
          com.google.protobuf.GeneratedMessage.BuilderParent parent) {
        super(parent);
        maybeForceBuilderInitialization();
      }
      private void maybeForceBuilderInitialization() {
        if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) {
        }
      }
      private static Builder create() {
        return new Builder();
      }

      public Builder clear() {
        super.clear();
        methodName_ = "";
        bitField0_ = (bitField0_ & ~0x00000001);
        num1_ = 0;
        bitField0_ = (bitField0_ & ~0x00000002);
        num2_ = 0;
        bitField0_ = (bitField0_ & ~0x00000004);
        return this;
      }

      public Builder clone() {
        return create().mergeFrom(buildPartial());
      }

      public com.google.protobuf.Descriptors.Descriptor
          getDescriptorForType() {
        return org.tao.pbtest.proto.CalculatorMsg.internal_static_RequestProto_descriptor;
      }

      public org.tao.pbtest.proto.CalculatorMsg.RequestProto getDefaultInstanceForType() {
        return org.tao.pbtest.proto.CalculatorMsg.RequestProto.getDefaultInstance();
      }

      public org.tao.pbtest.proto.CalculatorMsg.RequestProto build() {
        org.tao.pbtest.proto.CalculatorMsg.RequestProto result = buildPartial();
        if (!result.isInitialized()) {
          throw newUninitializedMessageException(result);
        }
        return result;
      }

      public org.tao.pbtest.proto.CalculatorMsg.RequestProto buildPartial() {
        org.tao.pbtest.proto.CalculatorMsg.RequestProto result = new org.tao.pbtest.proto.CalculatorMsg.RequestProto(this);
        int from_bitField0_ = bitField0_;
        int to_bitField0_ = 0;
        if (((from_bitField0_ & 0x00000001) == 0x00000001)) {
          to_bitField0_ |= 0x00000001;
        }
        result.methodName_ = methodName_;
        if (((from_bitField0_ & 0x00000002) == 0x00000002)) {
          to_bitField0_ |= 0x00000002;
        }
        result.num1_ = num1_;
        if (((from_bitField0_ & 0x00000004) == 0x00000004)) {
          to_bitField0_ |= 0x00000004;
        }
        result.num2_ = num2_;
        result.bitField0_ = to_bitField0_;
        onBuilt();
        return result;
      }

      public Builder mergeFrom(com.google.protobuf.Message other) {
        if (other instanceof org.tao.pbtest.proto.CalculatorMsg.RequestProto) {
          return mergeFrom((org.tao.pbtest.proto.CalculatorMsg.RequestProto)other);
        } else {
          super.mergeFrom(other);
          return this;
        }
      }

      public Builder mergeFrom(org.tao.pbtest.proto.CalculatorMsg.RequestProto other) {
        if (other == org.tao.pbtest.proto.CalculatorMsg.RequestProto.getDefaultInstance()) return this;
        if (other.hasMethodName()) {
          bitField0_ |= 0x00000001;
          methodName_ = other.methodName_;
          onChanged();
        }
        if (other.hasNum1()) {
          setNum1(other.getNum1());
        }
        if (other.hasNum2()) {
          setNum2(other.getNum2());
        }
        this.mergeUnknownFields(other.getUnknownFields());
        return this;
      }

      public final boolean isInitialized() {
        if (!hasMethodName()) {

          return false;
        }
        if (!hasNum1()) {

          return false;
        }
        if (!hasNum2()) {

          return false;
        }
        return true;
      }

      public Builder mergeFrom(
          com.google.protobuf.CodedInputStream input,
          com.google.protobuf.ExtensionRegistryLite extensionRegistry)
          throws java.io.IOException {
        org.tao.pbtest.proto.CalculatorMsg.RequestProto parsedMessage = null;
        try {
          parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry);
        } catch (com.google.protobuf.InvalidProtocolBufferException e) {
          parsedMessage = (org.tao.pbtest.proto.CalculatorMsg.RequestProto) e.getUnfinishedMessage();
          throw e;
        } finally {
          if (parsedMessage != null) {
            mergeFrom(parsedMessage);
          }
        }
        return this;
      }
      private int bitField0_;

      // required string methodName = 1;
      private java.lang.Object methodName_ = "";
      /**
       * required string methodName = 1;
       */
      public boolean hasMethodName() {
        return ((bitField0_ & 0x00000001) == 0x00000001);
      }
      /**
       * required string methodName = 1;
       */
      public java.lang.String getMethodName() {
        java.lang.Object ref = methodName_;
        if (!(ref instanceof java.lang.String)) {
          java.lang.String s = ((com.google.protobuf.ByteString) ref)
              .toStringUtf8();
          methodName_ = s;
          return s;
        } else {
          return (java.lang.String) ref;
        }
      }
      /**
       * required string methodName = 1;
       */
      public com.google.protobuf.ByteString
          getMethodNameBytes() {
        java.lang.Object ref = methodName_;
        if (ref instanceof String) {
          com.google.protobuf.ByteString b =
              com.google.protobuf.ByteString.copyFromUtf8(
                  (java.lang.String) ref);
          methodName_ = b;
          return b;
        } else {
          return (com.google.protobuf.ByteString) ref;
        }
      }
      /**
       * required string methodName = 1;
       */
      public Builder setMethodName(
          java.lang.String value) {
        if (value == null) {
    throw new NullPointerException();
  }
  bitField0_ |= 0x00000001;
        methodName_ = value;
        onChanged();
        return this;
      }
      /**
       * required string methodName = 1;
       */
      public Builder clearMethodName() {
        bitField0_ = (bitField0_ & ~0x00000001);
        methodName_ = getDefaultInstance().getMethodName();
        onChanged();
        return this;
      }
      /**
       * required string methodName = 1;
       */
      public Builder setMethodNameBytes(
          com.google.protobuf.ByteString value) {
        if (value == null) {
    throw new NullPointerException();
  }
  bitField0_ |= 0x00000001;
        methodName_ = value;
        onChanged();
        return this;
      }

      // required int32 num1 = 2;
      private int num1_ ;
      /**
       * required int32 num1 = 2;
       */
      public boolean hasNum1() {
        return ((bitField0_ & 0x00000002) == 0x00000002);
      }
      /**
       * required int32 num1 = 2;
       */
      public int getNum1() {
        return num1_;
      }
      /**
       * required int32 num1 = 2;
       */
      public Builder setNum1(int value) {
        bitField0_ |= 0x00000002;
        num1_ = value;
        onChanged();
        return this;
      }
      /**
       * required int32 num1 = 2;
       */
      public Builder clearNum1() {
        bitField0_ = (bitField0_ & ~0x00000002);
        num1_ = 0;
        onChanged();
        return this;
      }

      // required int32 num2 = 3;
      private int num2_ ;
      /**
       * required int32 num2 = 3;
       */
      public boolean hasNum2() {
        return ((bitField0_ & 0x00000004) == 0x00000004);
      }
      /**
       * required int32 num2 = 3;
       */
      public int getNum2() {
        return num2_;
      }
      /**
       * required int32 num2 = 3;
       */
      public Builder setNum2(int value) {
        bitField0_ |= 0x00000004;
        num2_ = value;
        onChanged();
        return this;
      }
      /**
       * required int32 num2 = 3;
       */
      public Builder clearNum2() {
        bitField0_ = (bitField0_ & ~0x00000004);
        num2_ = 0;
        onChanged();
        return this;
      }

      // @@protoc_insertion_point(builder_scope:RequestProto)
    }

    static {
      defaultInstance = new RequestProto(true);
      defaultInstance.initFields();
    }

    // @@protoc_insertion_point(class_scope:RequestProto)
  }

  public interface ResponseProtoOrBuilder
      extends com.google.protobuf.MessageOrBuilder {

    // required int32 result = 1;
    /**
     * required int32 result = 1;
     */
    boolean hasResult();
    /**
     * required int32 result = 1;
     */
    int getResult();
  }
  /**
   * Protobuf type {@code ResponseProto}
   */
  public static final class ResponseProto extends
      com.google.protobuf.GeneratedMessage
      implements ResponseProtoOrBuilder {
    // Use ResponseProto.newBuilder() to construct.
    private ResponseProto(com.google.protobuf.GeneratedMessage.Builder<?> builder) {
      super(builder);
      this.unknownFields = builder.getUnknownFields();
    }
    private ResponseProto(boolean noInit) { this.unknownFields = com.google.protobuf.UnknownFieldSet.getDefaultInstance(); }

    private static final ResponseProto defaultInstance;
    public static ResponseProto getDefaultInstance() {
      return defaultInstance;
    }

    public ResponseProto getDefaultInstanceForType() {
      return defaultInstance;
    }

    private final com.google.protobuf.UnknownFieldSet unknownFields;
    @java.lang.Override
    public final com.google.protobuf.UnknownFieldSet
        getUnknownFields() {
      return this.unknownFields;
    }
    private ResponseProto(
        com.google.protobuf.CodedInputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws com.google.protobuf.InvalidProtocolBufferException {
      initFields();
      int mutable_bitField0_ = 0;
      com.google.protobuf.UnknownFieldSet.Builder unknownFields =
          com.google.protobuf.UnknownFieldSet.newBuilder();
      try {
        boolean done = false;
        while (!done) {
          int tag = input.readTag();
          switch (tag) {
            case 0:
              done = true;
              break;
            default: {
              if (!parseUnknownField(input, unknownFields,
                                     extensionRegistry, tag)) {
                done = true;
              }
              break;
            }
            case 8: {
              bitField0_ |= 0x00000001;
              result_ = input.readInt32();
              break;
            }
          }
        }
      } catch (com.google.protobuf.InvalidProtocolBufferException e) {
        throw e.setUnfinishedMessage(this);
      } catch (java.io.IOException e) {
        throw new com.google.protobuf.InvalidProtocolBufferException(
            e.getMessage()).setUnfinishedMessage(this);
      } finally {
        this.unknownFields = unknownFields.build();
        makeExtensionsImmutable();
      }
    }
    public static final com.google.protobuf.Descriptors.Descriptor
        getDescriptor() {
      return org.tao.pbtest.proto.CalculatorMsg.internal_static_ResponseProto_descriptor;
    }

    protected com.google.protobuf.GeneratedMessage.FieldAccessorTable
        internalGetFieldAccessorTable() {
      return org.tao.pbtest.proto.CalculatorMsg.internal_static_ResponseProto_fieldAccessorTable
          .ensureFieldAccessorsInitialized(
              org.tao.pbtest.proto.CalculatorMsg.ResponseProto.class, org.tao.pbtest.proto.CalculatorMsg.ResponseProto.Builder.class);
    }

    public static com.google.protobuf.Parser<ResponseProto> PARSER =
        new com.google.protobuf.AbstractParser<ResponseProto>() {
      public ResponseProto parsePartialFrom(
          com.google.protobuf.CodedInputStream input,
          com.google.protobuf.ExtensionRegistryLite extensionRegistry)
          throws com.google.protobuf.InvalidProtocolBufferException {
        return new ResponseProto(input, extensionRegistry);
      }
    };

    @java.lang.Override
    public com.google.protobuf.Parser<ResponseProto> getParserForType() {
      return PARSER;
    }

    private int bitField0_;
    // required int32 result = 1;
    public static final int RESULT_FIELD_NUMBER = 1;
    private int result_;
    /**
     * required int32 result = 1;
     */
    public boolean hasResult() {
      return ((bitField0_ & 0x00000001) == 0x00000001);
    }
    /**
     * required int32 result = 1;
     */
    public int getResult() {
      return result_;
    }

    private void initFields() {
      result_ = 0;
    }
    private byte memoizedIsInitialized = -1;
    public final boolean isInitialized() {
      byte isInitialized = memoizedIsInitialized;
      if (isInitialized != -1) return isInitialized == 1;

      if (!hasResult()) {
        memoizedIsInitialized = 0;
        return false;
      }
      memoizedIsInitialized = 1;
      return true;
    }

    public void writeTo(com.google.protobuf.CodedOutputStream output)
                        throws java.io.IOException {
      getSerializedSize();
      if (((bitField0_ & 0x00000001) == 0x00000001)) {
        output.writeInt32(1, result_);
      }
      getUnknownFields().writeTo(output);
    }

    private int memoizedSerializedSize = -1;
    public int getSerializedSize() {
      int size = memoizedSerializedSize;
      if (size != -1) return size;

      size = 0;
      if (((bitField0_ & 0x00000001) == 0x00000001)) {
        size += com.google.protobuf.CodedOutputStream
          .computeInt32Size(1, result_);
      }
      size += getUnknownFields().getSerializedSize();
      memoizedSerializedSize = size;
      return size;
    }

    private static final long serialVersionUID = 0L;
    @java.lang.Override
    protected java.lang.Object writeReplace()
        throws java.io.ObjectStreamException {
      return super.writeReplace();
    }

    @java.lang.Override
    public boolean equals(final java.lang.Object obj) {
      if (obj == this) {
       return true;
      }
      if (!(obj instanceof org.tao.pbtest.proto.CalculatorMsg.ResponseProto)) {
        return super.equals(obj);
      }
      org.tao.pbtest.proto.CalculatorMsg.ResponseProto other = (org.tao.pbtest.proto.CalculatorMsg.ResponseProto) obj;

      boolean result = true;
      result = result && (hasResult() == other.hasResult());
      if (hasResult()) {
        result = result && (getResult()
            == other.getResult());
      }
      result = result &&
          getUnknownFields().equals(other.getUnknownFields());
      return result;
    }

    private int memoizedHashCode = 0;
    @java.lang.Override
    public int hashCode() {
      if (memoizedHashCode != 0) {
        return memoizedHashCode;
      }
      int hash = 41;
      hash = (19 * hash) + getDescriptorForType().hashCode();
      if (hasResult()) {
        hash = (37 * hash) + RESULT_FIELD_NUMBER;
        hash = (53 * hash) + getResult();
      }
      hash = (29 * hash) + getUnknownFields().hashCode();
      memoizedHashCode = hash;
      return hash;
    }

    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(
        com.google.protobuf.ByteString data)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(
        com.google.protobuf.ByteString data,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(byte[] data)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(
        byte[] data,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws com.google.protobuf.InvalidProtocolBufferException {
      return PARSER.parseFrom(data, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(java.io.InputStream input)
        throws java.io.IOException {
      return PARSER.parseFrom(input);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(
        java.io.InputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws java.io.IOException {
      return PARSER.parseFrom(input, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseDelimitedFrom(java.io.InputStream input)
        throws java.io.IOException {
      return PARSER.parseDelimitedFrom(input);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseDelimitedFrom(
        java.io.InputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws java.io.IOException {
      return PARSER.parseDelimitedFrom(input, extensionRegistry);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(
        com.google.protobuf.CodedInputStream input)
        throws java.io.IOException {
      return PARSER.parseFrom(input);
    }
    public static org.tao.pbtest.proto.CalculatorMsg.ResponseProto parseFrom(
        com.google.protobuf.CodedInputStream input,
        com.google.protobuf.ExtensionRegistryLite extensionRegistry)
        throws java.io.IOException {
      return PARSER.parseFrom(input, extensionRegistry);
    }

    public static Builder newBuilder() { return Builder.create(); }
    public Builder newBuilderForType() { return newBuilder(); }
    public static Builder newBuilder(org.tao.pbtest.proto.CalculatorMsg.ResponseProto prototype) {
      return newBuilder().mergeFrom(prototype);
    }
    public Builder toBuilder() { return newBuilder(this); }

    @java.lang.Override
    protected Builder newBuilderForType(
        com.google.protobuf.GeneratedMessage.BuilderParent parent) {
      Builder builder = new Builder(parent);
      return builder;
    }
    /**
     * Protobuf type {@code ResponseProto}
     */
    public static final class Builder extends
        com.google.protobuf.GeneratedMessage.Builder<Builder>
       implements org.tao.pbtest.proto.CalculatorMsg.ResponseProtoOrBuilder {
      public static final com.google.protobuf.Descriptors.Descriptor
          getDescriptor() {
        return org.tao.pbtest.proto.CalculatorMsg.internal_static_ResponseProto_descriptor;
      }

      protected com.google.protobuf.GeneratedMessage.FieldAccessorTable
          internalGetFieldAccessorTable() {
        return org.tao.pbtest.proto.CalculatorMsg.internal_static_ResponseProto_fieldAccessorTable
            .ensureFieldAccessorsInitialized(
                org.tao.pbtest.proto.CalculatorMsg.ResponseProto.class, org.tao.pbtest.proto.CalculatorMsg.ResponseProto.Builder.class);
      }

      // Construct using org.tao.pbtest.proto.CalculatorMsg.ResponseProto.newBuilder()
      private Builder() {
        maybeForceBuilderInitialization();
      }

      private Builder(
          com.google.protobuf.GeneratedMessage.BuilderParent parent) {
        super(parent);
        maybeForceBuilderInitialization();
      }
      private void maybeForceBuilderInitialization() {
        if (com.google.protobuf.GeneratedMessage.alwaysUseFieldBuilders) {
        }
      }
      private static Builder create() {
        return new Builder();
      }

      public Builder clear() {
        super.clear();
        result_ = 0;
        bitField0_ = (bitField0_ & ~0x00000001);
        return this;
      }

      public Builder clone() {
        return create().mergeFrom(buildPartial());
      }

      public com.google.protobuf.Descriptors.Descriptor
          getDescriptorForType() {
        return org.tao.pbtest.proto.CalculatorMsg.internal_static_ResponseProto_descriptor;
      }

      public org.tao.pbtest.proto.CalculatorMsg.ResponseProto getDefaultInstanceForType() {
        return org.tao.pbtest.proto.CalculatorMsg.ResponseProto.getDefaultInstance();
      }

      public org.tao.pbtest.proto.CalculatorMsg.ResponseProto build() {
        org.tao.pbtest.proto.CalculatorMsg.ResponseProto result = buildPartial();
        if (!result.isInitialized()) {
          throw newUninitializedMessageException(result);
        }
        return result;
      }

      public org.tao.pbtest.proto.CalculatorMsg.ResponseProto buildPartial() {
        org.tao.pbtest.proto.CalculatorMsg.ResponseProto result = new org.tao.pbtest.proto.CalculatorMsg.ResponseProto(this);
        int from_bitField0_ = bitField0_;
        int to_bitField0_ = 0;
        if (((from_bitField0_ & 0x00000001) == 0x00000001)) {
          to_bitField0_ |= 0x00000001;
        }
        result.result_ = result_;
        result.bitField0_ = to_bitField0_;
        onBuilt();
        return result;
      }

      public Builder mergeFrom(com.google.protobuf.Message other) {
        if (other instanceof org.tao.pbtest.proto.CalculatorMsg.ResponseProto) {
          return mergeFrom((org.tao.pbtest.proto.CalculatorMsg.ResponseProto)other);
        } else {
          super.mergeFrom(other);
          return this;
        }
      }

      public Builder mergeFrom(org.tao.pbtest.proto.CalculatorMsg.ResponseProto other) {
        if (other == org.tao.pbtest.proto.CalculatorMsg.ResponseProto.getDefaultInstance()) return this;
        if (other.hasResult()) {
          setResult(other.getResult());
        }
        this.mergeUnknownFields(other.getUnknownFields());
        return this;
      }

      public final boolean isInitialized() {
        if (!hasResult()) {

          return false;
        }
        return true;
      }

      public Builder mergeFrom(
          com.google.protobuf.CodedInputStream input,
          com.google.protobuf.ExtensionRegistryLite extensionRegistry)
          throws java.io.IOException {
        org.tao.pbtest.proto.CalculatorMsg.ResponseProto parsedMessage = null;
        try {
          parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry);
        } catch (com.google.protobuf.InvalidProtocolBufferException e) {
          parsedMessage = (org.tao.pbtest.proto.CalculatorMsg.ResponseProto) e.getUnfinishedMessage();
          throw e;
        } finally {
          if (parsedMessage != null) {
            mergeFrom(parsedMessage);
          }
        }
        return this;
      }
      private int bitField0_;

      // required int32 result = 1;
      private int result_ ;
      /**
       * required int32 result = 1;
       */
      public boolean hasResult() {
        return ((bitField0_ & 0x00000001) == 0x00000001);
      }
      /**
       * required int32 result = 1;
       */
      public int getResult() {
        return result_;
      }
      /**
       * required int32 result = 1;
       */
      public Builder setResult(int value) {
        bitField0_ |= 0x00000001;
        result_ = value;
        onChanged();
        return this;
      }
      /**
       * required int32 result = 1;
       */
      public Builder clearResult() {
        bitField0_ = (bitField0_ & ~0x00000001);
        result_ = 0;
        onChanged();
        return this;
      }

      // @@protoc_insertion_point(builder_scope:ResponseProto)
    }

    static {
      defaultInstance = new ResponseProto(true);
      defaultInstance.initFields();
    }

    // @@protoc_insertion_point(class_scope:ResponseProto)
  }

  private static com.google.protobuf.Descriptors.Descriptor
    internal_static_RequestProto_descriptor;
  private static
    com.google.protobuf.GeneratedMessage.FieldAccessorTable
      internal_static_RequestProto_fieldAccessorTable;
  private static com.google.protobuf.Descriptors.Descriptor
    internal_static_ResponseProto_descriptor;
  private static
    com.google.protobuf.GeneratedMessage.FieldAccessorTable
      internal_static_ResponseProto_fieldAccessorTable;

  public static com.google.protobuf.Descriptors.FileDescriptor
      getDescriptor() {
    return descriptor;
  }
  private static com.google.protobuf.Descriptors.FileDescriptor
      descriptor;
  static {
    java.lang.String[] descriptorData = {
      "\n\023CalculatorMsg.proto\">\n\014RequestProto\022\022\n" +
      "\nmethodName\030\001 \002(\t\022\014\n\004num1\030\002 \002(\005\022\014\n\004num2\030" +
      "\003 \002(\005\"\037\n\rResponseProto\022\016\n\006result\030\001 \002(\005B+" +
      "\n\024org.tao.pbtest.protoB\rCalculatorMsg\210\001\001" +
      "\240\001\001"
    };
    com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner =
      new com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() {
        public com.google.protobuf.ExtensionRegistry assignDescriptors(
            com.google.protobuf.Descriptors.FileDescriptor root) {
          descriptor = root;
          internal_static_RequestProto_descriptor =
            getDescriptor().getMessageTypes().get(0);
          internal_static_RequestProto_fieldAccessorTable = new
            com.google.protobuf.GeneratedMessage.FieldAccessorTable(
              internal_static_RequestProto_descriptor,
              new java.lang.String[] { "MethodName", "Num1", "Num2", });
          internal_static_ResponseProto_descriptor =
            getDescriptor().getMessageTypes().get(1);
          internal_static_ResponseProto_fieldAccessorTable = new
            com.google.protobuf.GeneratedMessage.FieldAccessorTable(
              internal_static_ResponseProto_descriptor,
              new java.lang.String[] { "Result", });
          return null;
        }
      };
    com.google.protobuf.Descriptors.FileDescriptor
      .internalBuildGeneratedFileFrom(descriptorData,
        new com.google.protobuf.Descriptors.FileDescriptor[] {
        }, assigner);
  }

  // @@protoc_insertion_point(outer_class_scope)
}


text:
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.

/*============================================================
**
**
**
**
**
** Purpose: Default way to read streams of resources on
** demand.
**
**         Version 2 support on October 6, 2003
**
===========================================================*/

namespace System.Resources
{
    using System;
    using System.IO;
    using System.Text;
    using System.Collections;
    using System.Collections.Generic;
    using System.Reflection;
    using System.Security;
    using System.Globalization;
    using System.Configuration.Assemblies;
    using System.Runtime.Versioning;
    using System.Diagnostics;
    using System.Diagnostics.Contracts;

    // Provides the default implementation of IResourceReader, reading
    // .resources file from the system default binary format.  This class
    // can be treated as an enumerator once.
    //
    // See the RuntimeResourceSet overview for details on the system
    // default file format.
    //

    internal struct ResourceLocator
    {
        internal Object _value;  // Can be null.  Consider WeakReference instead?
        internal int _dataPos;

        internal ResourceLocator(int dataPos, Object value)
        {
            _dataPos = dataPos;
            _value = value;
        }

        internal int DataPosition
        {
            get { return _dataPos; }
            //set { _dataPos = value; }
        }

        // Allows adding in profiling data in a future version, or a special
        // resource profiling build.  We could also use WeakReference.
        internal Object Value
        {
            get { return _value; }
            set { _value = value; }
        }

        internal static bool CanCache(ResourceTypeCode value)
        {
            Debug.Assert(value >= 0, "negative ResourceTypeCode.  What?");
            return value <= ResourceTypeCode.LastPrimitive;
        }
    }

    public sealed class ResourceReader : IResourceReader
    {
        // A reasonable default buffer size for reading from files, especially
        // when we will likely be seeking frequently.  Could be smaller, but does
        // it make sense to use anything less than one page?
        private const int DefaultFileStreamBufferSize = 4096;

        private BinaryReader _store;    // backing store we're reading from.
        // Used by RuntimeResourceSet and this class's enumerator.  Maps
        // resource name to a value, a ResourceLocator, or a
        // LooselyLinkedManifestResource.
        internal Dictionary<String, ResourceLocator> _resCache;
        private long _nameSectionOffset;  // Offset to name section of file.
        private long _dataSectionOffset;  // Offset to Data section of file.

        // Note this class is tightly coupled with UnmanagedMemoryStream.
        // At runtime when getting an embedded resource from an assembly,
        // we're given an UnmanagedMemoryStream referring to the mmap'ed portion
        // of the assembly.  The pointers here are pointers into that block of
        // memory controlled by the OS's loader.
        private int[] _nameHashes;    // hash values for all names.
        private unsafe int* _nameHashesPtr;  // In case we're using UnmanagedMemoryStream
        private int[] _namePositions; // relative locations of names
        private unsafe int* _namePositionsPtr;  // If we're using UnmanagedMemoryStream
        private RuntimeType[] _typeTable;    // Lazy array of Types for resource values.
        private int[] _typeNamePositions;  // To delay initialize type table
        private int _numResources;    // Num of resources files, in case arrays aren't allocated.

        // We'll include a separate code path that uses UnmanagedMemoryStream to
        // avoid allocating String objects and the like.
        private UnmanagedMemoryStream _ums;

        // Version number of .resources file, for compatibility
        private int _version;

#if RESOURCE_FILE_FORMAT_DEBUG
        private bool _debug;   // Whether this file has debugging stuff in it.
#endif

        public ResourceReader(String fileName)
        {
            _resCache = new Dictionary<String, ResourceLocator>(FastResourceComparer.Default);
            _store = new BinaryReader(new FileStream(fileName, FileMode.Open, FileAccess.Read, FileShare.Read, DefaultFileStreamBufferSize, FileOptions.RandomAccess), Encoding.UTF8);
            BCLDebug.Log("RESMGRFILEFORMAT", "ResourceReader .ctor(String).  UnmanagedMemoryStream: " + (_ums != null));

            try
            {
                ReadResources();
            }
            catch
            {
                _store.Close(); // If we threw an exception, close the file.
                throw;
            }
        }

        public ResourceReader(Stream stream)
        {
            if (stream == null)
                throw new ArgumentNullException(nameof(stream));
            if (!stream.CanRead)
                throw new ArgumentException(SR.Argument_StreamNotReadable);

            _resCache = new Dictionary<String, ResourceLocator>(FastResourceComparer.Default);
            _store = new BinaryReader(stream, Encoding.UTF8);
            // We have a faster code path for reading resource files from an assembly.
            _ums = stream as UnmanagedMemoryStream;

            BCLDebug.Log("RESMGRFILEFORMAT", "ResourceReader .ctor(Stream).  UnmanagedMemoryStream: " + (_ums != null));
            ReadResources();
        }

        // This is the constructor the RuntimeResourceSet calls,
        // passing in the stream to read from and the RuntimeResourceSet's
        // internal hash table (hash table of names with file offsets
        // and values, coupled to this ResourceReader).
        internal ResourceReader(Stream stream, Dictionary<String, ResourceLocator> resCache)
        {
            Debug.Assert(stream != null, "Need a stream!");
            Debug.Assert(stream.CanRead, "Stream should be readable!");
            Debug.Assert(resCache != null, "Need a Dictionary!");

            _resCache = resCache;
            _store = new BinaryReader(stream, Encoding.UTF8);

            _ums = stream as UnmanagedMemoryStream;

            BCLDebug.Log("RESMGRFILEFORMAT", "ResourceReader .ctor(Stream, Hashtable).  UnmanagedMemoryStream: " + (_ums != null));
            ReadResources();
        }

        public void Close()
        {
            Dispose(true);
        }

        public void Dispose()
        {
            Close();
        }

        private unsafe void Dispose(bool disposing)
        {
            if (_store != null)
            {
                _resCache = null;
                if (disposing)
                {
                    // Close the stream in a thread-safe way.  This fix means
                    // that we may call Close n times, but that's safe.
                    BinaryReader copyOfStore = _store;
                    _store = null;
                    if (copyOfStore != null)
                        copyOfStore.Close();
                }
                _store = null;
                _namePositions = null;
                _nameHashes = null;
                _ums = null;
                _namePositionsPtr = null;
                _nameHashesPtr = null;
            }
        }

        internal static unsafe int ReadUnalignedI4(int* p)
        {
            byte* buffer = (byte*)p;
            // Unaligned, little endian format
            return buffer[0] | (buffer[1] << 8) | (buffer[2] << 16) | (buffer[3] << 24);
        }

        private void SkipString()
        {
            int stringLength = _store.Read7BitEncodedInt();
            if (stringLength < 0)
            {
                throw new BadImageFormatException(SR.BadImageFormat_NegativeStringLength);
            }
            _store.BaseStream.Seek(stringLength, SeekOrigin.Current);
        }

        private unsafe int GetNameHash(int index)
        {
            Debug.Assert(index >= 0 && index < _numResources, "Bad index into hash array.  index: " + index);
            Debug.Assert((_ums == null && _nameHashes != null && _nameHashesPtr == null) ||
                            (_ums != null && _nameHashes == null && _nameHashesPtr != null), "Internal state mangled.");
            if (_ums == null)
                return _nameHashes[index];
            else
                return ReadUnalignedI4(&_nameHashesPtr[index]);
        }

        private unsafe int GetNamePosition(int index)
        {
            Debug.Assert(index >= 0 && index < _numResources, "Bad index into name position array.  index: " + index);
            Debug.Assert((_ums == null && _namePositions != null && _namePositionsPtr == null) ||
                            (_ums != null && _namePositions == null && _namePositionsPtr != null), "Internal state mangled.");
            int r;
            if (_ums == null)
                r = _namePositions[index];
            else
                r = ReadUnalignedI4(&_namePositionsPtr[index]);
            if (r < 0 || r > _dataSectionOffset - _nameSectionOffset)
            {
                throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesNameInvalidOffset, r));
            }
            return r;
        }

        IEnumerator IEnumerable.GetEnumerator()
        {
            return GetEnumerator();
        }

        public IDictionaryEnumerator GetEnumerator()
        {
            if (_resCache == null)
                throw new InvalidOperationException(SR.ResourceReaderIsClosed);
            return new ResourceEnumerator(this);
        }

        internal ResourceEnumerator GetEnumeratorInternal()
        {
            return new ResourceEnumerator(this);
        }

        // From a name, finds the associated virtual offset for the data.
        // To read the data, seek to _dataSectionOffset + dataPos, then
        // read the resource type & data.
        // This does a binary search through the names.
        internal int FindPosForResource(String name)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            int hash = FastResourceComparer.HashFunction(name);
            BCLDebug.Log("RESMGRFILEFORMAT", "FindPosForResource for " + name + "  hash: " + hash.ToString("x", CultureInfo.InvariantCulture));
            // Binary search over the hashes.  Use the _namePositions array to
            // determine where they exist in the underlying stream.
            int lo = 0;
            int hi = _numResources - 1;
            int index = -1;
            bool success = false;
            while (lo <= hi)
            {
                index = (lo + hi) >> 1;
                // Do NOT use subtraction here, since it will wrap for large
                // negative numbers.
                int currentHash = GetNameHash(index);
                int c;
                if (currentHash == hash)
                    c = 0;
                else if (currentHash < hash)
                    c = -1;
                else
                    c = 1;
                //BCLDebug.Log("RESMGRFILEFORMAT", "  Probing index "+index+"  lo: "+lo+"  hi: "+hi+"  c: "+c);
                if (c == 0)
                {
                    success = true;
                    break;
                }
                if (c < 0)
                    lo = index + 1;
                else
                    hi = index - 1;
            }
            if (!success)
            {
#if RESOURCE_FILE_FORMAT_DEBUG
                String lastReadString;
                lock(this) {
                    _store.BaseStream.Seek(_nameSectionOffset + GetNamePosition(index), SeekOrigin.Begin);
                    lastReadString = _store.ReadString();
                }
                BCLDebug.Log("RESMGRFILEFORMAT", LogLevel.Status, "FindPosForResource for ", name, " failed.  i: ", index, "  lo: ", lo, "  hi: ", hi, "  last read string: \"", lastReadString, '\'');
#endif
                return -1;
            }

            // index is the location in our hash array that corresponds with a
            // value in the namePositions array.
            // There could be collisions in our hash function.  Check on both sides
            // of index to find the range of hash values that are equal to the
            // target hash value.
            if (lo != index)
            {
                lo = index;
                while (lo > 0 && GetNameHash(lo - 1) == hash)
                    lo--;
            }
            if (hi != index)
            {
                hi = index;
                while (hi < _numResources - 1 && GetNameHash(hi + 1) == hash)
                    hi++;
            }

            lock (this)
            {
                for (int i = lo; i <= hi; i++)
                {
                    _store.BaseStream.Seek(_nameSectionOffset + GetNamePosition(i), SeekOrigin.Begin);
                    if (CompareStringEqualsName(name))
                    {
                        int dataPos = _store.ReadInt32();
                        if (dataPos < 0 || dataPos >= _store.BaseStream.Length - _dataSectionOffset)
                        {
                            throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesDataInvalidOffset, dataPos));
                        }
                        return dataPos;
                    }
                }
            }
            BCLDebug.Log("RESMGRFILEFORMAT", "FindPosForResource for " + name + ": Found a hash collision, HOWEVER, neither of these collided values equaled the given string.");
            return -1;
        }

        // This compares the String in the .resources file at the current position
        // with the string you pass in.
        // Whoever calls this method should make sure that they take a lock
        // so no one else can cause us to seek in the stream.
        private unsafe bool CompareStringEqualsName(String name)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            int byteLen = _store.Read7BitEncodedInt();
            if (byteLen < 0)
            {
                throw new BadImageFormatException(SR.BadImageFormat_NegativeStringLength);
            }
            if (_ums != null)
            {
                byte* bytes = _ums.PositionPointer;
                // Skip over the data in the Stream, positioning ourselves right after it.
                _ums.Seek(byteLen, SeekOrigin.Current);
                if (_ums.Position > _ums.Length)
                {
                    throw new BadImageFormatException(SR.BadImageFormat_ResourcesNameTooLong);
                }

                // On 64-bit machines, these char*'s may be misaligned.  Use a
                // byte-by-byte comparison instead.
                //return FastResourceComparer.CompareOrdinal((char*)bytes, byteLen/2, name) == 0;
                return FastResourceComparer.CompareOrdinal(bytes, byteLen, name) == 0;
            }
            else
            {
                // This code needs to be fast
                byte[] bytes = new byte[byteLen];
                int numBytesToRead = byteLen;
                while (numBytesToRead > 0)
                {
                    int n = _store.Read(bytes, byteLen - numBytesToRead, numBytesToRead);
                    if (n == 0)
                        throw new BadImageFormatException(SR.BadImageFormat_ResourceNameCorrupted);
                    numBytesToRead -= n;
                }
                return FastResourceComparer.CompareOrdinal(bytes, byteLen / 2, name) == 0;
            }
        }

        // This is used in the enumerator.  The enumerator iterates from 0 to n
        // of our resources and this returns the resource name for a particular
        // index.  The parameter is NOT a virtual offset.
        private unsafe String AllocateStringForNameIndex(int index, out int dataOffset)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            byte[] bytes;
            int byteLen;
            long nameVA = GetNamePosition(index);
            lock (this)
            {
                _store.BaseStream.Seek(nameVA + _nameSectionOffset, SeekOrigin.Begin);
                // Can't use _store.ReadString, since it's using UTF-8!
                byteLen = _store.Read7BitEncodedInt();
                if (byteLen < 0)
                {
                    throw new BadImageFormatException(SR.BadImageFormat_NegativeStringLength);
                }

                if (_ums != null)
                {
                    if (_ums.Position > _ums.Length - byteLen)
                        throw new BadImageFormatException(SR.Format(SR.BadImageFormat_ResourcesIndexTooLong, index));

                    String s = null;
                    char* charPtr = (char*)_ums.PositionPointer;

                    s = new String(charPtr, 0, byteLen / 2);

                    _ums.Position += byteLen;
                    dataOffset = _store.ReadInt32();
                    if (dataOffset < 0 || dataOffset >= _store.BaseStream.Length - _dataSectionOffset)
                    {
                        throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesDataInvalidOffset, dataOffset));
                    }
                    return s;
                }

                bytes = new byte[byteLen];
                // We must read byteLen bytes, or we have a corrupted file.
                // Use a blocking read in case the stream doesn't give us back
                // everything immediately.
                int count = byteLen;
                while (count > 0)
                {
                    int n = _store.Read(bytes, byteLen - count, count);
                    if (n == 0)
                        throw new EndOfStreamException(SR.Format(SR.BadImageFormat_ResourceNameCorrupted_NameIndex, index));
                    count -= n;
                }
                dataOffset = _store.ReadInt32();
                if (dataOffset < 0 || dataOffset >= _store.BaseStream.Length - _dataSectionOffset)
                {
                    throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesDataInvalidOffset, dataOffset));
                }
            }
            return Encoding.Unicode.GetString(bytes, 0, byteLen);
        }

        // This is used in the enumerator.  The enumerator iterates from 0 to n
        // of our resources and this returns the resource value for a particular
        // index.  The parameter is NOT a virtual offset.
        private Object GetValueForNameIndex(int index)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            long nameVA = GetNamePosition(index);
            lock (this)
            {
                _store.BaseStream.Seek(nameVA + _nameSectionOffset, SeekOrigin.Begin);
                SkipString();
                //BCLDebug.Log("RESMGRFILEFORMAT", "GetValueForNameIndex for index: "+index+"  skip (name length): "+skip);
                int dataPos = _store.ReadInt32();
                if (dataPos < 0 || dataPos >= _store.BaseStream.Length - _dataSectionOffset)
                {
                    throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesDataInvalidOffset, dataPos));
                }
                BCLDebug.Log("RESMGRFILEFORMAT", "GetValueForNameIndex: dataPos: " + dataPos);
                ResourceTypeCode junk;
                if (_version == 1)
                    return LoadObjectV1(dataPos);
                else
                    return LoadObjectV2(dataPos, out junk);
            }
        }

        // This takes a virtual offset into the data section and reads a String
        // from that location.
        // Anyone who calls LoadObject should make sure they take a lock so
        // no one can cause us to do a seek in here.
        internal String LoadString(int pos)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            _store.BaseStream.Seek(_dataSectionOffset + pos, SeekOrigin.Begin);
            String s = null;
            int typeIndex = _store.Read7BitEncodedInt();
            if (_version == 1)
            {
                if (typeIndex == -1)
                    return null;
                if (FindType(typeIndex) != typeof(String))
                    throw new InvalidOperationException(SR.Format(SR.InvalidOperation_ResourceNotString_Type, FindType(typeIndex).FullName));
                s = _store.ReadString();
            }
            else
            {
                ResourceTypeCode typeCode = (ResourceTypeCode)typeIndex;
                if (typeCode != ResourceTypeCode.String && typeCode != ResourceTypeCode.Null)
                {
                    String typeString;
                    if (typeCode < ResourceTypeCode.StartOfUserTypes)
                        typeString = typeCode.ToString();
                    else
                        typeString = FindType(typeCode - ResourceTypeCode.StartOfUserTypes).FullName;
                    throw new InvalidOperationException(SR.Format(SR.InvalidOperation_ResourceNotString_Type, typeString));
                }
                if (typeCode == ResourceTypeCode.String) // ignore Null
                    s = _store.ReadString();
            }
            BCLDebug.Log("RESMGRFILEFORMAT", "LoadString(" + pos.ToString("x", CultureInfo.InvariantCulture) + " returned " + (s == null ? "[a null string]" : s));
            return s;
        }

        // Called from RuntimeResourceSet
        internal Object LoadObject(int pos)
        {
            if (_version == 1)
                return LoadObjectV1(pos);
            ResourceTypeCode typeCode;
            return LoadObjectV2(pos, out typeCode);
        }

        internal Object LoadObject(int pos, out ResourceTypeCode typeCode)
        {
            if (_version == 1)
            {
                Object o = LoadObjectV1(pos);
                typeCode = (o is String) ? ResourceTypeCode.String : ResourceTypeCode.StartOfUserTypes;
                return o;
            }
            return LoadObjectV2(pos, out typeCode);
        }

        // This takes a virtual offset into the data section and reads an Object
        // from that location.
        // Anyone who calls LoadObject should make sure they take a lock so
        // no one can cause us to do a seek in here.
        internal Object LoadObjectV1(int pos)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            Debug.Assert(_version == 1, ".resources file was not a V1 .resources file!");

            try
            {
                // mega try-catch performs exceptionally bad on x64; factored out body into
                // _LoadObjectV1 and wrap here.
                return _LoadObjectV1(pos);
            }
            catch (EndOfStreamException eof)
            {
                throw new BadImageFormatException(SR.BadImageFormat_TypeMismatch, eof);
            }
            catch (ArgumentOutOfRangeException e)
            {
                throw new BadImageFormatException(SR.BadImageFormat_TypeMismatch, e);
            }
        }

        private Object _LoadObjectV1(int pos)
        {
            _store.BaseStream.Seek(_dataSectionOffset + pos, SeekOrigin.Begin);
            int typeIndex = _store.Read7BitEncodedInt();
            if (typeIndex == -1)
                return null;
            RuntimeType type = FindType(typeIndex);
            BCLDebug.Log("RESMGRFILEFORMAT", "LoadObject type: " + type.Name + "  pos: 0x" + _store.BaseStream.Position.ToString("x", CultureInfo.InvariantCulture));
            // Consider putting in logic to see if this type is a
            // primitive or a value type first, so we can reach the
            // deserialization code faster for arbitrary objects.

            if (type == typeof(String))
                return _store.ReadString();
            else if (type == typeof(Int32))
                return _store.ReadInt32();
            else if (type == typeof(Byte))
                return _store.ReadByte();
            else if (type == typeof(SByte))
                return _store.ReadSByte();
            else if (type == typeof(Int16))
                return _store.ReadInt16();
            else if (type == typeof(Int64))
                return _store.ReadInt64();
            else if (type == typeof(UInt16))
                return _store.ReadUInt16();
            else if (type == typeof(UInt32))
                return _store.ReadUInt32();
            else if (type == typeof(UInt64))
                return _store.ReadUInt64();
            else if (type == typeof(Single))
                return _store.ReadSingle();
            else if (type == typeof(Double))
                return _store.ReadDouble();
            else if (type == typeof(DateTime))
            {
                // Ideally we should use DateTime's ToBinary & FromBinary,
                // but we can't for compatibility reasons.
                return new DateTime(_store.ReadInt64());
            }
            else if (type == typeof(TimeSpan))
                return new TimeSpan(_store.ReadInt64());
            else if (type == typeof(Decimal))
            {
                int[] bits = new int[4];
                for (int i = 0; i < bits.Length; i++)
                    bits[i] = _store.ReadInt32();
                return new Decimal(bits);
            }
            else
            {
                throw new NotSupportedException(SR.NotSupported_ResourceObjectSerialization);
            }
        }

        internal Object LoadObjectV2(int pos, out ResourceTypeCode typeCode)
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");
            Debug.Assert(_version >= 2, ".resources file was not a V2 (or higher) .resources file!");

            try
            {
                // mega try-catch performs exceptionally bad on x64; factored out body into
                // _LoadObjectV2 and wrap here.
                return _LoadObjectV2(pos, out typeCode);
            }
            catch (EndOfStreamException eof)
            {
                throw new BadImageFormatException(SR.BadImageFormat_TypeMismatch, eof);
            }
            catch (ArgumentOutOfRangeException e)
            {
                throw new BadImageFormatException(SR.BadImageFormat_TypeMismatch, e);
            }
        }

        private Object _LoadObjectV2(int pos, out ResourceTypeCode typeCode)
        {
            _store.BaseStream.Seek(_dataSectionOffset + pos, SeekOrigin.Begin);
            typeCode = (ResourceTypeCode)_store.Read7BitEncodedInt();

            BCLDebug.Log("RESMGRFILEFORMAT", "LoadObjectV2 type: " + typeCode + "  pos: 0x" + _store.BaseStream.Position.ToString("x", CultureInfo.InvariantCulture));

            switch (typeCode)
            {
                case ResourceTypeCode.Null:
                    return null;

                case ResourceTypeCode.String:
                    return _store.ReadString();

                case ResourceTypeCode.Boolean:
                    return _store.ReadBoolean();

                case ResourceTypeCode.Char:
                    return (char)_store.ReadUInt16();

                case ResourceTypeCode.Byte:
                    return _store.ReadByte();

                case ResourceTypeCode.SByte:
                    return _store.ReadSByte();

                case ResourceTypeCode.Int16:
                    return _store.ReadInt16();

                case ResourceTypeCode.UInt16:
                    return _store.ReadUInt16();

                case ResourceTypeCode.Int32:
                    return _store.ReadInt32();

                case ResourceTypeCode.UInt32:
                    return _store.ReadUInt32();

                case ResourceTypeCode.Int64:
                    return _store.ReadInt64();

                case ResourceTypeCode.UInt64:
                    return _store.ReadUInt64();

                case ResourceTypeCode.Single:
                    return _store.ReadSingle();

                case ResourceTypeCode.Double:
                    return _store.ReadDouble();

                case ResourceTypeCode.Decimal:
                    return _store.ReadDecimal();

                case ResourceTypeCode.DateTime:
                    // Use DateTime's ToBinary & FromBinary.
                    Int64 data = _store.ReadInt64();
                    return DateTime.FromBinary(data);

                case ResourceTypeCode.TimeSpan:
                    Int64 ticks = _store.ReadInt64();
                    return new TimeSpan(ticks);

                // Special types
                case ResourceTypeCode.ByteArray:
                    {
                        int len = _store.ReadInt32();
                        if (len < 0)
                        {
                            throw new BadImageFormatException(SR.Format(SR.BadImageFormat_ResourceDataLengthInvalid, len));
                        }

                        if (_ums == null)
                        {
                            if (len > _store.BaseStream.Length)
                            {
                                throw new BadImageFormatException(SR.Format(SR.BadImageFormat_ResourceDataLengthInvalid, len));
                            }
                            return _store.ReadBytes(len);
                        }

                        if (len > _ums.Length - _ums.Position)
                        {
                            throw new BadImageFormatException(SR.Format(SR.BadImageFormat_ResourceDataLengthInvalid, len));
                        }

                        byte[] bytes = new byte[len];
                        int r = _ums.Read(bytes, 0, len);
                        Debug.Assert(r == len, "ResourceReader needs to use a blocking read here.  (Call _store.ReadBytes(len)?)");
                        return bytes;
                    }

                case ResourceTypeCode.Stream:
                    {
                        int len = _store.ReadInt32();
                        if (len < 0)
                        {
                            throw new BadImageFormatException(SR.Format(SR.BadImageFormat_ResourceDataLengthInvalid, len));
                        }
                        if (_ums == null)
                        {
                            byte[] bytes = _store.ReadBytes(len);
                            // Lifetime of memory == lifetime of this stream.
                            return new PinnedBufferMemoryStream(bytes);
                        }

                        // make sure we don't create an UnmanagedMemoryStream that is longer than the resource stream.
                        if (len > _ums.Length - _ums.Position)
                        {
                            throw new BadImageFormatException(SR.Format(SR.BadImageFormat_ResourceDataLengthInvalid, len));
                        }

                        // For the case that we've memory mapped in the .resources
                        // file, just return a Stream pointing to that block of memory.
                        unsafe
                        {
                            return new UnmanagedMemoryStream(_ums.PositionPointer, len, len, FileAccess.Read);
                        }
                    }

                default:
                    if (typeCode < ResourceTypeCode.StartOfUserTypes)
                    {
                        throw new BadImageFormatException(SR.BadImageFormat_TypeMismatch);
                    }
                    break;
            }

            // Normal serialized objects
            throw new NotSupportedException(SR.NotSupported_ResourceObjectSerialization);
        }

        // Reads in the header information for a .resources file.  Verifies some
        // of the assumptions about this resource set, and builds the class table
        // for the default resource file format.
        private void ReadResources()
        {
            Debug.Assert(_store != null, "ResourceReader is closed!");

            try
            {
                // mega try-catch performs exceptionally bad on x64; factored out body into
                // _ReadResources and wrap here.
                _ReadResources();
            }
            catch (EndOfStreamException eof)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted, eof);
            }
            catch (IndexOutOfRangeException e)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted, e);
            }
        }

        private void _ReadResources()
        {
            // Read ResourceManager header
            // Check for magic number
            int magicNum = _store.ReadInt32();
            if (magicNum != ResourceManager.MagicNumber)
                throw new ArgumentException(SR.Resources_StreamNotValid);
            // Assuming this is ResourceManager header V1 or greater, hopefully
            // after the version number there is a number of bytes to skip
            // to bypass the rest of the ResMgr header. For V2 or greater, we
            // use this to skip to the end of the header
            int resMgrHeaderVersion = _store.ReadInt32();
            int numBytesToSkip = _store.ReadInt32();
            if (numBytesToSkip < 0 || resMgrHeaderVersion < 0)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
            }
            if (resMgrHeaderVersion > 1)
            {
                BCLDebug.Log("RESMGRFILEFORMAT", LogLevel.Status, "ReadResources: Unexpected ResMgr header version: {0}  Skipping ahead {1} bytes.", resMgrHeaderVersion, numBytesToSkip);
                _store.BaseStream.Seek(numBytesToSkip, SeekOrigin.Current);
            }
            else
            {
                BCLDebug.Log("RESMGRFILEFORMAT", "ReadResources: Parsing ResMgr header v1.");
                // We don't care about numBytesToSkip; read the rest of the header

                // Read in type name for a suitable ResourceReader
                // Note ResourceWriter & InternalResGen use different Strings.
                String readerType = _store.ReadString();
                readerType = System.CoreLib.FixupCoreLibName(readerType);
                AssemblyName mscorlib = new AssemblyName(ResourceManager.MscorlibName);

                if (!ResourceManager.CompareNames(readerType, ResourceManager.ResReaderTypeName, mscorlib))
                    throw new NotSupportedException(SR.Format(SR.NotSupported_WrongResourceReader_Type, readerType));

                // Skip over type name for a suitable ResourceSet
                SkipString();
            }

            // Read RuntimeResourceSet header
            // Do file version check
            int version = _store.ReadInt32();
            if (version != RuntimeResourceSet.Version && version != 1)
                throw new ArgumentException(SR.Format(SR.Arg_ResourceFileUnsupportedVersion, RuntimeResourceSet.Version, version));
            _version = version;

#if RESOURCE_FILE_FORMAT_DEBUG
            // Look for ***DEBUG*** to see if this is a debuggable file.
            long oldPos = _store.BaseStream.Position;
            _debug = false;
            try {
                String debugString = _store.ReadString();
                _debug = String.Equals("***DEBUG***", debugString);
            }
            catch(IOException) {
            }
            catch(OutOfMemoryException) {
            }
            if (_debug) {
                Console.WriteLine("ResourceReader is looking at a debuggable .resources file, version {0}", _version);
            }
            else {
                _store.BaseStream.Position = oldPos;
            }
#endif

            _numResources = _store.ReadInt32();
            if (_numResources < 0)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
            }
            BCLDebug.Log("RESMGRFILEFORMAT", "ReadResources: Expecting " + _numResources + " resources.");
#if RESOURCE_FILE_FORMAT_DEBUG
            if (ResourceManager.DEBUG >= 4)
                Console.WriteLine("ResourceReader::ReadResources - Reading in "+_numResources+" resources");
#endif

            // Read type positions into type positions array.
            // But delay initialize the type table.
            int numTypes = _store.ReadInt32();
            if (numTypes < 0)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
            }
            _typeTable = new RuntimeType[numTypes];
            _typeNamePositions = new int[numTypes];
            for (int i = 0; i < numTypes; i++)
            {
                _typeNamePositions[i] = (int)_store.BaseStream.Position;

                // Skip over the Strings in the file.  Don't create types.
                SkipString();
            }

#if RESOURCE_FILE_FORMAT_DEBUG
                if (ResourceManager.DEBUG >= 5)
                    Console.WriteLine("ResourceReader::ReadResources - Reading in "+numTypes+" type table entries");
#endif

            // Prepare to read in the array of name hashes
            //  Note that the name hashes array is aligned to 8 bytes so
            //  we can use pointers into it on 64 bit machines. (4 bytes
            //  may be sufficient, but let's plan for the future)
            //  Skip over alignment stuff.  All public .resources files
            //  should be aligned   No need to verify the byte values.
            long pos = _store.BaseStream.Position;
            int alignBytes = ((int)pos) & 7;
            if (alignBytes != 0)
            {
                for (int i = 0; i < 8 - alignBytes; i++)
                {
                    _store.ReadByte();
                }
            }

            // Read in the array of name hashes
#if RESOURCE_FILE_FORMAT_DEBUG
                //  Skip over "HASHES->"
                if (_debug) {
                    _store.BaseStream.Position += 8;
                }
#endif

            if (_ums == null)
            {
                _nameHashes = new int[_numResources];
                for (int i = 0; i < _numResources; i++)
                {
                    _nameHashes[i] = _store.ReadInt32();
                }
            }
            else
            {
                int seekPos = unchecked(4 * _numResources);
                if (seekPos < 0)
                {
                    throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
                }
                unsafe
                {
                    _nameHashesPtr = (int*)_ums.PositionPointer;
                    // Skip over the array of nameHashes.
                    _ums.Seek(seekPos, SeekOrigin.Current);
                    // get the position pointer once more to check that the whole table is within the stream
                    byte* junk = _ums.PositionPointer;
                }
            }

            // Read in the array of relative positions for all the names.
#if RESOURCE_FILE_FORMAT_DEBUG
            // Skip over "POS---->"
            if (_debug) {
                _store.BaseStream.Position += 8;
            }
#endif
            if (_ums == null)
            {
                _namePositions = new int[_numResources];
                for (int i = 0; i < _numResources; i++)
                {
                    int namePosition = _store.ReadInt32();
                    if (namePosition < 0)
                    {
                        throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
                    }

                    _namePositions[i] = namePosition;
                }
            }
            else
            {
                int seekPos = unchecked(4 * _numResources);
                if (seekPos < 0)
                {
                    throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
                }
                unsafe
                {
                    _namePositionsPtr = (int*)_ums.PositionPointer;
                    // Skip over the array of namePositions.
                    _ums.Seek(seekPos, SeekOrigin.Current);
                    // get the position pointer once more to check that the whole table is within the stream
                    byte* junk = _ums.PositionPointer;
                }
            }

            // Read location of data section.
            _dataSectionOffset = _store.ReadInt32();
            if (_dataSectionOffset < 0)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
            }

            // Store current location as start of name section
            _nameSectionOffset = _store.BaseStream.Position;

            // _nameSectionOffset should be <= _dataSectionOffset; if not, it's corrupt
            if (_dataSectionOffset < _nameSectionOffset)
            {
                throw new BadImageFormatException(SR.BadImageFormat_ResourcesHeaderCorrupted);
            }

            BCLDebug.Log("RESMGRFILEFORMAT", String.Format(CultureInfo.InvariantCulture, "ReadResources: _nameOffset = 0x{0:x}  _dataOffset = 0x{1:x}", _nameSectionOffset, _dataSectionOffset));
        }

        // This allows us to delay-initialize the Type[].  This might be a
        // good startup time savings, since we might have to load assemblies
        // and initialize Reflection.
        private RuntimeType FindType(int typeIndex)
        {
            if (typeIndex < 0 || typeIndex >= _typeTable.Length)
            {
                throw new BadImageFormatException(SR.BadImageFormat_InvalidType);
            }
            if (_typeTable[typeIndex] == null)
            {
                long oldPos = _store.BaseStream.Position;
                try
                {
                    _store.BaseStream.Position = _typeNamePositions[typeIndex];
                    String typeName = _store.ReadString();
                    _typeTable[typeIndex] = (RuntimeType)Type.GetType(typeName, true);
                }
                // If serialization isn't supported, we convert FileNotFoundException to
                // NotSupportedException for consistency with v2. This is a corner-case, but the
                // idea is that we want to give the user a more accurate error message. Even if
                // the dependency were found, we know it will require serialization since it
                // can't be one of the types we special case. So if the dependency were found,
                // it would go down the serialization code path, resulting in NotSupported for
                // SKUs without serialization.
                //
                // We don't want to regress the expected case by checking the type info before
                // getting to Type.GetType -- this is costly with v1 resource formats.
                catch (FileNotFoundException)
                {
                    throw new NotSupportedException(SR.NotSupported_ResourceObjectSerialization);
                }
                finally
                {
                    _store.BaseStream.Position = oldPos;
                }
            }
            Debug.Assert(_typeTable[typeIndex] != null, "Should have found a type!");
            return _typeTable[typeIndex];
        }

        public void GetResourceData(String resourceName, out String resourceType, out byte[] resourceData)
        {
            if (resourceName == null)
                throw new ArgumentNullException(nameof(resourceName));
            if (_resCache == null)
                throw new InvalidOperationException(SR.ResourceReaderIsClosed);

            // Get the type information from the data section.  Also,
            // sort all of the data section's indexes to compute length of
            // the serialized data for this type (making sure to subtract
            // off the length of the type code).
            int[] sortedDataPositions = new int[_numResources];
            int dataPos = FindPosForResource(resourceName);
            if (dataPos == -1)
            {
                throw new ArgumentException(SR.Format(SR.Arg_ResourceNameNotExist, resourceName));
            }

            lock (this)
            {
                // Read all the positions of data within the data section.
                for (int i = 0; i < _numResources; i++)
                {
                    _store.BaseStream.Position = _nameSectionOffset + GetNamePosition(i);
                    // Skip over name of resource
                    int numBytesToSkip = _store.Read7BitEncodedInt();
                    if (numBytesToSkip < 0)
                    {
                        throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesNameInvalidOffset, numBytesToSkip));
                    }
                    _store.BaseStream.Position += numBytesToSkip;

                    int dPos = _store.ReadInt32();
                    if (dPos < 0 || dPos >= _store.BaseStream.Length - _dataSectionOffset)
                    {
                        throw new FormatException(SR.Format(SR.BadImageFormat_ResourcesDataInvalidOffset, dPos));
                    }
                    sortedDataPositions[i] = dPos;
                }
                Array.Sort(sortedDataPositions);

                int index = Array.BinarySearch(sortedDataPositions, dataPos);
                Debug.Assert(index >= 0 && index < _numResources, "Couldn't find data position within sorted data positions array!");
                long nextData = (index < _numResources - 1) ? sortedDataPositions[index + 1] + _dataSectionOffset : _store.BaseStream.Length;
                int len = (int)(nextData - (dataPos + _dataSectionOffset));
                Debug.Assert(len >= 0 && len <= (int)_store.BaseStream.Length - dataPos + _dataSectionOffset, "Length was negative or outside the bounds of the file!");

                // Read type code then byte[]
                _store.BaseStream.Position = _dataSectionOffset + dataPos;
                ResourceTypeCode typeCode = (ResourceTypeCode)_store.Read7BitEncodedInt();
                if (typeCode < 0 || typeCode >= ResourceTypeCode.StartOfUserTypes + _typeTable.Length)
                {
                    throw new BadImageFormatException(SR.BadImageFormat_InvalidType);
                }
                resourceType = TypeNameFromTypeCode(typeCode);

                // The length must be adjusted to subtract off the number
                // of bytes in the 7 bit encoded type code.
                len -= (int)(_store.BaseStream.Position - (_dataSectionOffset + dataPos));
                byte[] bytes = _store.ReadBytes(len);
                if (bytes.Length != len)
                    throw new FormatException(SR.BadImageFormat_ResourceNameCorrupted);
                resourceData = bytes;
            }
        }

        private String TypeNameFromTypeCode(ResourceTypeCode typeCode)
        {
            Debug.Assert(typeCode >= 0, "can't be negative");
            if (typeCode < ResourceTypeCode.StartOfUserTypes)
            {
                Debug.Assert(!String.Equals(typeCode.ToString(), "LastPrimitive"), "Change ResourceTypeCode metadata order so LastPrimitive isn't what Enum.ToString prefers.");
                return "ResourceTypeCode." + typeCode.ToString();
            }
            else
            {
                int typeIndex = typeCode - ResourceTypeCode.StartOfUserTypes;
                Debug.Assert(typeIndex >= 0 && typeIndex < _typeTable.Length, "TypeCode is broken or corrupted!");
                long oldPos = _store.BaseStream.Position;
                try
                {
                    _store.BaseStream.Position = _typeNamePositions[typeIndex];
                    return _store.ReadString();
                }
                finally
                {
                    _store.BaseStream.Position = oldPos;
                }
            }
        }

        internal sealed class ResourceEnumerator : IDictionaryEnumerator
        {
            private const int ENUM_DONE = Int32.MinValue;
            private const int ENUM_NOT_STARTED = -1;

            private ResourceReader _reader;
            private bool _currentIsValid;
            private int _currentName;
            private int _dataPosition; // cached for case-insensitive table

            internal ResourceEnumerator(ResourceReader reader)
            {
                _currentName = ENUM_NOT_STARTED;
                _reader = reader;
                _dataPosition = -2;
            }

            public bool MoveNext()
            {
                if (_currentName == _reader._numResources - 1 || _currentName == ENUM_DONE)
                {
                    _currentIsValid = false;
                    _currentName = ENUM_DONE;
                    return false;
                }
                _currentIsValid = true;
                _currentName++;
                return true;
            }

            public Object Key
            {
                get
                {
                    if (_currentName == ENUM_DONE) throw new InvalidOperationException(SR.InvalidOperation_EnumEnded);
                    if (!_currentIsValid) throw new InvalidOperationException(SR.InvalidOperation_EnumNotStarted);
                    if (_reader._resCache == null) throw new InvalidOperationException(SR.ResourceReaderIsClosed);

                    return _reader.AllocateStringForNameIndex(_currentName, out _dataPosition);
                }
            }

            public Object Current
            {
                get
                {
                    return Entry;
                }
            }

            // Warning: This requires that you call the Key or Entry property FIRST before calling it!
            internal int DataPosition
            {
                get
                {
                    return _dataPosition;
                }
            }

            public DictionaryEntry Entry
            {
                get
                {
                    if (_currentName == ENUM_DONE) throw new InvalidOperationException(SR.InvalidOperation_EnumEnded);
                    if (!_currentIsValid) throw new InvalidOperationException(SR.InvalidOperation_EnumNotStarted);
                    if (_reader._resCache == null) throw new InvalidOperationException(SR.ResourceReaderIsClosed);

                    String key;
                    Object value = null;
                    lock (_reader)
                    { // locks should be taken in the same order as in RuntimeResourceSet.GetObject to avoid deadlock
                        lock (_reader._resCache)
                        {
                            key = _reader.AllocateStringForNameIndex(_currentName, out _dataPosition); // AllocateStringForNameIndex could lock on _reader
                            ResourceLocator locator;
                            if (_reader._resCache.TryGetValue(key, out locator))
                            {
                                value = locator.Value;
                            }
                            if (value == null)
                            {
                                if (_dataPosition == -1)
                                    value = _reader.GetValueForNameIndex(_currentName);
                                else
                                    value = _reader.LoadObject(_dataPosition);
                                // If enumeration and subsequent lookups happen very
                                // frequently in the same process, add a ResourceLocator
                                // to _resCache here.  But WinForms enumerates and
                                // just about everyone else does lookups.  So caching
                                // here may bloat working set.
                            }
                        }
                    }
                    return new DictionaryEntry(key, value);
                }
            }

            public Object Value
            {
                get
                {
                    if (_currentName == ENUM_DONE) throw new InvalidOperationException(SR.InvalidOperation_EnumEnded);
                    if (!_currentIsValid) throw new InvalidOperationException(SR.InvalidOperation_EnumNotStarted);
                    if (_reader._resCache == null) throw new InvalidOperationException(SR.ResourceReaderIsClosed);

                    // Consider using _resCache here, eventually, if
                    // this proves to be an interesting perf scenario.
                    // But mixing lookups and enumerators shouldn't be
                    // particularly compelling.
                    return _reader.GetValueForNameIndex(_currentName);
                }
            }

            public void Reset()
            {
                if (_reader._resCache == null) throw new InvalidOperationException(SR.ResourceReaderIsClosed);
                _currentIsValid = false;
                _currentName = ENUM_NOT_STARTED;
            }
        }
    }
}

redpajama_set_name: RedPajamaGithub