// Copyright 2017 The Cobalt Authors. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "cobalt/browser/memory_tracker/tool/print_tool.h"

#include <map>
#include <sstream>
#include <string>
#include <vector>

#include "base/basictypes.h"
#include "base/threading/platform_thread.h"
#include "cobalt/base/c_val.h"
#include "cobalt/browser/memory_tracker/tool/util.h"
#include "nb/analytics/memory_tracker.h"
#include "nb/analytics/memory_tracker_helpers.h"
#include "starboard/common/log.h"
#include "starboard/types.h"

namespace cobalt {
namespace browser {
namespace memory_tracker {

using nb::analytics::AllocationGroup;

class PrintTool::CvalsMap {
 public:
  typedef base::CVal<base::cval::SizeInBytes> CValType;

  ~CvalsMap() {
    while (!map_.empty()) {
      MapCvals::iterator it = map_.begin();
      delete it->second;
      map_.erase(it);
    }
  }

  void Update(const std::string& name, size_t value) {
    std::string cval_name = GetCvalName(name);
    CValType*& val = map_[cval_name];
    if (!val) {
      // Create if not found.
      val = new CValType(cval_name, 0,
                         "Automatically generated by the "
                         "browser::memory_tracker system.");
    }
    (*val) = value;
  }

  static std::string GetCvalName(const std::string& name) {
    std::stringstream ss;
    ss << "Memory.Scope." << name;
    return ss.str();
  }

 private:
  typedef std::map<std::string, CValType*> MapCvals;
  MapCvals map_;
};

PrintTool::PrintTool() : cvals_map_(new CvalsMap) {}

PrintTool::~PrintTool() {}

void PrintTool::Run(Params* params) {
  const std::string kSeparator =
      "--------------------------------------------------";

  while (!params->finished()) {
    std::vector<const AllocationGroup*> vector_output;
    params->memory_tracker()->GetAllocationGroups(&vector_output);

    typedef std::map<std::string, const AllocationGroup*> Map;
    typedef Map::const_iterator MapIt;

    Map output;
    for (size_t i = 0; i < vector_output.size(); ++i) {
      const AllocationGroup* group = vector_output[i];
      output[group->name()] = group;
    }

    int32 num_allocs = 0;
    int64 total_bytes = 0;

    struct F {
      static void PrintRow(std::stringstream* ss, const std::string& v1,
                           const std::string& v2, const std::string& v3) {
        ss->width(25);
        *ss << std::left << v1;
        ss->width(13);
        *ss << std::right << v2 << "  ";
        ss->width(10);
        *ss << std::right << v3 << "\n";
      }
    };

    if (params->memory_tracker()->IsMemoryTrackingEnabled()) {
      // If this isn't true then it would cause an infinite loop. The
      // following will likely crash.
      SB_DCHECK(false) << "Unexpected, memory tracking should be disabled.";
    }

    std::stringstream ss;

    ss << kNewLine;
    ss << "TimeNow " << params->TimeInMinutesString()
       << " (minutes):" << kNewLine << kNewLine;

    ss << kSeparator << kNewLine;
    nb::analytics::MemoryStats memstats =
        nb::analytics::GetProcessMemoryStats();

    F::PrintRow(&ss, "MALLOC STAT", "IN USE BYTES", "");
    ss << kSeparator << kNewLine;
    F::PrintRow(&ss, "Total CPU Reserved",
                NumberFormatWithCommas(memstats.total_cpu_memory), "");

    F::PrintRow(&ss, "Total CPU Used",
                NumberFormatWithCommas(memstats.used_cpu_memory), "");

    F::PrintRow(&ss, "Total GPU Reserved",
                NumberFormatWithCommas(memstats.total_gpu_memory), "");

    F::PrintRow(&ss, "Total GPU Used",
                NumberFormatWithCommas(memstats.used_gpu_memory), "");

    ss << kSeparator << kNewLine << kNewLine;

    ss << kSeparator << kNewLine;
    F::PrintRow(&ss, "MEMORY REGION", "IN USE BYTES", "NUM ALLOCS");
    ss << kSeparator << kNewLine;

    for (MapIt it = output.begin(); it != output.end(); ++it) {
      const AllocationGroup* group = it->second;
      if (!group) {
        continue;
      }

      int32 num_group_allocs = -1;
      int64 total_group_bytes = -1;

      group->GetAggregateStats(&num_group_allocs, &total_group_bytes);
      SB_DCHECK(-1 != num_group_allocs);
      SB_DCHECK(-1 != total_group_bytes);

      cvals_map_->Update(group->name(), static_cast<size_t>(total_group_bytes));

      num_allocs += num_group_allocs;
      total_bytes += total_group_bytes;

      F::PrintRow(&ss, it->first, NumberFormatWithCommas(total_group_bytes),
                  NumberFormatWithCommas(num_group_allocs));
    }

    cvals_map_->Update("Total", static_cast<size_t>(total_bytes));

    ss << kNewLine;

    F::PrintRow(&ss, "Total (in groups above)",
                NumberFormatWithCommas(total_bytes),
                NumberFormatWithCommas(num_allocs));

    ss << kSeparator << kNewLine;
    ss << kNewLine << kNewLine;

    params->logger()->Output(ss.str().c_str());
    // Output once every 5 seconds.
    base::PlatformThread::Sleep(base::TimeDelta::FromSeconds(5));
  }
}

std::string PrintTool::tool_name() const { return "MemoryTrackerPrintThread"; }

}  // namespace memory_tracker
}  // namespace browser
}  // namespace cobalt
