/*
 *  Copyright 2004 The WebRTC Project Authors. All rights reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include <time.h>

#if defined(WEBRTC_WIN)
#include "webrtc/base/win32.h"
#endif

#include <algorithm>
#include "webrtc/base/common.h"
#include "webrtc/base/diskcache.h"
#include "webrtc/base/fileutils.h"
#include "webrtc/base/pathutils.h"
#include "webrtc/base/stream.h"
#include "webrtc/base/stringencode.h"
#include "webrtc/base/stringutils.h"

#if !defined(NDEBUG)
#define TRANSPARENT_CACHE_NAMES 1
#else
#define TRANSPARENT_CACHE_NAMES 0
#endif

namespace rtc {

class DiskCache;

///////////////////////////////////////////////////////////////////////////////
// DiskCacheAdapter
///////////////////////////////////////////////////////////////////////////////

class DiskCacheAdapter : public StreamAdapterInterface {
public:
  DiskCacheAdapter(const DiskCache* cache, const std::string& id, size_t index,
                   StreamInterface* stream)
  : StreamAdapterInterface(stream), cache_(cache), id_(id), index_(index)
  { }
  ~DiskCacheAdapter() override {
    Close();
    cache_->ReleaseResource(id_, index_);
  }

private:
  const DiskCache* cache_;
  std::string id_;
  size_t index_;
};

///////////////////////////////////////////////////////////////////////////////
// DiskCache
///////////////////////////////////////////////////////////////////////////////

DiskCache::DiskCache() : max_cache_(0), total_size_(0), total_accessors_(0) {
}

DiskCache::~DiskCache() {
  ASSERT(0 == total_accessors_);
}

bool DiskCache::Initialize(const std::string& folder, size_t size) {
  if (!folder_.empty() || !Filesystem::CreateFolder(folder))
    return false;

  folder_ = folder;
  max_cache_ = size;
  ASSERT(0 == total_size_);

  if (!InitializeEntries())
    return false;

  return CheckLimit();
}

bool DiskCache::Purge() {
  if (folder_.empty())
    return false;

  if (total_accessors_ > 0) {
    LOG_F(LS_WARNING) << "Cache files open";
    return false;
  }

  if (!PurgeFiles())
    return false;

  map_.clear();
  return true;
}

bool DiskCache::LockResource(const std::string& id) {
  Entry* entry = GetOrCreateEntry(id, true);
  if (LS_LOCKED == entry->lock_state)
    return false;
  if ((LS_UNLOCKED == entry->lock_state) && (entry->accessors > 0))
    return false;
  if ((total_size_ > max_cache_) && !CheckLimit()) {
    LOG_F(LS_WARNING) << "Cache overfull";
    return false;
  }
  entry->lock_state = LS_LOCKED;
  return true;
}

StreamInterface* DiskCache::WriteResource(const std::string& id, size_t index) {
  Entry* entry = GetOrCreateEntry(id, false);
  if (LS_LOCKED != entry->lock_state)
    return NULL;

  size_t previous_size = 0;
  std::string filename(IdToFilename(id, index));
  FileStream::GetSize(filename, &previous_size);
  ASSERT(previous_size <= entry->size);
  if (previous_size > entry->size) {
    previous_size = entry->size;
  }

  scoped_ptr<FileStream> file(new FileStream);
  if (!file->Open(filename, "wb", NULL)) {
    LOG_F(LS_ERROR) << "Couldn't create cache file";
    return NULL;
  }

  entry->streams = std::max(entry->streams, index + 1);
  entry->size -= previous_size;
  total_size_ -= previous_size;

  entry->accessors += 1;
  total_accessors_ += 1;
  return new DiskCacheAdapter(this, id, index, file.release());
}

bool DiskCache::UnlockResource(const std::string& id) {
  Entry* entry = GetOrCreateEntry(id, false);
  if (LS_LOCKED != entry->lock_state)
    return false;

  if (entry->accessors > 0) {
    entry->lock_state = LS_UNLOCKING;
  } else {
    entry->lock_state = LS_UNLOCKED;
    entry->last_modified = time(0);
    CheckLimit();
  }
  return true;
}

StreamInterface* DiskCache::ReadResource(const std::string& id,
                                         size_t index) const {
  const Entry* entry = GetEntry(id);
  if (LS_UNLOCKED != entry->lock_state)
    return NULL;
  if (index >= entry->streams)
    return NULL;

  scoped_ptr<FileStream> file(new FileStream);
  if (!file->Open(IdToFilename(id, index), "rb", NULL))
    return NULL;

  entry->accessors += 1;
  total_accessors_ += 1;
  return new DiskCacheAdapter(this, id, index, file.release());
}

bool DiskCache::HasResource(const std::string& id) const {
  const Entry* entry = GetEntry(id);
  return (NULL != entry) && (entry->streams > 0);
}

bool DiskCache::HasResourceStream(const std::string& id, size_t index) const {
  const Entry* entry = GetEntry(id);
  if ((NULL == entry) || (index >= entry->streams))
    return false;

  std::string filename = IdToFilename(id, index);

  return FileExists(filename);
}

bool DiskCache::DeleteResource(const std::string& id) {
  Entry* entry = GetOrCreateEntry(id, false);
  if (!entry)
    return true;

  if ((LS_UNLOCKED != entry->lock_state) || (entry->accessors > 0))
    return false;

  bool success = true;
  for (size_t index = 0; index < entry->streams; ++index) {
    std::string filename = IdToFilename(id, index);

    if (!FileExists(filename))
      continue;

    if (!DeleteFile(filename)) {
      LOG_F(LS_ERROR) << "Couldn't remove cache file: " << filename;
      success = false;
    }
  }

  total_size_ -= entry->size;
  map_.erase(id);
  return success;
}

bool DiskCache::CheckLimit() {
#if !defined(NDEBUG)
  // Temporary check to make sure everything is working correctly.
  size_t cache_size = 0;
  for (EntryMap::iterator it = map_.begin(); it != map_.end(); ++it) {
    cache_size += it->second.size;
  }
  ASSERT(cache_size == total_size_);
#endif

  // TODO: Replace this with a non-brain-dead algorithm for clearing out the
  // oldest resources... something that isn't O(n^2)
  while (total_size_ > max_cache_) {
    EntryMap::iterator oldest = map_.end();
    for (EntryMap::iterator it = map_.begin(); it != map_.end(); ++it) {
      if ((LS_UNLOCKED != it->second.lock_state) || (it->second.accessors > 0))
        continue;
      oldest = it;
      break;
    }
    if (oldest == map_.end()) {
      LOG_F(LS_WARNING) << "All resources are locked!";
      return false;
    }
    for (EntryMap::iterator it = oldest++; it != map_.end(); ++it) {
      if (it->second.last_modified < oldest->second.last_modified) {
        oldest = it;
      }
    }
    if (!DeleteResource(oldest->first)) {
      LOG_F(LS_ERROR) << "Couldn't delete from cache!";
      return false;
    }
  }
  return true;
}

std::string DiskCache::IdToFilename(const std::string& id, size_t index) const {
#ifdef TRANSPARENT_CACHE_NAMES
  // This escapes colons and other filesystem characters, so the user can't open
  // special devices (like "COM1:"), or access other directories.
  size_t buffer_size = id.length()*3 + 1;
  char* buffer = new char[buffer_size];
  encode(buffer, buffer_size, id.data(), id.length(),
         unsafe_filename_characters(), '%');
  // TODO: ASSERT(strlen(buffer) < FileSystem::MaxBasenameLength());
#else  // !TRANSPARENT_CACHE_NAMES
  // We might want to just use a hash of the filename at some point, both for
  // obfuscation, and to avoid both filename length and escaping issues.
  ASSERT(false);
#endif  // !TRANSPARENT_CACHE_NAMES

  char extension[32];
  sprintfn(extension, ARRAY_SIZE(extension), ".%u", index);

  Pathname pathname;
  pathname.SetFolder(folder_);
  pathname.SetBasename(buffer);
  pathname.SetExtension(extension);

#ifdef TRANSPARENT_CACHE_NAMES
  delete [] buffer;
#endif  // TRANSPARENT_CACHE_NAMES

  return pathname.pathname();
}

bool DiskCache::FilenameToId(const std::string& filename, std::string* id,
                             size_t* index) const {
  Pathname pathname(filename);
  unsigned tempdex;
  if (1 != sscanf(pathname.extension().c_str(), ".%u", &tempdex))
    return false;

  *index = static_cast<size_t>(tempdex);

  size_t buffer_size = pathname.basename().length() + 1;
  char* buffer = new char[buffer_size];
  decode(buffer, buffer_size, pathname.basename().data(),
         pathname.basename().length(), '%');
  id->assign(buffer);
  delete [] buffer;
  return true;
}

DiskCache::Entry* DiskCache::GetOrCreateEntry(const std::string& id,
                                              bool create) {
  EntryMap::iterator it = map_.find(id);
  if (it != map_.end())
    return &it->second;
  if (!create)
    return NULL;
  Entry e;
  e.lock_state = LS_UNLOCKED;
  e.accessors = 0;
  e.size = 0;
  e.streams = 0;
  e.last_modified = time(0);
  it = map_.insert(EntryMap::value_type(id, e)).first;
  return &it->second;
}

void DiskCache::ReleaseResource(const std::string& id, size_t index) const {
  const Entry* entry = GetEntry(id);
  if (!entry) {
    LOG_F(LS_WARNING) << "Missing cache entry";
    ASSERT(false);
    return;
  }

  entry->accessors -= 1;
  total_accessors_ -= 1;

  if (LS_UNLOCKED != entry->lock_state) {
    // This is safe, because locked resources only issue WriteResource, which
    // is non-const.  Think about a better way to handle it.
    DiskCache* this2 = const_cast<DiskCache*>(this);
    Entry* entry2 = this2->GetOrCreateEntry(id, false);

    size_t new_size = 0;
    std::string filename(IdToFilename(id, index));
    FileStream::GetSize(filename, &new_size);
    entry2->size += new_size;
    this2->total_size_ += new_size;

    if ((LS_UNLOCKING == entry->lock_state) && (0 == entry->accessors)) {
      entry2->last_modified = time(0);
      entry2->lock_state = LS_UNLOCKED;
      this2->CheckLimit();
    }
  }
}

///////////////////////////////////////////////////////////////////////////////

} // namespace rtc
