// Copyright 2018 The Chromium OS 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 SMBPROVIDER_MOUNT_TRACKER_H_
#define SMBPROVIDER_MOUNT_TRACKER_H_

#include <memory>
#include <string>
#include <unordered_map>
#include <unordered_set>
#include <utility>

#include <base/callback.h>
#include <base/time/tick_clock.h>
#include <libpasswordprovider/password.h>

#include "smbprovider/constants.h"
#include "smbprovider/id_map.h"
#include "smbprovider/metadata_cache.h"
#include "smbprovider/samba_interface.h"
#include "smbprovider/smb_credential.h"
#include "smbprovider/smbprovider_helper.h"

namespace smbprovider {

class MountTracker {
 public:
  MountTracker(std::unique_ptr<base::TickClock> tick_clock,
               bool metadata_cache_enabled);
  MountTracker(const MountTracker&) = delete;
  MountTracker& operator=(const MountTracker&) = delete;

  ~MountTracker();

  // Returns true if |mount_id| is already mounted.
  bool IsAlreadyMounted(int32_t mount_id) const;

  // Return true if |samba_interface_id| is already mounted.
  bool IsAlreadyMounted(
      const SambaInterface::SambaInterfaceId samba_interface_id) const;

  // Adds |mount_root| to the |mounts_| map and adds SambaInterfaceId to
  // |samba_interface_map_|.  Ids are >=0 and are not re-used within the
  // lifetime of this class.
  // TODO(zentaro): Review if this should have a maximum number of mounts,
  // even if it is relatively large. It may already be enforced at a higher
  // level.
  void AddMount(const std::string& mount_root,
                SmbCredential credential,
                std::unique_ptr<SambaInterface> samba_interface,
                int32_t* mount_id);

  // Returns true if |mount_id| was mounted and removes the mount. Returns false
  // if |mount_id| does not exist in |mounts_|.
  bool RemoveMount(int32_t mount_id);

  // Uses the mount root associated with |mount_id| and appends |entry_path|
  // to form |full_path|. Returns true if |full_path| has been properly appended
  // with the full path. Returns false if |mount_id| does not exist in
  // |mounts_|.
  bool GetFullPath(int32_t mount_id,
                   const std::string& entry_path,
                   std::string* full_path) const;

  // Gets the mount root of the mount associated with |mount_id|. Returns false
  // if |mount_id| does not exist in |mounts_|.
  bool GetMountRootPath(int32_t mount_id, std::string* mount_root) const;

  // Uses the mount root associated with |mount_id| to remove the root path
  // from |full_path| to yield a relative path.
  std::string GetRelativePath(int32_t mount_id,
                              const std::string& full_path) const;

  // Returns the number of mounts.
  size_t MountCount() const { return mounts_.Count(); }

  // Returns the SmbCredential for |samba_interface_id|. A SambaInterfaceId must
  // exist for this function.
  // TODO(jimmyxgong): Change this function to return a bool and have an out
  // parameter for an SmbCredential.
  const SmbCredential& GetCredential(
      SambaInterface::SambaInterfaceId samba_interface_id) const;

  // Gives a pointer to the SambaInterface corresponding to |mount_id|.
  // Returns true if |samba_interface| points to an existing SambaInterface
  // pointer. Returns false if |mount_id| does not exist in |mounts_|.
  bool GetSambaInterface(int32_t mount_id,
                         SambaInterface** samba_interface) const;

  // Gets a pointer to the metadata cache for |mount_id|. Returns true if
  // getting metadata cache succeeds. Returns false if |mount_id| does not
  // exist in |mounts_|.
  bool GetMetadataCache(int32_t mount_id, MetadataCache** cache) const;

  // Updates the SmbCredential within MountInfo. Returns true if updating mount
  // credentials succeeds. Returns false if |mount_id| does not exist in
  // |mounts_|.
  bool UpdateCredential(int32_t mount_id, SmbCredential credential);

  // Updates the share_path of a mount. Returns true if updating a mount's share
  // path succeeds. Returns false if |mount_id| does not exist in |mounts_|.
  bool UpdateSharePath(int32_t mount_id, const std::string& share_path);

 private:
  // Maintains the state of a single mount. Contains the mount root path and
  // the metadata cache.
  struct MountInfo {
    MountInfo() = default;
    MountInfo(MountInfo&& other) = default;
    MountInfo(const std::string& mount_root,
              base::TickClock* tick_clock,
              SmbCredential credential,
              std::unique_ptr<SambaInterface> samba_interface,
              bool metadata_cache_enabled)
        : mount_root(mount_root),
          credential(std::move(credential)),
          samba_interface(std::move(samba_interface)) {
      auto cache_mode = metadata_cache_enabled ? MetadataCache::Mode::kStandard
                                               : MetadataCache::Mode::kDisabled;
      cache = std::make_unique<MetadataCache>(
          tick_clock, base::Microseconds(kMetadataCacheLifetimeMicroseconds),
          cache_mode);
    }
    MountInfo(const MountInfo&) = delete;
    MountInfo& operator=(const MountInfo&) = delete;

    MountInfo& operator=(MountInfo&& other) = default;

    std::string mount_root;
    SmbCredential credential;
    std::unique_ptr<SambaInterface> samba_interface;
    std::unique_ptr<MetadataCache> cache;

  };

  // Returns true if |mount_id| exists as a value in |samba_interface_map_|.
  // This method is only used for DCHECK to ensure that |mounts_| is in sync
  // |samba_interface_map_|
  bool ExistsInSambaInterfaceMap(const int32_t mount_id) const;

  // Returns a new MountInfo.
  MountInfo CreateMountInfo(const std::string& mount_root,
                            SmbCredential credential,
                            std::unique_ptr<SambaInterface> samba_interface);

  // Adds |samba_interface_id| to |mount_id| mapping to |samba_interface_map_|.
  void AddSambaInterfaceIdToSambaInterfaceMap(int32_t mount_id);

  // Returns the SambaInterfaceId corresponding to the |mount_id|.
  SambaInterface::SambaInterfaceId GetSambaInterfaceIdForMountId(
      int32_t mount_id) const;

  // Removes |samba_interface_id| from |samba_interface_map_|.
  void DeleteSambaInterfaceIdFromSambaInterfaceMap(int32_t mount_id);

  // Maps MountId to MountInfo.
  IdMap<MountInfo> mounts_;

  // Maps SambaInterfaceId to MountId.
  std::unordered_map<SambaInterface::SambaInterfaceId, int32_t>
      samba_interface_map_;

  std::unique_ptr<base::TickClock> tick_clock_;
  bool metadata_cache_enabled_;
};

}  // namespace smbprovider

#endif  // SMBPROVIDER_MOUNT_TRACKER_H_
