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

// This file is autogenerated by:
//     mojo/public/tools/bindings/mojom_bindings_generator.py
// For:
//     mojom/vanadium/discovery.mojom
//

package io.v.mojo.discovery;

public final class Service extends org.chromium.mojo.bindings.Struct {

    private static final int STRUCT_SIZE = 56;
    private static final org.chromium.mojo.bindings.DataHeader[] VERSION_ARRAY = new org.chromium.mojo.bindings.DataHeader[] {new org.chromium.mojo.bindings.DataHeader(56, 0)};
    private static final org.chromium.mojo.bindings.DataHeader DEFAULT_STRUCT_INFO = VERSION_ARRAY[0];

    public String instanceId;
    public String instanceName;
    public String interfaceName;
    public java.util.Map<String, String> attrs;
    public String[] addrs;
    public java.util.Map<String, byte[]> attachments;

    private Service(int version) {
        super(STRUCT_SIZE, version);
    }

    public Service() {
        this(0);
    }

    public static Service deserialize(org.chromium.mojo.bindings.Message message) {
        return decode(new org.chromium.mojo.bindings.Decoder(message));
    }

    @SuppressWarnings("unchecked")
    public static Service decode(org.chromium.mojo.bindings.Decoder decoder0) {
        if (decoder0 == null) {
            return null;
        }
        org.chromium.mojo.bindings.DataHeader mainDataHeader = decoder0.readAndValidateDataHeader(VERSION_ARRAY);
        Service result = new Service(mainDataHeader.elementsOrVersion);
        if (mainDataHeader.elementsOrVersion >= 0) {
            result.instanceId = decoder0.readString(8, true);
        }
        if (mainDataHeader.elementsOrVersion >= 0) {
            result.instanceName = decoder0.readString(16, true);
        }
        if (mainDataHeader.elementsOrVersion >= 0) {
            result.interfaceName = decoder0.readString(24, false);
        }
        if (mainDataHeader.elementsOrVersion >= 0) {
            org.chromium.mojo.bindings.Decoder decoder1 = decoder0.readPointer(32, true);
            if (decoder1 == null) {
                result.attrs = null;
            } else {
                decoder1.readDataHeaderForMap();
                String[] keys0;
                String[] values0;
                {
                    org.chromium.mojo.bindings.Decoder decoder2 = decoder1.readPointer(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE, false);
                    {
                        org.chromium.mojo.bindings.DataHeader si2 = decoder2.readDataHeaderForPointerArray(org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                        keys0 = new String[si2.elementsOrVersion];
                        for (int i2 = 0; i2 < si2.elementsOrVersion; ++i2) {
                            keys0[i2] = decoder2.readString(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i2, false);
                        }
                    }
                }
                {
                    org.chromium.mojo.bindings.Decoder decoder2 = decoder1.readPointer(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE, false);
                    {
                        org.chromium.mojo.bindings.DataHeader si2 = decoder2.readDataHeaderForPointerArray(keys0.length);
                        values0 = new String[si2.elementsOrVersion];
                        for (int i2 = 0; i2 < si2.elementsOrVersion; ++i2) {
                            values0[i2] = decoder2.readString(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i2, false);
                        }
                    }
                }
                result.attrs = new java.util.HashMap<String, String>();
                for (int index0 = 0; index0 < keys0.length; ++index0) {
                    result.attrs.put(keys0[index0],  values0[index0]);
                }
            }
        }
        if (mainDataHeader.elementsOrVersion >= 0) {
            org.chromium.mojo.bindings.Decoder decoder1 = decoder0.readPointer(40, false);
            {
                org.chromium.mojo.bindings.DataHeader si1 = decoder1.readDataHeaderForPointerArray(org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                result.addrs = new String[si1.elementsOrVersion];
                for (int i1 = 0; i1 < si1.elementsOrVersion; ++i1) {
                    result.addrs[i1] = decoder1.readString(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i1, false);
                }
            }
        }
        if (mainDataHeader.elementsOrVersion >= 0) {
            org.chromium.mojo.bindings.Decoder decoder1 = decoder0.readPointer(48, true);
            if (decoder1 == null) {
                result.attachments = null;
            } else {
                decoder1.readDataHeaderForMap();
                String[] keys0;
                byte[][] values0;
                {
                    org.chromium.mojo.bindings.Decoder decoder2 = decoder1.readPointer(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE, false);
                    {
                        org.chromium.mojo.bindings.DataHeader si2 = decoder2.readDataHeaderForPointerArray(org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                        keys0 = new String[si2.elementsOrVersion];
                        for (int i2 = 0; i2 < si2.elementsOrVersion; ++i2) {
                            keys0[i2] = decoder2.readString(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i2, false);
                        }
                    }
                }
                {
                    org.chromium.mojo.bindings.Decoder decoder2 = decoder1.readPointer(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE, false);
                    {
                        org.chromium.mojo.bindings.DataHeader si2 = decoder2.readDataHeaderForPointerArray(keys0.length);
                        values0 = new byte[si2.elementsOrVersion][];
                        for (int i2 = 0; i2 < si2.elementsOrVersion; ++i2) {
                            values0[i2] = decoder2.readBytes(org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i2, org.chromium.mojo.bindings.BindingsHelper.NOTHING_NULLABLE, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                        }
                    }
                }
                result.attachments = new java.util.HashMap<String, byte[]>();
                for (int index0 = 0; index0 < keys0.length; ++index0) {
                    result.attachments.put(keys0[index0],  values0[index0]);
                }
            }
        }
        return result;
    }

    @SuppressWarnings("unchecked")
    @Override
    protected final void encode(org.chromium.mojo.bindings.Encoder encoder) {
        org.chromium.mojo.bindings.Encoder encoder0 = encoder.getEncoderAtDataOffset(DEFAULT_STRUCT_INFO);
        encoder0.encode(instanceId, 8, true);
        encoder0.encode(instanceName, 16, true);
        encoder0.encode(interfaceName, 24, false);
        if (attrs == null) {
            encoder0.encodeNullPointer(32, true);
        } else {
            org.chromium.mojo.bindings.Encoder encoder1 = encoder0.encoderForMap(32);
            int size0 = attrs.size();
            String[] keys0 = new String[size0];
            String[] values0 = new String[size0];
            int index0 = 0;
            for (java.util.Map.Entry<String, String> entry0 : attrs.entrySet()) {
                keys0[index0] = entry0.getKey();
                values0[index0] = entry0.getValue();
                ++index0;
            }
            {
                org.chromium.mojo.bindings.Encoder encoder2 = encoder1.encodePointerArray(keys0.length, org.chromium.mojo.bindings.DataHeader.HEADER_SIZE, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                for (int i1 = 0; i1 < keys0.length; ++i1) {
                    encoder2.encode(keys0[i1], org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i1, false);
                }
            }
            {
                org.chromium.mojo.bindings.Encoder encoder2 = encoder1.encodePointerArray(values0.length, org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                for (int i1 = 0; i1 < values0.length; ++i1) {
                    encoder2.encode(values0[i1], org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i1, false);
                }
            }
        }
        if (addrs == null) {
            encoder0.encodeNullPointer(40, false);
        } else {
            org.chromium.mojo.bindings.Encoder encoder1 = encoder0.encodePointerArray(addrs.length, 40, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
            for (int i0 = 0; i0 < addrs.length; ++i0) {
                encoder1.encode(addrs[i0], org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i0, false);
            }
        }
        if (attachments == null) {
            encoder0.encodeNullPointer(48, true);
        } else {
            org.chromium.mojo.bindings.Encoder encoder1 = encoder0.encoderForMap(48);
            int size0 = attachments.size();
            String[] keys0 = new String[size0];
            byte[][] values0 = new byte[size0][];
            int index0 = 0;
            for (java.util.Map.Entry<String, byte[]> entry0 : attachments.entrySet()) {
                keys0[index0] = entry0.getKey();
                values0[index0] = entry0.getValue();
                ++index0;
            }
            {
                org.chromium.mojo.bindings.Encoder encoder2 = encoder1.encodePointerArray(keys0.length, org.chromium.mojo.bindings.DataHeader.HEADER_SIZE, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                for (int i1 = 0; i1 < keys0.length; ++i1) {
                    encoder2.encode(keys0[i1], org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i1, false);
                }
            }
            {
                org.chromium.mojo.bindings.Encoder encoder2 = encoder1.encodePointerArray(values0.length, org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                for (int i1 = 0; i1 < values0.length; ++i1) {
                    encoder2.encode(values0[i1], org.chromium.mojo.bindings.DataHeader.HEADER_SIZE + org.chromium.mojo.bindings.BindingsHelper.POINTER_SIZE * i1, org.chromium.mojo.bindings.BindingsHelper.NOTHING_NULLABLE, org.chromium.mojo.bindings.BindingsHelper.UNSPECIFIED_ARRAY_LENGTH);
                }
            }
        }
    }

    /**
     * @see Object#equals(Object)
     */
    @Override
    public boolean equals(Object object) {
        if (object == this)
            return true;
        if (object == null)
            return false;
        if (getClass() != object.getClass())
            return false;
        Service other = (Service) object;
        if (!org.chromium.mojo.bindings.BindingsHelper.equals(this.instanceId, other.instanceId))
            return false;
        if (!org.chromium.mojo.bindings.BindingsHelper.equals(this.instanceName, other.instanceName))
            return false;
        if (!org.chromium.mojo.bindings.BindingsHelper.equals(this.interfaceName, other.interfaceName))
            return false;
        if (!org.chromium.mojo.bindings.BindingsHelper.equals(this.attrs, other.attrs))
            return false;
        if (!java.util.Arrays.deepEquals(this.addrs, other.addrs))
            return false;
        if (!org.chromium.mojo.bindings.BindingsHelper.equals(this.attachments, other.attachments))
            return false;
        return true;
    }

    /**
     * @see Object#hashCode()
     */
    @Override
    public int hashCode() {
        final int prime = 31;
        int result = prime + getClass().hashCode();
        result = prime * result + org.chromium.mojo.bindings.BindingsHelper.hashCode(instanceId);
        result = prime * result + org.chromium.mojo.bindings.BindingsHelper.hashCode(instanceName);
        result = prime * result + org.chromium.mojo.bindings.BindingsHelper.hashCode(interfaceName);
        result = prime * result + org.chromium.mojo.bindings.BindingsHelper.hashCode(attrs);
        result = prime * result + java.util.Arrays.deepHashCode(addrs);
        result = prime * result + org.chromium.mojo.bindings.BindingsHelper.hashCode(attachments);
        return result;
    }
}

