blob: 505ef7f7a2f047549b6c56b771cefb745cce1459 [file] [log] [blame]
/*
* Copyright © 2012 Linaro Limited
*
* This file is part of glmark2.
*
* glmark2 is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* glmark2 is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with glmark2. If not, see <http://www.gnu.org/licenses/>.
*
* Authors:
* Simon Que <sque@chromium.org>
*/
#define __STDC_FORMAT_MACROS
#include <inttypes.h>
#include <stdio.h>
#include <sys/time.h>
#include "timer.h"
#include "util.h"
Timer::Timer(int max_cycles, const std::string& name) {
data_.resize(max_cycles);
timestamp_count_ = 0;
cycle_count_ = 0;
max_cycles_ = max_cycles;
current_cycle_data_ = &data_[0];
timer_list[name] = this;
name_ = name;
}
Timer::~Timer() {
timer_list.erase(name_);
}
void Timer::set_max_timestamps(int max_timestamps) {
max_timestamps_ = max_timestamps;
for (std::vector<std::vector<uint64_t> >::iterator iter = data_.begin();
iter != data_.end(); ++iter) {
(*iter).resize(max_timestamps);
}
}
void Timer::next_cycle() {
// However many timestamps have been recorded on the first cycle is the max
// number of timestamps allowed on subsequent cycles.
if (cycle_count_ == 0) {
set_max_timestamps(timestamp_count_);
} else if (timestamp_count_ < max_timestamps_) {
for (int i = timestamp_count_; i < max_timestamps_; i += 1)
(*current_cycle_data_)[i] =
(*current_cycle_data_)[timestamp_count_ - 1];
}
if (cycle_count_ < max_cycles_) {
cycle_count_ += 1;
timestamp_count_ = 0;
current_cycle_data_ = &data_[cycle_count_];
}
}
void Timer::read_timestamp(int id) {
// Do not read a timestamp if we've exceeded the max number of timestamps
// (established by number of calls on cycle 0) or the max number of cycles.
if (timestamp_count_ >= max_timestamps_ && cycle_count_ > 0)
return;
if (cycle_count_ >= max_cycles_)
return;
// First cycle has no limit to timestamps.
// Subsequent cycles must not exceed that number of timestamps.
if (cycle_count_ == 0) {
timestamp_ids_.push_back(id);
data_[0].push_back(Util::get_timestamp_us());
} else {
(*current_cycle_data_)[timestamp_count_] = Util::get_timestamp_us();
}
timestamp_count_ += 1;
}
void Timer::print_results() {
unsigned int i;
int j;
for (i = 0; i < timestamp_ids_.size() - 1; i += 1)
printf("\t%d", timestamp_ids_[i]);
printf("\n");
for (i = 0; i < timestamp_ids_.size(); i += 1)
printf("========");
printf("\n");
for (j = 0; j < cycle_count_; j += 1) {
std::vector<uint64_t>& current = data_[j];
if (j > 0)
printf("%" PRIi64 "", current[0] - data_[j-1][max_timestamps_-1]);
for(int i = 0; i < max_timestamps_ - 1; i++) {
printf("\t%" PRIi64 "", current[i + 1] - current[i]);
}
printf("\n");
}
}
Timer* Timer::get_timer(const std::string& name) {
std::map<std::string, Timer*>::const_iterator iter = timer_list.find(name);
if (iter == timer_list.end())
return NULL;
return iter->second;
}
std::map<std::string, Timer*> Timer::timer_list;