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

// A set of structs and interface methods designed to exercise fidl_encode,
// fidl_decode, and fidl_validate.

library fidl.test.coding.fuchsia;

protocol Handles {
    // Starting easy: just a handle.
    NonnullableHandle(handle h0);

    // Multiple handles!
    MultipleNonnullableHandles(uint32 data0, handle h0, uint64 data1, handle h1, handle h2, uint64 data2);
    MultipleNullableHandles(uint32 data0, handle? h0, uint64 data1, handle? h1, handle? h2, uint64 data2);
};

resource struct NonnullableHandleArray {
    array<handle>:4 handles;
};

protocol Arrays {
    ArrayOfNonnullableHandles(array<handle>:4 handles);
    ArrayOfNullableHandles(array<handle?>:4 handles);
    ArrayOfArrayOfNonnullableHandles(array<array<handle>:3>:4 handles);
    OutOfLineArrayOfNonnullableHandles(NonnullableHandleArray? handles);
};

protocol Strings {
    UnboundedNonnullableString(string s0);
    UnboundedNullableString(string? s0);
    Bounded32NonnullableString(string:32 s0);
    Bounded32NullableString(string:32? s0);
    MultipleNonnullableStrings(string s0, string s1);
    MultipleNullableStrings(string? s0, string? s1);
};

protocol Vectors {
    UnboundedNonnullableVectorOfHandles(vector<handle> vh0);
    UnboundedNullableVectorOfHandles(vector<handle>? vh0);
    Bounded32NonnullableVectorOfHandles(vector<handle>:32 vh0);
    Bounded32NullableVectorOfHandles(vector<handle>:32? vh0);
    MultipleNonnullableVectorsOfHandles(vector<handle> vh0, vector<handle> vh1);
    MultipleNullableVectorsOfHandles(vector<handle>? vh0, vector<handle>? vh1);
    UnboundedNonnullableVectorOfUint32s(vector<uint32> vu0);
    UnboundedNullableVectorOfUint32s(vector<uint32>? vu0);
    Bounded32NonnullableVectorOfUint32s(vector<uint32>:32 vu0);
    Bounded32NullableVectorOfUint32s(vector<uint32>:32? vu0);
    MultipleNonnullableVectorsOfUint32s(vector<uint32> vu0, vector<uint32> vu1);
    MultipleNullableVectorsOfUint32s(vector<uint32>? vu0, vector<uint32>? vu1);
};

resource union SingleHandleUnion {
    1: handle h0;
};

resource union MultipleHandlesUnion {
    1: handle h;
    2: array<handle>:2 hs;
    3: array<array<handle>:2>:2 hss;
};

resource union MaybeRecurse {
    1: handle h;
    2: MaybeRecurseHelper more;
};

// Unions cannot have nullable fields, so wrap it in a struct.
resource struct MaybeRecurseHelper {
    MaybeRecurse? more;
};

protocol Unions {
    SingleHandleUnion(SingleHandleUnion u);
    SingleHandleUnionPointer(SingleHandleUnion u);
    MultipleHandlesUnion(MultipleHandlesUnion u);
    MultipleHandlesUnionPointer(MultipleHandlesUnion? u);
    Recursion(MaybeRecurse u);
};

resource struct Inline3 {
    uint32 padding;
    handle h;
};

resource struct Inline2 {
    uint64 padding;
    Inline3 l3;
    handle h;
};

resource struct Inline1 {
    handle h;
    Inline2 l2;
    uint64 padding;
};

resource struct Inline0 {
    uint64 padding;
    Inline1 L1;
    handle h;
};

resource struct OutOfLine3 {
    uint32 padding;
    handle h;
};

resource struct OutOfLine2 {
    uint64 padding;
    OutOfLine3? l3_present;
    OutOfLine3? l3_absent;
    OutOfLine3 l3_inline;
};

resource struct OutOfLine1 {
    handle h;
    OutOfLine2? l2_present;
    OutOfLine2 l2_inline;
    OutOfLine2? l2_absent;
    uint64 padding;
};

resource struct OutOfLine0 {
    uint64 padding;
    OutOfLine1? l1_absent;
    OutOfLine1 l1_inline;
    handle h;
    OutOfLine1? l1_present;
};

protocol Structs {
    Inline(Inline0 l0);
    OutOfLine(OutOfLine0 l0);
};
