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

#ifndef SRC_MEDIA_AUDIO_BIN_IHDA_CODEC_STATE_H_
#define SRC_MEDIA_AUDIO_BIN_IHDA_CODEC_STATE_H_

#include <stddef.h>
#include <stdint.h>
#include <zircon/assert.h>
#include <zircon/types.h>

#include <memory>

#include <intel-hda/utils/codec-caps.h>
#include <intel-hda/utils/codec-commands.h>
#include <intel-hda/utils/codec-state.h>

namespace audio {
namespace intel_hda {

struct AudioWidgetState;
using AudioWidgetStatePtr = std::unique_ptr<AudioWidgetState>;

struct FunctionGroupState;
struct AudioFunctionGroupState;
using FunctionGroupStatePtr = std::unique_ptr<FunctionGroupState>;

struct PowerState {
  // Section 7.3.4.12 : Supported Power States
  uint32_t supported_states_;

  // Section 7.3.3.10 : Current power state
  uint8_t set_;
  uint8_t active_;
  bool error_;
  bool clock_stop_ok_;
  bool settings_reset_;
};

// Section 7.3.3.14.  Present only in nodes (function groups and widgets) whose
// capabilities indicate the ability to send unsolicited responses.
struct UnsolicitedResponseState {
  bool enabled() const { return (raw_data_ & 0x80) != 0; }
  uint8_t tag() const { return static_cast<uint8_t>(raw_data_ & 0x3f); }
  uint8_t raw_data_;
};

struct AudioWidgetState {
  struct StreamFormat {
    // Stream format bitfields documented in section 3.7.1
    static constexpr uint16_t FLAG_NON_PCM = (1u << 15);

    uint32_t BASE() const { return (raw_data_ & (1u << 14)) ? 44100 : 48000; }
    uint32_t CHAN() const { return (raw_data_ & 0xF) + 1; }
    uint32_t DIV() const { return ((raw_data_ >> 8) & 0x7) + 1; }
    uint32_t MULT() const {
      uint32_t bits = (raw_data_ >> 11) & 0x7;
      if (bits >= 4)
        return 0;
      return bits + 1;
    }
    uint32_t BITS() const {
      switch ((raw_data_ >> 4) & 0x7) {
        case 0:
          return 8u;
        case 1:
          return 16u;
        case 2:
          return 20u;
        case 3:
          return 24u;
        case 4:
          return 32u;
        default:
          return 0u;
      }
    }

    bool is_pcm() const { return (raw_data_ & FLAG_NON_PCM) == 0; }
    uint32_t sample_rate() const { return (BASE() * MULT()) / DIV(); }
    uint32_t channels() const { return CHAN(); }
    uint32_t bits_per_chan() const { return BITS(); }

    uint16_t raw_data_;
  };

  struct AmpState {
    uint8_t gain[2];
    bool mute[2];
  };

  struct ConnListEntry {
    bool range_;
    uint16_t nid_;
    AmpState amp_state_;
  };

  explicit AudioWidgetState(const AudioWidgetCaps& caps) : caps_(caps) {}

  const AudioWidgetCaps caps_;
  const AudioFunctionGroupState* afg_ = nullptr;
  uint16_t nid_;

  // Note: to simplify life, the widget struct contains the union of all of
  // the different field which may be needed for any type of audio widget.
  // Not all of the fields will be meaningful depending on the widget type.
  uint32_t pcm_size_rate_;  // Section 7.3.4.7 : Supported PCM sizes and rates
  uint32_t pcm_formats_;    // Section 7.3.4.8 : Supported PCM formats
  uint32_t pin_caps_ = 0;   // Section 7.3.4.9 : Pin Capabilities
  StreamFormat cur_format_;

  // Section 7.3.3.11 : Stream tag and channel routing for converters.
  uint8_t stream_tag_;
  uint8_t stream_chan_;

  // Section 7.3.4.10 : Amplifier capabilities
  AmpCaps input_amp_caps_;
  AmpCaps output_amp_caps_;

  // Section 7.3.3.7 : Amplifier Gain/Mute state
  AmpState input_amp_state_;
  AmpState output_amp_state_;

  // Sections 7.3.3.2, 7.3.3.3 & 7.3.4.11 : Connection List
  bool long_form_conn_list_;
  uint8_t conn_list_len_;
  std::unique_ptr<ConnListEntry[]> conn_list_;
  uint16_t connected_nid_;
  uint8_t connected_nid_ndx_;

  // Sections 7.3.4.12 & 7.3.3.10.
  PowerState power_;

  // Section 7.3.4.13 : Processing Capabilities
  bool can_bypass_processing_;
  uint8_t processing_coefficient_count_;

  // Section 7.3.4.15 : Volume Knob Capabilities
  bool vol_knob_is_delta_;
  uint8_t vol_knob_steps_;

  // Section 7.3.3.31.  Present only in pin complexes
  ConfigDefaults cfg_defaults_;

  // Section 7.3.3.12.  Present only in pin complexes
  PinWidgetCtrlState pin_widget_ctrl_;

  // Section 7.3.3.14.
  UnsolicitedResponseState unsol_resp_ctrl_;

  // Section 7.3.3.15
  //
  // Only valid for pin complexes, only run if the pin complex supports
  // presence detect and the config defaults do not indicate a jack detect
  // override.
  PinSenseState pin_sense_;
  bool pin_sense_valid_ = false;

  // Section 7.3.3.16 : External amp power down state
  EAPDState eapd_state_;
};

struct FunctionGroupState {
  virtual ~FunctionGroupState() {}

  enum class Type : uint8_t {
    AUDIO = 0x01,
    MODEM = 0x02,
    VENDOR_START = 0x80,
    VENDOR_END = 0xFF,
  };

  // Section 7.3.3.30
  struct ImplementationID {
    uint32_t BoardImplID() const { return (raw_data_ >> 8) & 0xFFFFFF; }
    uint16_t BoardMfrID() const { return static_cast<uint16_t>(raw_data_ >> 16); }
    uint8_t BoardSKU() const { return static_cast<uint8_t>((raw_data_ >> 8) & 0xFF); }
    uint8_t AssemblyID() const { return static_cast<uint8_t>(raw_data_ & 0xFF); }
    uint32_t raw_data_;
  };

  const Type type_;
  bool can_send_unsolicited_;
  uint16_t nid_;
  ImplementationID impl_id_;
  UnsolicitedResponseState unsol_resp_ctrl_;

 protected:
  explicit FunctionGroupState(Type type) : type_(type) {}
};

struct AudioFunctionGroupState : public FunctionGroupState {
  AudioFunctionGroupState() : FunctionGroupState(Type::AUDIO) {}

  AudioFunctionGroupCaps caps_;
  uint32_t default_pcm_size_rate_;  // Section 7.3.4.7 : Supported PCM sizes and rates
  uint32_t default_pcm_formats_;    // Section 7.3.4.8 : Supported PCM formats

  // Section 7.3.4.10 : Amplifier capabilities
  AmpCaps default_input_amp_caps_;
  AmpCaps default_output_amp_caps_;

  // Sections 7.3.4.12 & 7.3.3.10.
  PowerState power_;

  // Section 7.3.4.14 : GPIO Counts
  bool gpio_can_wake_;
  bool gpio_can_send_unsolicited_;
  uint8_t gpio_count_;
  uint8_t gpo_count_;
  uint8_t gpi_count_;

  uint8_t widget_count_ = 0;
  uint8_t widget_starting_id_ = 0;
  std::unique_ptr<AudioWidgetStatePtr[]> widgets_;
};

struct ModemFunctionGroupState : public FunctionGroupState {
  ModemFunctionGroupState() : FunctionGroupState(Type::MODEM) {}
};

struct VendorFunctionGroupState : public FunctionGroupState {
  explicit VendorFunctionGroupState(Type type) : FunctionGroupState(type) {
    ZX_DEBUG_ASSERT((type >= Type::VENDOR_START) && (type <= Type::VENDOR_START));
  }
};

struct CodecState {
  void reset() { fn_groups_ = nullptr; }

  uint16_t vendor_id_;
  uint16_t device_id_;

  uint8_t major_rev_;
  uint8_t minor_rev_;
  uint8_t vendor_rev_id_;
  uint8_t vendor_stepping_id_;

  uint8_t fn_group_count_;
  uint8_t fn_group_starting_id_;
  std::unique_ptr<FunctionGroupStatePtr[]> fn_groups_;
};

}  // namespace intel_hda
}  // namespace audio

#endif  // SRC_MEDIA_AUDIO_BIN_IHDA_CODEC_STATE_H_
