// Copyright 2019 The Fuchsia Authors
//
// Use of this source code is governed by a MIT-style
// license that can be found in the LICENSE file or at
// https://opensource.org/licenses/MIT

#ifndef ZIRCON_SYSTEM_DEV_BUS_PCI_DEVICE_H_
#define ZIRCON_SYSTEM_DEV_BUS_PCI_DEVICE_H_

#include "allocation.h"
#include "capabilities.h"
#include "config.h"
#include "device_proxy.h"
#include "ref_counted.h"
#include <assert.h>
#include <ddktl/device.h>
#include <fbl/algorithm.h>
#include <fbl/intrusive_double_list.h>
#include <fbl/intrusive_wavl_tree.h>
#include <fbl/macros.h>
#include <fbl/mutex.h>
#include <fbl/ref_ptr.h>
#include <fbl/unique_ptr.h>
#include <hw/pci.h>
#include <lib/zx/channel.h>
#include <region-alloc/region-alloc.h>
#include <sys/types.h>
#include <zircon/compiler.h>
#include <zircon/errors.h>
#include <zircon/hw/pci.h>
#include <zircon/thread_annotations.h>

namespace pci {

// UpstreamNode includes device.h, so only forward declare it here.
class UpstreamNode;
class BusLinkInterface;

// A pci::Device represents a given PCI(e) device on a bus. It can be used
// standalone for a regular PCI(e) device on the bus, or as the base class for a
// Bridge. Most work a pci::Device does is limited to its own registers in
// configuration space and are managed through their Config object handled to it
// during creation. One of the biggest responsibilities of the pci::Device class
// is fulfill the PCI protocol for the driver downstream operating the PCI
// device this corresponds to.
class Device;
using PciDeviceType = ddk::Device<pci::Device, ddk::Rxrpcable>;
class Device : public PciDeviceType,
               public fbl::DoublyLinkedListable<Device*> {
public:
    using NodeState = fbl::WAVLTreeNodeState<fbl::RefPtr<pci::Device>>;
    struct BusListTraits {
        static NodeState& node_state(Device& device) {
            return device.bus_list_state_;
        }
    };

    // These traits are used for the WAVL tree implementation. They allow device objects
    // to be sorted and found in trees by composite bdf address.
    struct KeyTraitsSortByBdf {
        static const pci_bdf_t& GetKey(pci::Device& dev) {
            return dev.cfg_->bdf();
        }

        static bool LessThan(const pci_bdf_t& bdf1, const pci_bdf_t& bdf2) {
            return (bdf1.bus_id < bdf2.bus_id) ||
                   ((bdf1.bus_id == bdf2.bus_id) && (bdf1.device_id < bdf2.device_id)) ||
                   ((bdf1.bus_id == bdf2.bus_id) && (bdf1.device_id == bdf2.device_id) &&
                    (bdf1.function_id < bdf2.function_id));
        }

        static bool EqualTo(const pci_bdf_t& bdf1, const pci_bdf_t& bdf2) {
            return (bdf1.bus_id == bdf2.bus_id) && (bdf1.device_id == bdf2.device_id) &&
                   (bdf1.function_id == bdf2.function_id);
        }
    };

    // struct used to hold information about a configured base address register
    struct BarInfo {
        size_t size = 0;
        zx_paddr_t address = 0; // Allocated address for the bar
        bool is_mmio;
        bool is_64bit;
        bool is_prefetchable;
        uint32_t bar_id; // The bar index in the config space. If the bar is 64 bit
        // then this corresponds to the first half of the register pair
        fbl::unique_ptr<PciAllocation> allocation;
    };

    struct Capabilities {
        CapabilityList list;
        PciExpressCapability* pcie;
    };

    // DDKTL PciProtocol methods that will be called by Rxrpc.
    zx_status_t RpcConfigRead(const zx::unowned_channel& ch);
    zx_status_t RpcConfigWrite(const zx::unowned_channel& ch);
    zx_status_t RpcEnableBusMaster(const zx::unowned_channel& ch);
    zx_status_t RpcGetAuxdata(const zx::unowned_channel& ch);
    zx_status_t RpcGetBar(const zx::unowned_channel& ch);
    zx_status_t RpcGetBti(const zx::unowned_channel& ch);
    zx_status_t RpcGetDeviceInfo(const zx::unowned_channel& ch);
    zx_status_t RpcGetNextCapability(const zx::unowned_channel& ch);
    zx_status_t RpcMapInterrupt(const zx::unowned_channel& ch);
    zx_status_t RpcQueryIrqMode(const zx::unowned_channel& ch);
    zx_status_t RpcResetDevice(const zx::unowned_channel& ch);
    zx_status_t RpcSetIrqMode(const zx::unowned_channel& ch);
    zx_status_t DdkRxrpc(zx_handle_t channel);

    // DDK mix-in impls
    void DdkRelease() { delete this; }

    // Create, but do not initialize, a device.
    static zx_status_t Create(zx_device_t* parent,
                              fbl::RefPtr<Config>&& config,
                              UpstreamNode* upstream,
                              BusLinkInterface* bli);
    zx_status_t CreateProxy();
    virtual ~Device();

    // Bridge or DeviceImpl will need to implement refcounting
    PCI_REQUIRE_REFCOUNTED;

    // Disallow copying, assigning and moving.
    DISALLOW_COPY_ASSIGN_AND_MOVE(Device);

    // Trigger a function level reset (if possible)
    // TODO(cja): port zx_status_t DoFunctionLevelReset() when we have a way to test it

    // Modify bits in the device's command register (in the device config space),
    // clearing the bits specified by clr_bits and setting the bits specified by set
    // bits.  Specifically, the operation will be applied as...
    //
    // WR(cmd, (RD(cmd) & ~clr) | set)
    //
    // @param clr_bits The mask of bits to be cleared.
    // @param clr_bits The mask of bits to be set.
    // @return A zx_status_t indicating success or failure of the operation.
    zx_status_t ModifyCmd(uint16_t clr_bits, uint16_t set_bits) TA_EXCL(dev_lock_);

    // Enable or disable bus mastering in a device's configuration.
    //
    // @param enable If true, allow the device to access main system memory as a bus
    // master.
    // @return A zx_status_t indicating success or failure of the operation.
    zx_status_t EnableBusMaster(bool enabled) TA_EXCL(dev_lock_);

    // Enable or disable PIO access in a device's configuration.
    //
    // @param enable If true, allow the device to access its PIO mapped registers.
    // @return A zx_status_t indicating success or failure of the operation.
    zx_status_t EnablePio(bool enabled) TA_EXCL(dev_lock_);

    // Enable or disable MMIO access in a device's configuration.
    //
    // @param enable If true, allow the device to access its MMIO mapped registers.
    // @return A zx_status_t indicating success or failure of the operation.
    zx_status_t EnableMmio(bool enabled) TA_EXCL(dev_lock_);

    // Return information about the requested base address register, if it has been
    // allocated.
    //
    // @param bar_id The index of the BAR register to fetch info for
    // @param out_info A pointer to a BarInfo buffer to store the bar info
    //
    // @return ZX_OK on success, ZX_INVALID_ARGS if bad a bar bar index or
    // pointer is passed in, and ZX_BAD_STATE if the device is disabled.
    zx_status_t GetBarInfo(uint32_t bar_id, const BarInfo* out_info) const;

    // Requests a device unplug itself from its UpstreamNode and the Bus list.
    virtual void Unplug() TA_EXCL(dev_lock_);
    // TODO(cja): port void SetQuirksDone() TA_REQ(dev_lock_) { quirks_done_ = true; }
    const fbl::RefPtr<Config>& config() const { return cfg_; }

    bool plugged_in() const { return plugged_in_; }
    bool disabled() const { return disabled_; }
    bool quirks_done() const { return quirks_done_; }
    bool is_bridge() const { return is_bridge_; }
    uint16_t vendor_id() const { return vendor_id_; }
    uint16_t device_id() const { return device_id_; }
    uint8_t class_id() const { return class_id_; }
    uint8_t subclass() const { return subclass_; }
    uint8_t prog_if() const { return prog_if_; }
    uint8_t rev_id() const { return rev_id_; }
    uint8_t bus_id() const { return cfg_->bdf().bus_id; }
    uint8_t dev_id() const { return cfg_->bdf().device_id; }
    uint8_t func_id() const { return cfg_->bdf().function_id; }
    uint32_t bar_count() const { return bar_count_; }
    const CapabilityList& capabilities() const { return caps_.list; }

    // Dump some information about the device
    virtual void Dump() const;

    // Devices need to exist in both the top level bus driver class, as well
    // as in a list for roots/bridges to track their downstream children. These
    // traits facilitate that for us.
protected:
    Device(zx_device_t* parent,
           fbl::RefPtr<Config>&& config,
           UpstreamNode* upstream,
           BusLinkInterface* bli,
           bool is_bridge)
        : PciDeviceType(parent),
          is_bridge_(is_bridge),
          cfg_(std::move(config)),
          bar_count_(is_bridge ? PCI_BAR_REGS_PER_BRIDGE : PCI_BAR_REGS_PER_DEVICE),
          upstream_(upstream),
          bli_(bli) {}

    zx_status_t Init() TA_EXCL(dev_lock_);
    zx_status_t InitLocked() TA_REQ(dev_lock_);
    fbl::Mutex* dev_lock() { return &dev_lock_; }

    // Read the value of the Command register, requires the dev_lock.
    uint16_t ReadCmdLocked() TA_REQ(dev_lock_) TA_EXCL(cmd_reg_lock_) {
        fbl::AutoLock cmd_lock(&cmd_reg_lock_);
        return cfg_->Read(Config::kCommand);
    }
    void ModifyCmdLocked(uint16_t clr_bits, uint16_t set_bits)
        TA_REQ(dev_lock_) TA_EXCL(cmd_reg_lock_);
    void AssignCmdLocked(uint16_t value) TA_REQ(dev_lock_) TA_EXCL(cmd_reg_lock_) {
        ModifyCmdLocked(0xFFFF, value);
    }

    bool IoEnabled() TA_REQ(dev_lock_) {
        return ReadCmdLocked() & PCI_COMMAND_IO_EN;
    }

    bool MmioEnabled() TA_REQ(dev_lock_) {
        return ReadCmdLocked() & PCI_COMMAND_MEM_EN;
    }

    zx_status_t ProbeCapabilities() TA_REQ(dev_lock_);
    zx_status_t ParseCapabilities() TA_REQ(dev_lock_);
    // TODO(cja) port zx_status_t ParseExtendedCapabilities() TA_REQ(dev_lock_);

    fbl::Mutex cmd_reg_lock_;       // Protection for access to the command register.
    const bool is_bridge_;          // True if this device is also a bridge
    const fbl::RefPtr<Config> cfg_; // Pointer to the device's config interface.
    uint16_t vendor_id_;            // The device's vendor ID, as read from config
    uint16_t device_id_;            // The device's device ID, as read from config
    uint8_t class_id_;              // The device's class ID, as read from config.
    uint8_t subclass_;              // The device's subclass, as read from config.
    uint8_t prog_if_;               // The device's programming interface (from cfg)
    uint8_t rev_id_;                // The device's revision ID (from cfg)

    // State related to lifetime management.
    bool plugged_in_ = false;
    bool disabled_ = false;
    bool quirks_done_ = false;
    mutable fbl::Mutex dev_lock_;

    // Info about the BARs computed and cached during the initial setup/probe,
    // indexed by starting BAR register index.
    BarInfo bars_[PCI_MAX_BAR_REGS];
    const uint32_t bar_count_;

    // An upstream node will outlive its downstream devices
    UpstreamNode* upstream_; // The upstream node in the device graph.
    BusLinkInterface* const bli_;

private:
    zx_status_t RpcReply(const zx::unowned_channel& ch, zx_status_t st,
                         zx_handle_t* handles = nullptr, const uint32_t handle_cnt = 0);
    // Allow UpstreamNode implementations to Probe/Allocate/Configure/Disable.
    friend class UpstreamNode;
    friend class Bridge;
    friend class Root;
    // Probes a BAR's configuration. If it is already allocated it will try to
    // reserve the existing address window for it so that devices configured by system
    // firmware can be maintained as much as possible.
    zx_status_t ProbeBar(uint32_t bar_id) TA_REQ(dev_lock_);
    // Allocates address space for a BAR if it does not already exist.
    zx_status_t AllocateBar(uint32_t bar_id) TA_REQ(dev_lock_);
    // Called a device to configure (probe/allocate) its BARs
    zx_status_t ConfigureBarsLocked() TA_REQ(dev_lock_);
    // Called by an UpstreamNode to configure the BARs of a device downsteream.
    // Bridge implements it so it can allocate its bridge windows and own BARs before
    // configuring downstream BARs..
    virtual zx_status_t ConfigureBars() TA_EXCL(dev_lock_);

    // Disable a device, and anything downstream of it.  The device will
    // continue to enumerate, but users will only be able to access config (and
    // only in a read only fashion).  BAR windows, bus mastering, and interrupts
    // will all be disabled.
    virtual void Disable() TA_EXCL(dev_lock_);
    void DisableLocked() TA_REQ(dev_lock_);

    Capabilities caps_ = {};

    // IRQ structures
    // TODO(cja): Port over the IRQ support from kernel pci.

    // Used for Rxrpc / RpcReply for protocol buffers.
    PciRpcMsg request_;
    PciRpcMsg response_;

    // These allow a device to exist in an upstream node list as well
    // as the top level bus list of all devices.
    friend struct BusListTraits;
    friend struct UpstreamListTraits;
    NodeState bus_list_state_;
};

} // namespace pci

#endif // ZIRCON_SYSTEM_DEV_BUS_PCI_DEVICE_H_
