// 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.

#pragma once

#include <fbl/intrusive_double_list.h>
#include <fbl/vector.h>
#include <zircon/device/audio.h>
#include <zircon/hw/usb/audio.h>

#include <utility>

#include "usb-audio.h"
#include "usb-audio-descriptors.h"

namespace audio {
namespace usb {

class UsbAudioDevice;
class AudioPath;

class UsbAudioStreamInterface :
    public fbl::DoublyLinkedListable<fbl::unique_ptr<UsbAudioStreamInterface>> {
  public:
    // A small helper struct which maps from a Fuchsia format range to the
    // alternate interface ID which supports that range.
    struct FormatMapEntry {
        const audio_stream_format_range_t range_;

        // The alternate interface ID, endpoint address, and maximum request
        // size  which need to be used when configuring the stream interface to
        // use the format described by range_.
        const uint8_t alt_id_;
        const uint8_t ep_addr_;
        const uint16_t max_req_size_;

        FormatMapEntry(const audio_stream_format_range_t& range,
                       uint8_t alt_id,
                       uint8_t ep_addr,
                       uint16_t max_req_size)
            : range_(range),
              alt_id_(alt_id),
              ep_addr_(ep_addr),
              max_req_size_(max_req_size) {}
    };

    // Note that UsbAudioStreamInterfaces are entirely owned by UsbAudioDevice
    // instances.  The stream interface needs to hold a pointer to its parent,
    // so it is critically important that the owning parent is certain that
    // the stream interface (and all of its children) have been properly shut
    // down before exiting.  At all times, the lifetime of the stream interface
    // needs to be a subset of the lifetime of the device parent.
    //
    // Note, the iterator passed to the create method *must* be pointing at a
    // valid interface header with class == audio and subclass == streaming
    // interface.  The interface ID encountered in this first header will become
    // the interface ID of this StreamInterface object.
    static fbl::unique_ptr<UsbAudioStreamInterface>
        Create(UsbAudioDevice* parent, DescriptorListMemory::Iterator* iter);

    // Called to add a new alternate streaming interface to this StreamInterface
    // object.  The iterator must be pointing at a valid audio stream interface
    // descriptor which shares a an IID with this object.
    zx_status_t AddInterface(DescriptorListMemory::Iterator* iter);

    // Called after all of the interface descriptors have been discovered and
    // added to this stream interface to allow the stream interface a chance to
    // build its list of format ranges and the alternate interface ID which
    // support them.
    zx_status_t BuildFormatMap();

    // Called from the UsbAudioStream to lookup the index of a format which
    // matches the user's request.  Note, this does not actually cause the
    // interface to switch to this format.  Use ActivateFormat, passing the
    // index retrieved from there, to achieve that.
    zx_status_t LookupFormat(uint32_t frames_per_second,
                             uint16_t channels,
                             audio_sample_format_t sample_format,
                             size_t* out_format_ndx);

    // Called from the UsbAudioStream to activate the chosen format interface
    // and to configure the specific frame rate for that interface.
    zx_status_t ActivateFormat(size_t ndx, uint32_t frames_per_second);

    // Called from the UsbAudioStream to activate the alternate idle interface
    // (if any).  Will return ZX_ERR_NOT_SUPPORTED if there is no idle
    // interface.
    zx_status_t ActivateIdleFormat();

    // Called at the end of device probing to link a discovered audio path to
    // this stream interface.
    void LinkPath(fbl::unique_ptr<AudioPath> path);

    uint8_t iid() const { return iid_; }
    uint16_t max_req_size() const { return max_req_size_; }
    const fbl::unique_ptr<AudioPath>& path() { return path_; }
    const fbl::Vector<FormatMapEntry>& formats() { return  format_map_; }

    // Properties shared by all formats of this stream interface.
    uint8_t term_link() const { return term_link_; }
    uint8_t ep_addr()   const { return ep_addr_; }
    uint8_t ep_attr()   const { return ep_attr_; }

    Direction direction() const {
        return (ep_addr() & USB_ENDPOINT_DIR_MASK)
            ? Direction::Input
            : Direction::Output;
    }

    EndpointSyncType ep_sync_type() const {
        return static_cast<EndpointSyncType>(ep_attr() & USB_ENDPOINT_SYNCHRONIZATION_MASK);
    }

    // Accessor for debug logging.
    const char* log_prefix() const;

  private:
    friend class std::default_delete<UsbAudioStreamInterface>;

    // An internal helper class which contains all of the information we need to
    // support an alternate interface setting which supports a given format.
    class Format : public fbl::DoublyLinkedListable<fbl::unique_ptr<Format>> {
      public:
        Format(const UsbAudioStreamInterface* parent,
               fbl::RefPtr<DescriptorListMemory> desc_list,
               const usb_interface_descriptor_t* interface_hdr,
               const usb_audio_as_header_desc* class_hdr)
            : parent_(parent),
              desc_list_(std::move(desc_list)),
              interface_hdr_(interface_hdr),
              class_hdr_(class_hdr) {}

        const char* log_prefix()     const { return parent_->log_prefix(); }
        uint8_t     iid()            const { return interface_hdr_->bInterfaceNumber; }
        uint8_t     alt_id()         const { return interface_hdr_->bAlternateSetting; }
        uint8_t     term_link()      const { return class_hdr_->bTerminalLink; }
        uint16_t    format_tag()     const { return class_hdr_->wFormatTag; }
        uint8_t     ep_addr()        const { return ep_desc_->bEndpointAddress; }
        uint8_t     ep_attr()        const { return ep_desc_->bmAttributes; }
        uint16_t    max_req_size()   const { return ep_desc_->wMaxPacketSize; }
        uint8_t     frame_rate_cnt() const { return fmt_desc_->bSamFreqType; }
        uint8_t     ch_count()       const { return fmt_desc_->bNrChannels; }
        uint8_t     bit_resolution() const { return fmt_desc_->bBitResolution; }
        uint8_t     subframe_bytes() const { return fmt_desc_->bSubFrameSize; }

        // Min/Max continuous frame rates.  Valid *only* after initialize has
        // been successfully called, and *only* if frame_rate_cnt() == 0.
        uint32_t min_cont_frame_rate() const {
            ZX_DEBUG_ASSERT(frame_rate_cnt() == 0);
            return UnpackFrameRate(fmt_desc_->tSamFreq[0]);
        }

        uint32_t max_cont_frame_rate() const {
            ZX_DEBUG_ASSERT(frame_rate_cnt() == 0);
            return UnpackFrameRate(fmt_desc_->tSamFreq[1]);
        }

        // Fetch discrete frame rate #ndx.  Valid *only* after initialize has
        // been successfully called, and *only* if ndx < frame_rate_cnt()
        uint32_t frame_rate(uint8_t ndx) const {
            ZX_DEBUG_ASSERT(ndx < frame_rate_cnt());
            return UnpackFrameRate(fmt_desc_->tSamFreq[ndx]);
        }

        zx_status_t Init(DescriptorListMemory::Iterator* iter);

      private:
        friend class std::default_delete<Format>;
        ~Format() = default;

        // Packing format described in section 2.2.5 of USB Device Class
        // Definition for Audio Data Formats.
        static inline uint32_t UnpackFrameRate(const usb_audio_as_samp_freq& rate) {
            return (static_cast<uint32_t>(rate.freq[2]) << 16) |
                   (static_cast<uint32_t>(rate.freq[1]) <<  8) |
                    static_cast<uint32_t>(rate.freq[0]);
        }

        // Determined at construction time
        const UsbAudioStreamInterface* parent_;
        const fbl::RefPtr<DescriptorListMemory> desc_list_;
        const usb_interface_descriptor_t* const interface_hdr_;
        const usb_audio_as_header_desc* const class_hdr_;

        // Determined at initialization time
        const usb_audio_as_format_type_i_desc* fmt_desc_ = nullptr;
        const usb_endpoint_descriptor_t* ep_desc_ = nullptr;
        const usb_audio_as_isoch_ep_desc* class_ep_desc_ = nullptr;
    };

    UsbAudioStreamInterface(UsbAudioDevice* parent,
                            fbl::RefPtr<DescriptorListMemory> desc_list,
                            uint8_t iid)
        : parent_(*parent),
          iid_(iid),
          desc_list_(std::move(desc_list)) {
        ZX_DEBUG_ASSERT(parent != nullptr);
    }
    ~UsbAudioStreamInterface() = default;

    // The reference to our parent.  Note, because of this unmanaged reference,
    // it is critically important that the surrounding code ensure that we never
    // outlive our parent device.
    UsbAudioDevice& parent_;

    // The unique interface ID for this group of alternate interface descriptions.
    const uint8_t iid_;

    // Cached, unmanaged pointers to our interface and class descriptors.  The
    // memory which backs these descriptors is kept alive by the top level
    // desc_list_ reference.
    //
    // TODO(johngro) : this desc_list_ memory is contained in our parent
    // UsbAudioDevice.  Since we have already committed to having a lifetime
    // which is strictly <= the lifetime of our parent, we should probably just
    // access the descriptor memory using our parent instead of holding our own
    // reference to it.
    const fbl::RefPtr<DescriptorListMemory> desc_list_;

    // A pointer to an "idle" interface; IOW an interface which defines no
    // endpoints.  While not all audio streaming interfaces have one of these,
    // many seem to.  In theory, this allows a stream interface to save
    // isochronos bandwidth by selecting an alternate interface which requires
    // no isoch bandwidth allocation when the device is idle.
    const usb_interface_descriptor_t* idle_hdr_ = nullptr;

    // The terminal link ID which is shared by all of the valid formats we have
    // discovered.
    uint8_t term_link_ = 0xFF;

    // The endpoint address and attributes which are shared by all of the valid
    // formats we have discovered.
    uint8_t ep_addr_ = 0xFF;
    uint8_t ep_attr_ = 0x0;

    // The largest maximum request size computed across all of our discovered
    // endpoints.
    uint16_t max_req_size_ = 0;

    // A list of the formats (generic descriptors followed by a class specific
    // interface descriptor) we have discovered.
    fbl::DoublyLinkedList<fbl::unique_ptr<Format>> formats_;

    // The path through the control interface's terminal/unit graph that this
    // streaming interface is linked to.
    fbl::unique_ptr<AudioPath> path_;

    // A vector which contains the mappings from Fuchsia format ranges to the
    // alternate interface ID of the interface which supports that format range.
    fbl::Vector<FormatMapEntry> format_map_;
};

}  // namespace usb
}  // namespace audio

